diff options
Diffstat (limited to 'httemplate/elements')
-rw-r--r-- | httemplate/elements/contact.html | 2 | ||||
-rw-r--r-- | httemplate/elements/cust_pkg_usageprice.html | 9 | ||||
-rw-r--r-- | httemplate/elements/email-link.html | 3 | ||||
-rw-r--r-- | httemplate/elements/form-create_ticket.html | 2 | ||||
-rw-r--r-- | httemplate/elements/form-file_upload.html | 1 | ||||
-rw-r--r-- | httemplate/elements/htmlarea.html | 4 | ||||
-rw-r--r-- | httemplate/elements/images/ui-icons_ef8c08_256x240.png | bin | 0 -> 4369 bytes | |||
-rw-r--r-- | httemplate/elements/menu.html | 4 | ||||
-rw-r--r-- | httemplate/elements/order_pkg.js | 68 | ||||
-rw-r--r-- | httemplate/elements/polygon.html | 127 | ||||
-rw-r--r-- | httemplate/elements/popup_link-send_report_batch.html | 28 | ||||
-rw-r--r-- | httemplate/elements/schedule-appointment.html | 3 | ||||
-rw-r--r-- | httemplate/elements/select-terms.html | 2 | ||||
-rw-r--r-- | httemplate/elements/select-tower_sector.html | 7 | ||||
-rw-r--r-- | httemplate/elements/template_image-dialog.html | 279 | ||||
-rw-r--r-- | httemplate/elements/tr-pkg_svc.html | 67 | ||||
-rw-r--r-- | httemplate/elements/tr-polygon.html | 5 | ||||
-rw-r--r-- | httemplate/elements/tr-select-months.html | 1 | ||||
-rw-r--r-- | httemplate/elements/tr-td-label.html | 2 |
19 files changed, 518 insertions, 96 deletions
diff --git a/httemplate/elements/contact.html b/httemplate/elements/contact.html index ef74481c0..87e15debe 100644 --- a/httemplate/elements/contact.html +++ b/httemplate/elements/contact.html @@ -135,7 +135,7 @@ tie my %label, 'Tie::IxHash', my $first = 0; foreach my $phone_type ( qsearch({table=>'phone_type', order_by=>'weight'}) ) { - next if $phone_type->typename eq 'Home'; + next if $phone_type->typename =~ /^(Home|Fax)$/; my $f = 'phonetypenum'.$phone_type->phonetypenum; $label{$f} = $phone_type->typename. ' phone'; $size{$f} = $first++ ? 10 : 15; diff --git a/httemplate/elements/cust_pkg_usageprice.html b/httemplate/elements/cust_pkg_usageprice.html index 729099320..74b7842be 100644 --- a/httemplate/elements/cust_pkg_usageprice.html +++ b/httemplate/elements/cust_pkg_usageprice.html @@ -23,15 +23,16 @@ > % my $info = $part_pkg_usageprice->target_info; % my $amount = $part_pkg_usageprice->amount / ($info->{multiplier}||1); - <OPTION VALUE="">Additional <% $info->{label} %> + <OPTION VALUE="">Additional <% $info->{label} %></OPTION> % for (1..100) { #100? arbitrary. - <OPTION VALUE="<% $_ %>"><% +% my $selected = ($opt{'curr_quantity'} == $_) ? ' SELECTED' : ''; + <OPTION VALUE="<% $_ %>"<% $selected %>><% $money_char. sprintf('%.2f', $_ * $part_pkg_usageprice->price ). ' '. 'for'. #( $part_pkg_usageprice->action eq 'increment' ? 'per' : 'for' ). ' '. ( $_ * $amount ). ' '. $info->{label} - %> + %></OPTION> % } </SELECT> </TD> @@ -42,8 +43,6 @@ % } <%init> -#my $targets = FS::part_pkg_usageprice->targets; - my( %opt ) = @_; my $conf = new FS::Conf; diff --git a/httemplate/elements/email-link.html b/httemplate/elements/email-link.html index 2612faabb..16935cf98 100644 --- a/httemplate/elements/email-link.html +++ b/httemplate/elements/email-link.html @@ -10,7 +10,8 @@ die "'table' required" if !$table; die "'search_hash' required" if !$search_hash; my $uri = new URI; -$uri->query_form($search_hash); +my @params = map { $_, $search_hash->{$_} } sort keys %$search_hash; +$uri->query_form(@params); my $query = $uri->query; my $label = ($opt{'label'} || 'Email a notice to these customers'); </%init> diff --git a/httemplate/elements/form-create_ticket.html b/httemplate/elements/form-create_ticket.html index 362e82397..d76c0d83e 100644 --- a/httemplate/elements/form-create_ticket.html +++ b/httemplate/elements/form-create_ticket.html @@ -6,7 +6,7 @@ function updateTicketLink() { link.href = "<% $new_base.'?'. join(';', map( { ($_ eq 'Queue') ? () : "$_=$new_param{$_}"} - keys %new_param),'Queue=') %>" + selector.options[selector.selectedIndex].value; + sort keys %new_param),'Queue=') %>" + selector.options[selector.selectedIndex].value; } </SCRIPT> <A NAME="tickets"><FONT CLASS="fsinnerbox-title">Tickets</FONT></A> diff --git a/httemplate/elements/form-file_upload.html b/httemplate/elements/form-file_upload.html index 45b6c97f2..3542a5a8e 100644 --- a/httemplate/elements/form-file_upload.html +++ b/httemplate/elements/form-file_upload.html @@ -69,6 +69,7 @@ Example: <div style="display:none:" id="uploadError"></div> <FORM NAME = "<% $opt{name} %>" + ID = "<% $opt{id} %>" ACTION = "<% $fsurl %>misc/file-upload.html" METHOD = "POST" ENCTYPE = "multipart/form-data" diff --git a/httemplate/elements/htmlarea.html b/httemplate/elements/htmlarea.html index 7c40e61c7..d8b25121a 100644 --- a/httemplate/elements/htmlarea.html +++ b/httemplate/elements/htmlarea.html @@ -12,7 +12,7 @@ Example: </%doc> % #init -<SCRIPT TYPE="text/javascript" src="<% $p %>elements/ckeditor/ckeditor.js"> +<SCRIPT TYPE="text/javascript" src="<% $fsurl %>elements/ckeditor/ckeditor.js"> </SCRIPT> % #editor @@ -35,7 +35,7 @@ my $config = { 'skin' => 'kama', 'toolbarCanCollapse' => JSON::true, 'removePlugins' => 'elementspath', - 'basePath' => $p.'elements/ckeditor/', + 'basePath' => $fsurl.'elements/ckeditor/', 'enterMode' => 2, %{ $opt{config} || {} }, }; diff --git a/httemplate/elements/images/ui-icons_ef8c08_256x240.png b/httemplate/elements/images/ui-icons_ef8c08_256x240.png Binary files differnew file mode 100644 index 000000000..85e63e9f6 --- /dev/null +++ b/httemplate/elements/images/ui-icons_ef8c08_256x240.png diff --git a/httemplate/elements/menu.html b/httemplate/elements/menu.html index a5fb15bc2..ea6933198 100644 --- a/httemplate/elements/menu.html +++ b/httemplate/elements/menu.html @@ -381,6 +381,8 @@ if( $curuser->access_right('Financial reports') ) { $report_financial{'Tax Liability (vendor tax data)'} = [ $fsurl.'search/report_newtax.html', 'Tax liability report (vendor tax data)' ] if $taxproducts; + $report_financial{'Monthly Sales and Taxes'} = [$fsurl.'search/tax_sales.html', 'Monthly sales and taxes report']; + # most sites don't need this but there isn't really a config to enable it $report_financial{'E911 Fee Summary'} = [ $fsurl.'search/report_e911.html', 'E911 fee summary' ]; @@ -767,7 +769,7 @@ tie my %config_nms, 'Tie::IxHash', ; tie my %config_misc, 'Tie::IxHash'; -$config_misc{'Message templates'} = [ $fsurl.'browse/msg_template.html', 'Templates for customer notices' ] +$config_misc{'Message templates'} = [ $fsurl.'browse/msg_template/email.html', 'Templates for customer notices' ] if $curuser->access_right(['View templates', 'View global templates', 'Edit templates', 'Edit global templates', ]); $config_misc{'Advertising sources'} = [ $fsurl.'browse/part_referral.html', 'Where a customer heard about your service.' ] diff --git a/httemplate/elements/order_pkg.js b/httemplate/elements/order_pkg.js index 3586a54cb..a850d2193 100644 --- a/httemplate/elements/order_pkg.js +++ b/httemplate/elements/order_pkg.js @@ -1,10 +1,12 @@ function pkg_changed () { var form = document.OrderPkgForm; var discountnum = form.discountnum; + var opt = form.pkgpart.options[form.pkgpart.selectedIndex]; + + usageprice_pkg_changed( opt.value ); if ( form.pkgpart.selectedIndex > 0 ) { - var opt = form.pkgpart.options[form.pkgpart.selectedIndex]; var date_button = document.getElementById('start_date_button'); var date_button_disabled = document.getElementById('start_date_disabled'); var date_text = document.getElementById('start_date_text'); @@ -68,78 +70,14 @@ function pkg_changed () { } } - get_part_pkg_usageprice( opt.value, update_part_pkg_usageprice ); - } else { form.submitButton.disabled = true; if ( discountnum ) { form.discountnum.disabled = true; } discountnum_changed(form.discountnum); } -} - -function update_part_pkg_usageprice(part_pkg_usageprice) { - - var table = document.getElementById('cust_pkg_usageprice_table'); - - // black the current usage price rows - for ( var r = table.rows.length - 1; r >= 0; r-- ) { - table.deleteRow(r); - } - - // add the new usage price rows - var rownum = 0; - var usagepriceArray = eval('(' + part_pkg_usageprice + ')' ); - for ( var s = 0; s < usagepriceArray.length; s=s+2 ) { - //surely this should be some kind of JSON structure - var html = usagepriceArray[s+0]; - var javascript = usagepriceArray[s+1]; - - // a lot like ("inspiried by") edit/elements/edit.html function spawn_<%$field%> - - // XXX evaluate the javascript - //if (window.ActiveXObject) { - // window.execScript(newfunc); - //} else { /* (window.XMLHttpRequest) */ - // //window.eval(newfunc); - // setTimeout(newfunc, 0); - //} - - var row = table.insertRow(rownum++); - - //var label_cell = document.createElement('TD'); - - //label_cell.id = '<% $field %>_label' + <%$field%>_fieldnum; - - //label_cell.style.textAlign = "right"; - //label_cell.style.verticalAlign = "top"; - //label_cell.style.borderTop = "1px solid black"; - //label_cell.style.paddingTop = "5px"; - - //label_cell.innerHTML = '<% $label %>'; - - //row.appendChild(label_cell); - - var widget_cell = document.createElement('TD'); - - //widget_cell.style.borderTop = "1px solid black"; - widget_cell.style.paddingTop = "3px"; - widget_cell.colSpan = "2"; - - widget_cell.innerHTML = html; - - row.appendChild(widget_cell); - - } - - if ( rownum > 0 ) { - document.getElementById('cust_pkg_usageprice_title').style.display = ''; - } else { - document.getElementById('cust_pkg_usageprice_title').style.display = 'none'; - } } - function standardize_new_location() { var form = document.OrderPkgForm; var loc = form.locationnum; diff --git a/httemplate/elements/polygon.html b/httemplate/elements/polygon.html new file mode 100644 index 000000000..c26e98546 --- /dev/null +++ b/httemplate/elements/polygon.html @@ -0,0 +1,127 @@ +<%init> +my %opt = @_; +my $field = $opt{'field'}; +my $id = $opt{'id'} || $opt{'field'}; +my $div_id = "div_$id"; + +my $vertices_json = $opt{'curr_value'} || '[]'; +</%init> +<& hidden.html, %opt &> +<div id="<% $div_id %>" style="height: 600px; width: 600px"></div> + +<script src="https://maps.googleapis.com/maps/api/js?libraries=drawing"></script> +<script> +var map; +var drawingManager; + +function updateFormInput(event) { + var path = window.polygon.getPath(); + var vertices = []; // array of arrays, geoJSON style + for (var i =0; i < path.getLength(); i++) { + var xy = path.getAt(i); + vertices[i] = [ xy.lat(), xy.lng() ]; + } + console.log(vertices); //XXX + $('#<% $field %>').prop('value', JSON.stringify(vertices)); +} + +$(function() { + mapOptions = { + zoom: 4, + center: {lat: 39.40114, lng: -96.57127}, // continental U.S. + mapTypeId: google.maps.MapTypeId.ROADMAP, + panControl: true, + scaleControl: true, + streetViewControl: false, + }; + map = new google.maps.Map($('#<% $div_id %>')[0], mapOptions); + + var polygonComplete = function(p) { + window.polygon = p; + if (drawingManager) { + drawingManager.setDrawingMode(null); + drawingManager.setOptions({ drawingControl: false }); + } + // double click to delete a vertex (so long as it remains a polygon) + p.addListener('dblclick', function (mev) { + if (mev.vertex != null && window.polygon.getPath().length > 3) { + p.getPath().removeAt(mev.vertex); + } + }); + // any time the polygon is modified, update the vertex list + p.getPath().addListener('set_at', updateFormInput); + p.getPath().addListener('insert_at', updateFormInput); + p.getPath().addListener('remove_at', updateFormInput); + + // and also now + updateFormInput(); + }; + + var polygonOptions = { + fillColor: '#0000a0', + fillOpacity: 0.2, + strokeColor: '#0000a0', + strokeWeight: 2, + clickable: false, + editable: true, + zIndex: 1, + map: map, + }; + + var vertex_array = <% $vertices_json %>; + if ( vertex_array.length > 2 ) { + // then we already have a polygon. make it acceptable to google maps, + // and also create a bounding box for it and fit the map to that. + + var path = []; + var bounds = new google.maps.LatLngBounds(); + for (var i = 0; i < vertex_array.length; i++) { + var xy = new google.maps.LatLng(vertex_array[i][0], vertex_array[i][1]); + path.push(xy); + bounds.extend(xy); + } + + polygonOptions.paths = [ path ]; + polygonComplete(new google.maps.Polygon(polygonOptions)); + map.fitBounds(bounds); + + } else { + // there are no vertices, or not enough to make a polygon, so + // enable drawing mode to create a new one + + drawingManager = new google.maps.drawing.DrawingManager({ + drawingMode: google.maps.drawing.OverlayType.POLYGON, + drawingControl: true, + drawingControlOptions: { + position: google.maps.ControlPosition.TOP_CENTER, + drawingModes: [ + google.maps.drawing.OverlayType.POLYGON, + ] + }, + polygonOptions: polygonOptions, + }); + + // after a single polygon is drawn: remember it, add a listener to let + // nodes be deleted, and exit drawing mode + drawingManager.addListener('polygoncomplete', polygonComplete); + drawingManager.setMap(map); + + // center the map on the user (for lack of a better choice) + if (navigator.geolocation) { + navigator.geolocation.getCurrentPosition(function(position) { + var pos = { + lat: position.coords.latitude, + lng: position.coords.longitude + }; + + map.setCenter(pos); + map.setZoom(12); + }); + } // on error, or if geolocation isn't available, do nothing + } + +}); + + </script> + </body> +</html> diff --git a/httemplate/elements/popup_link-send_report_batch.html b/httemplate/elements/popup_link-send_report_batch.html new file mode 100644 index 000000000..5f4471054 --- /dev/null +++ b/httemplate/elements/popup_link-send_report_batch.html @@ -0,0 +1,28 @@ +<%doc> + +Example: + +<& /elements/popup_link-send_report_batch.html, + reportname => 'sales_commission_pkg', + label => 'Click here to send reports by email', +&> +</%doc> +<& /elements/popup_link.html, $params &>\ +<%init> + +my $params = { 'closetext' => emt('Close') }; + +if (ref($_[0]) eq 'HASH') { + $params = { %$params, %{ $_[0] } }; +} else { + $params = { %$params, @_ }; +} + +$params->{'label'} ||= emt('Send reports by email'); +$params->{'actionlabel'} ||= emt('Send reports'); +#$params->{'width'} ||= 350; +$params->{'height'} ||= 650; + +$params->{'action'} = $fsurl. 'misc/send-report.html?reportname='. $params->{'reportname'}; + +</%init> diff --git a/httemplate/elements/schedule-appointment.html b/httemplate/elements/schedule-appointment.html index 45a8a5bab..69b9f422b 100644 --- a/httemplate/elements/schedule-appointment.html +++ b/httemplate/elements/schedule-appointment.html @@ -12,7 +12,8 @@ my $custnum = encode_entities( $cgi->param('custnum') ); my $query = join('&', map "username=$_", @username). "&LengthMin=$LengthMin". - "&custnum=$custnum"; + "&custnum=$custnum". + "&RedirectToBasics=1"; #XXX '&pkgnum=$pkgnum";need to be for specific package/location, not just for a customer... default to active(/ordered) package in a pkg_class w/ticketing_queueid, otherwise, a popup? we're getting complicated like form-creat_ticket.html my $url = $p. 'rt/Search/Schedule.html?'. $query; diff --git a/httemplate/elements/select-terms.html b/httemplate/elements/select-terms.html index 716832f52..a330df17c 100644 --- a/httemplate/elements/select-terms.html +++ b/httemplate/elements/select-terms.html @@ -36,7 +36,7 @@ my $empty_value = $opt{'empty_value'} || ''; my @terms = ( emt('Payable upon receipt'), ( map "Net $_", - 0, 3, 5, 9, 10, 14, 15, 18, 20, 21, 25, 30, 45, 60, 90 ), + 0, 3, 5, 7, 9, 10, 14, 15, 18, 20, 21, 25, 30, 45, 60, 90 ), ); my @pre_options = $opt{pre_options} ? @{ $opt{pre_options} } : (); diff --git a/httemplate/elements/select-tower_sector.html b/httemplate/elements/select-tower_sector.html index a16d3bfa0..76ff25223 100644 --- a/httemplate/elements/select-tower_sector.html +++ b/httemplate/elements/select-tower_sector.html @@ -2,6 +2,8 @@ <& /elements/select-table.html, table => 'tower_sector', name_col => 'description', + addl_from => 'JOIN tower USING (towernum)', + extra_sql => q(WHERE disabled = '' OR disabled IS NULL), order_by => 'ORDER BY towernum,sectorname', empty_label => ' ', @_ @@ -11,8 +13,9 @@ <& /elements/select-table.html, table => 'tower', name_col => 'towername', + hashref => { 'disabled' => '', }, id => 'towernum', - field => 'dummy_towernum', + field => 'towernum', onchange => 'change_towernum(this.value);', element_etc => 'STYLE="vertical-align:top"', &> @@ -63,5 +66,5 @@ foreach my $towernum (keys %sectors_of) { } } -my $empty_label = $opt{'empty_label'} || 'Include services with no tower/sector'; +my $empty_label = $opt{'empty_label'} || 'Include services with no sector'; </%init> diff --git a/httemplate/elements/template_image-dialog.html b/httemplate/elements/template_image-dialog.html new file mode 100644 index 000000000..b471d28da --- /dev/null +++ b/httemplate/elements/template_image-dialog.html @@ -0,0 +1,279 @@ +<%doc> + +Creates a jquery dialog box that opens when javascript function insertImageDialog +is called, allows user to select an image and specify attributes for it, then passes +img tag with base64 encoded data url to a callback javascript function. + +Accepts the following options: + +callback - pass the html for the selected img to this javascript function; +if omitted, will only include fields for viewing/uploading image + +url - to redirect to after upload, otherwise just refreshes dialog window + +</%doc> + +<% include('/elements/xmlhttp.html', + 'url' => $fsurl.'misc/xmlhttp-template_image.cgi', + 'subs' => [ 'get_template_image' ], + ) %> + +<DIV ID="insert_image_dialog" title="Template Images"> + +<TABLE BORDER="0" STYLE="width: 100%"><TR><TD> + +<FORM ID="insert_image_form"> + +<% &ntable("#cccccc", 2) %> + + <TR> + <TH>Image</TH> + <TD> + <SELECT ID="insert_image_imgnum" ONCHANGE="insertImageDialog($('#insert_image_imgnum').val())"> + <OPTION VALUE="">(select an image)</OPTION> + </SELECT> + </TD> + </TR> +% if ($opt{'callback'}) { + <TR> + <TH>Width</TH> + <TD><INPUT TYPE="text" SIZE="5" ID="insert_image_width" ONCHANGE="previewInsertImage()"></TD> + </TR> + <TR> + <TH>Height</TH> + <TD><INPUT TYPE="text" SIZE="5" ID="insert_image_height" ONCHANGE="previewInsertImage()"></TD> + </TR> + <TR> + <TH>Align</TH> + <TD> + <SELECT ID="insert_image_float" ONCHANGE="previewInsertImage()"> + <OPTION VALUE="none">inline</OPTION> + <OPTION VALUE="left">left</OPTION> + <OPTION VALUE="right">right</OPTION> + </SELECT> + </TD> + </TR> + <TR> + <TH>Alt Text</TH> + <TD><INPUT TYPE="text" SIZE="20" ID="insert_image_alt" ONCHANGE="previewInsertImage()"></TD> + </TR> + <TR> + <TD COLSPAN="2" ALIGN="center" STYLE="padding-top:6px"> + <INPUT TYPE="button" ID="insert_image_button" VALUE="Insert Image" ONCLICK="insertImage()"> + </TD> + </TR> +% } # if $opt{'callback'} + +</TABLE> + +</FORM> + +% if ($canedit) { + +<P><B><% emt('Upload New Image') %></B></P> + +<% include('/elements/form-file_upload.html', + 'name' => 'TemplateImageUploadForm', + 'id' => 'TemplateImageUploadForm', + 'action' => $fsurl.'misc/process/template_image-upload.cgi', + 'num_files' => 1, + 'fields' => [ 'name', 'agentnum' ], + 'url' => $opt{'url'} || 'javascript:refreshImageList(1)', + ) + %> + + <% &ntable("#cccccc", 2) %> + + <% include( '/elements/tr-input-text.html', + 'field' => 'name', + 'label' => 'Name', + 'required' => 1, + 'id' => 'upload_form_name', + ) + %> + + <% include( '/elements/tr-select-agent.html', + 'label' => "<B>Agent</B>", + 'empty_label' => '(global)', + 'agent_virt' => 1, + 'agent_null_right' => 'Edit global templates', + ) + %> + + <% include( '/elements/tr-file-upload.html', + 'field' => 'file', + 'label' => 'File', + ) + %> + + <TR> + <TD COLSPAN="2" ALIGN="center" STYLE="padding-top:6px"> + <INPUT TYPE = "submit" + NAME = "submitButton" + ID = "submitButton" + VALUE = "Upload image" + > + </TD> + </TR> + +</TABLE> + +</FORM> + +% } #if canedit + +</TD><TD width="100%"> + +<DIV ID="insert_image_preview_box"> + <P><B><% emt('Image Preview') %></B></P> + <SPAN ID="insert_image_loading"><B>(<% emt('Loading image...') %>)</B></SPAN> + <IMG SRC="" ID="insert_image_preview"> +</DIV> + +</TD></TR></TABLE> +</DIV> + +<SCRIPT> + +// initialize & close dialog window, initialize imgobj cache && image list +$( '#insert_image_dialog' ).dialog({ + width: 800, + height: 550, + resizable: true, + autoOpen: false, +}); +var imgobj = new Object; +refreshImageList(0); + +// this is the main func to invoke from links outside this file. +// opens dialog if needed +// updates dialog with passed imgnum +// caches image info through an xmlhttp request if needed +// pass 'upload' as imgnum for upload-only view +function insertImageDialog (imgnum) { + if (imgnum == 'upload') { + $('#insert_image_form').hide(); + $('#insert_image_preview_box').hide(); + imgnum = undefined; + } else { + $('#insert_image_form').show(); + $('#insert_image_preview_box').show(); + } + if (imgnum && !imgobj[imgnum]) { + clearInsertImageDialog(); + $('#insert_image_loading').show(); + $('#insert_image_imgnum').val(imgnum); + get_template_image('imgnum',imgnum, + function (result) { + var images = JSON.parse(result) || []; + for (i = 0; i < images.length; i++) { + imgobj[images[i].imgnum] = images[i]; + } + updateInsertImageDialog(); + } + ); + } else if (imgnum) { + $('#insert_image_imgnum').val(imgnum); + updateInsertImageDialog(); + } else { + clearInsertImageDialog(); + } + if (!$( '#insert_image_dialog' ).dialog( 'isOpen' )) { + $( '#insert_image_dialog' ).dialog( 'open' ); + } +} + +// sets dialog values to a default "Loading..." state, including imgnum +function clearInsertImageDialog () { + $('#insert_image_imgnum').val(''); + $('#insert_image_preview').attr('src',''); + $('#insert_image_loading').hide(); +} + +// updates preview src from cache based on imgnum from form +// then calls previewInsertImage +function updateInsertImageDialog () { + var imgnum = $('#insert_image_imgnum').val(); + $('#insert_image_loading').hide(); + $('#insert_image_preview').attr('src',imgobj[imgnum].src); + previewInsertImage(); +} + +// updates preview width/height/alt/float based on current form values +function previewInsertImage () { + $('#insert_image_preview').css('width',$('#insert_image_width').val()); + $('#insert_image_preview').css('height',$('#insert_image_height').val()); + $('#insert_image_preview').css('float',$('#insert_image_float').val()); + $('#insert_image_preview').attr('alt',$('#insert_image_alt').val()); +} + +// constructs html based on the form contents, +// passes it to callback & closes dialog +function insertImage() { + var imgnum = $('#insert_image_imgnum').val(); + if (!(imgnum && imgobj[imgnum])) { + return ''; + } + var width = $('#insert_image_width').val() || ''; + var height = $('#insert_image_height').val() || ''; + var alt = $('#insert_image_alt').val() || ''; + var float = $('#insert_image_float').val(); + var imgtag = '<IMG SRC="' + imgobj[imgnum].src + '"'; + if (width) { + imgtag += ' WIDTH="' + width + '"'; + } + if (height) { + imgtag += ' HEIGHT="' + height + '"'; + } + if (alt) { + imgtag += ' ALT="' + alt + '"'; + } + if (float) { + imgtag += ' STYLE="float: ' + float + '"'; + } + imgtag += '>'; + <% $opt{'callback'} %>(imgtag); + $( '#insert_image_dialog' ).dialog( 'close' ); +} + +// uses xmlhttp request to initialize image list & refresh it after uploads +function refreshImageList (fromupload) { + get_template_image('no_src','1', + function (result) { + if (fromupload) { + $("#TemplateImageUploadForm")[0].reset(); + } + var images = JSON.parse(result) || []; + var latest; + for (i = 0; i < images.length; i++) { + if ( $("#insert_image_imgnum option[value='" + images[i].imgnum + "']").length == 0 ) { + $("#insert_image_imgnum").append('<OPTION VALUE="'+images[i].imgnum+'">'+images[i].name+'</OPTION>'); + latest = images[i].imgnum; + } + } + if (fromupload) { + location.hash = "insert_image_dialog"; + if (latest) { + // small risk of a race condition with other newly-uploaded images, + // but does no real damage (our image still shows up in the list) + insertImageDialog(latest); + } + } + } + ); +} + +</SCRIPT> + +<%init> +my %opt = @_; + +my $curuser = $FS::CurrentUser::CurrentUser; + +die "access denied" + unless $curuser->access_right([ 'View templates', 'View global templates', + 'Edit templates', 'Edit global templates', ]); + +my $canedit = $curuser->access_right([ 'Edit templates', 'Edit global templates' ]); +</%init> + diff --git a/httemplate/elements/tr-pkg_svc.html b/httemplate/elements/tr-pkg_svc.html index cfef51ce2..de3f95a3a 100644 --- a/httemplate/elements/tr-pkg_svc.html +++ b/httemplate/elements/tr-pkg_svc.html @@ -1,8 +1,13 @@ <TR> <TD CLASS="background" COLSPAN=99> +<SCRIPT> +var provision_hold_td = []; +var provision_hold_input = []; +</SCRIPT> + <% itable('', 4, 1) %><TR><TD VALIGN="top"> -<% $thead %> +<% pkg_svc_thead() %> %foreach my $part_svc ( @part_svc ) { % my $svcpart = $part_svc->svcpart; @@ -78,24 +83,52 @@ <INPUT TYPE="checkbox" NAME="no_bulk_skip<% $svcpart %>" VALUE="Y"<% $bulk_skip =~ /^Y/i ? '' : ' CHECKED' %>> </TD> - <TD ALIGN="center"> - <INPUT TYPE="checkbox" NAME="provision_hold<% $svcpart %>" VALUE="Y"<% $provision_hold =~ /^Y/i ? ' CHECKED' : ''%>> + <TD ALIGN="center" ID="td_provision_hold<% $svcpart %>"> + <INPUT TYPE="checkbox" ID="input_provision_hold<% $svcpart %>" NAME="provision_hold<% $svcpart %>" VALUE="Y"<% $provision_hold =~ /^Y/i ? ' CHECKED' : ''%>> </TD> +<SCRIPT> +provision_hold_td.push(document.getElementById('td_provision_hold<% $svcpart %>')); +provision_hold_input.push(document.getElementById('input_provision_hold<% $svcpart %>')); +</SCRIPT> </TR> % foreach ( 1 .. $columns-1 ) { % if ( $count == int( $_ * scalar(@part_svc) / $columns ) ) { % - </TABLE></TD><TD VALIGN="top"><% $thead %> + </TABLE></TD><TD VALIGN="top"><% pkg_svc_thead() %> % } % } % $count++; % -% } +% } # foreach $part_svc </TR></TABLE></TD></TR></TABLE> +<SCRIPT> +// start_on_hold from edit/part_pkg.cgi +// toggles display of provision_hold checkboxes when that changes +function provision_hold_check () { + var start_on_hold = document.getElementById('start_on_hold'); + if (start_on_hold) { + for (i = 0; i < provision_hold_td.length; i++) { + provision_hold_td[i].style.display = start_on_hold.checked ? '' : 'none'; + } + for (i = 0; i < provision_hold_input.length; i++) { + provision_hold_input[i].disabled = start_on_hold.checked ? false : true; + } + } +} +function provision_hold_init () { + var start_on_hold = document.getElementById('start_on_hold'); + if (start_on_hold) { + start_on_hold.onchange = provision_hold_check; + provision_hold_check(); + } +} +provision_hold_init(); +</SCRIPT> + % if ( scalar(@possible_exports) > 0 || scalar(@mapped_exports) > 0 ) { <TABLE><TR> <TH BGCOLOR="#dcdcdc">Export</TH> @@ -130,15 +163,21 @@ my %opt = @_; my $cgi = $opt{'cgi'}; -my $thead = "\n\n". ntable('#cccccc', 2). - '<TR>'. - '<TH BGCOLOR="#dcdcdc"><FONT SIZE=-1>Quan.</FONT></TH>'. - '<TH BGCOLOR="#dcdcdc"><FONT SIZE=-1>Primary</FONT></TH>'. - '<TH BGCOLOR="#dcdcdc">Service</TH>'. - '<TH BGCOLOR="#dcdcdc"><FONT SIZE=-1>Hide<BR>from<BR>Invoices</FONT></TH>'. - '<TH BGCOLOR="#dcdcdc"><FONT SIZE=-1>Bulk<BR>Charge</FONT></TH>'. - '<TH BGCOLOR="#dcdcdc"><FONT SIZE=-1>Hold<BR>Until<BR>Provision</FONT></TH>'. - '</TR>'; +my $thead_count = 0; +sub pkg_svc_thead { + $thead_count += 1; + return "\n\n". ntable('#cccccc', 2). + '<TR>'. + '<TH BGCOLOR="#dcdcdc"><FONT SIZE=-1>Quan.</FONT></TH>'. + '<TH BGCOLOR="#dcdcdc"><FONT SIZE=-1>Primary</FONT></TH>'. + '<TH BGCOLOR="#dcdcdc">Service</TH>'. + '<TH BGCOLOR="#dcdcdc"><FONT SIZE=-1>Hide<BR>from<BR>Invoices</FONT></TH>'. + '<TH BGCOLOR="#dcdcdc"><FONT SIZE=-1>Bulk<BR>Charge</FONT></TH>'. + '<TH BGCOLOR="#dcdcdc" ID="th_provision_hold' . $thead_count . '"><FONT SIZE=-1>Remove Hold After Provisioning</FONT></TH>'. + '</TR>'. + qq!<SCRIPT>provision_hold_td.push(document.getElementById('th_provision_hold$thead_count'))</SCRIPT>!; +; +} my $part_pkg = $opt{'object'}; my $pkgpart = $part_pkg->pkgpart; diff --git a/httemplate/elements/tr-polygon.html b/httemplate/elements/tr-polygon.html new file mode 100644 index 000000000..6990d3da6 --- /dev/null +++ b/httemplate/elements/tr-polygon.html @@ -0,0 +1,5 @@ +<tr> +<td colspan=2> +<& polygon.html, @_ &> +</td> +</tr> diff --git a/httemplate/elements/tr-select-months.html b/httemplate/elements/tr-select-months.html index 3ff28f99b..b90ce1ed7 100644 --- a/httemplate/elements/tr-select-months.html +++ b/httemplate/elements/tr-select-months.html @@ -7,6 +7,5 @@ $opt{labels} = { '' => '', map { $_ => emt('[quant,_1,month]', $_) } 1 .. $max }; -warn Dumper(\%opt); </%init> <& tr-select.html, %opt &> diff --git a/httemplate/elements/tr-td-label.html b/httemplate/elements/tr-td-label.html index 78690f1fb..f7067221b 100644 --- a/httemplate/elements/tr-td-label.html +++ b/httemplate/elements/tr-td-label.html @@ -9,7 +9,7 @@ Actually <TR> <TH> $label </TH> VALIGN = "<% $opt{'valign'} || 'top' %>" STYLE = "<% $style %>" ID = "<% $opt{label_id} || $opt{id}. '_label0' %>" - ><% $required %><% $opt{label} %></TD> + ><% $required %><% $opt{label} %></TH> <%init> |