WooCommerce PDF Invoices & Packing Slips - Version 2.5.0

Version Description

  • Feature: Manually regenerate individual documents with latest settings (shop address/footer/etc)
  • Feature: Shortcode to download invoice: [wcpdf_download_invoice]
  • Feature: Logo height setting
  • Fix: textdomain fallback would fail on specific site domains including .mo
  • Fix: Unnecessary extra page on edge case table heights
  • Fix: Settings disappearing when overriding document titles to empty string
  • Fix: check if header logo file still exists before loading
  • Fix: If document is already created, disregard 'disable for:' setting
  • Fix: Reading document settings & number when stored incorrectly (by external plugins)
  • Tested up to WooCommerce 4.2
Download this release

Release Info

Developer pomegranate
Plugin Icon 128x128 WooCommerce PDF Invoices & Packing Slips
Version 2.5.0
Comparing to
See all releases

Code changes from version 2.4.10 to 2.5.0

assets/css/order-styles.css CHANGED
@@ -67,13 +67,47 @@
67
  margin-left:20px!important;
68
  }
69
 
70
- .dashicons-edit,
71
- .dashicons-trash {
 
72
  opacity:0.5;
73
  }
74
 
75
- .dashicons-edit:hover,
76
- .dashicons-trash:hover {
 
77
  opacity:1;
78
  cursor:pointer;
79
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
67
  margin-left:20px!important;
68
  }
69
 
70
+ .wcpdf-data-fields .wpo-wcpdf-edit-date-number,
71
+ .wcpdf-data-fields .wpo-wcpdf-delete-document,
72
+ .wcpdf-data-fields .wpo-wcpdf-regenerate-document {
73
  opacity:0.5;
74
  }
75
 
76
+ .wcpdf-data-fields .wpo-wcpdf-edit-date-number:hover,
77
+ .wcpdf-data-fields .wpo-wcpdf-delete-document:hover,
78
+ .wcpdf-data-fields .wpo-wcpdf-regenerate-document:hover {
79
  opacity:1;
80
  cursor:pointer;
81
  }
82
+
83
+ .wcpdf-data-fields h4 .wcpdf-regenerate-spin {
84
+ opacity: 1;
85
+ -webkit-animation: spin 1.6s linear infinite; /* Safari */
86
+ animation: spin 1.6s linear infinite;
87
+ pointer-events: none;
88
+ }
89
+
90
+ /* Safari */
91
+ @-webkit-keyframes wcpdf-regenerate-spin {
92
+ 0% { -webkit-transform: rotate(0deg); }
93
+ 100% { -webkit-transform: rotate(-360deg); }
94
+ }
95
+
96
+ @keyframes wcpdf-regenerate-spin {
97
+ 0% { transform: rotate(0deg); }
98
+ 100% { transform: rotate(-360deg); }
99
+ }
100
+
101
+ .wcpdf-data-fields .document-action-success,
102
+ .wcpdf-data-fields .document-action-failed {
103
+ display: none;
104
+ vertical-align: middle;
105
+ }
106
+
107
+ .wcpdf-data-fields .document-action-success {
108
+ color: #2aad2a;
109
+ }
110
+
111
+ .wcpdf-data-fields .document-action-failed {
112
+ color: red;
113
+ }
assets/js/order-script.js CHANGED
@@ -1,69 +1,107 @@
1
- jQuery(document).ready(function($) {
2
- $("#doaction, #doaction2").click(function (event) {
3
- var actionselected = $(this).attr("id").substr(2);
4
- var action = $('select[name="' + actionselected + '"]').val();
5
- if ( $.inArray(action, wpo_wcpdf_ajax.bulk_actions) !== -1 ) {
6
- event.preventDefault();
7
- var template = action;
8
- var checked = [];
9
- $('tbody th.check-column input[type="checkbox"]:checked').each(
10
- function() {
11
- checked.push($(this).val());
12
- }
13
- );
14
-
15
- if (!checked.length) {
16
- alert('You have to select order(s) first!');
17
- return;
18
- }
19
-
20
- var order_ids=checked.join('x');
21
-
22
- if (wpo_wcpdf_ajax.ajaxurl.indexOf("?") != -1) {
23
- url = wpo_wcpdf_ajax.ajaxurl+'&action=generate_wpo_wcpdf&document_type='+template+'&order_ids='+order_ids+'&_wpnonce='+wpo_wcpdf_ajax.nonce;
24
- } else {
25
- url = wpo_wcpdf_ajax.ajaxurl+'?action=generate_wpo_wcpdf&document_type='+template+'&order_ids='+order_ids+'&_wpnonce='+wpo_wcpdf_ajax.nonce;
26
- }
27
-
28
- window.open(url,'_blank');
29
- }
30
- });
31
-
32
- $('#wpo_wcpdf-data-input-box').insertAfter('#woocommerce-order-data');
33
-
34
- // enable invoice number edit if user initiated
35
- $( ".wpo-wcpdf-set-date-number, .wpo-wcpdf-edit-date-number" ).click(function() {
36
- $form = $(this).closest('.wcpdf-data-fields');
37
- $form.find(".read-only").hide();
38
- $form.find(".editable").show();
39
- $form.find(':input').prop('disabled', false);
40
- });
41
-
42
- $( ".wcpdf-data-fields .wpo-wcpdf-delete-document" ).click(function() {
43
- if ( window.confirm( wpo_wcpdf_ajax.confirm_delete ) === false ) {
44
- return; // having second thoughts
45
- }
46
-
47
- $form = $(this).closest('.wcpdf-data-fields');
48
- $.ajax({
49
- url: wpo_wcpdf_ajax.ajaxurl,
50
- data: {
51
- action : 'wpo_wcpdf_delete_document',
52
- security: $(this).data('nonce'),
53
- document: $form.data('document'),
54
- order_id: $form.data('order_id')
55
- },
56
- type: 'POST',
57
- context: $form,
58
- success: function( response ) {
59
- if ( response.success ) {
60
- $(this).find(':input').val("");
61
- $(this).find('.read-only').hide();
62
- $(this).find('.wpo-wcpdf-delete-document').hide();
63
- }
64
- }
65
- });
66
- });
67
-
68
- });
69
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ jQuery(document).ready(function($) {
2
+ $("#doaction, #doaction2").click(function (event) {
3
+ var actionselected = $(this).attr("id").substr(2);
4
+ var action = $('select[name="' + actionselected + '"]').val();
5
+ if ( $.inArray(action, wpo_wcpdf_ajax.bulk_actions) !== -1 ) {
6
+ event.preventDefault();
7
+ var template = action;
8
+ var checked = [];
9
+ $('tbody th.check-column input[type="checkbox"]:checked').each(
10
+ function() {
11
+ checked.push($(this).val());
12
+ }
13
+ );
14
+
15
+ if (!checked.length) {
16
+ alert('You have to select order(s) first!');
17
+ return;
18
+ }
19
+
20
+ var order_ids=checked.join('x');
21
+
22
+ if (wpo_wcpdf_ajax.ajaxurl.indexOf("?") != -1) {
23
+ url = wpo_wcpdf_ajax.ajaxurl+'&action=generate_wpo_wcpdf&document_type='+template+'&order_ids='+order_ids+'&_wpnonce='+wpo_wcpdf_ajax.nonce;
24
+ } else {
25
+ url = wpo_wcpdf_ajax.ajaxurl+'?action=generate_wpo_wcpdf&document_type='+template+'&order_ids='+order_ids+'&_wpnonce='+wpo_wcpdf_ajax.nonce;
26
+ }
27
+
28
+ window.open(url,'_blank');
29
+ }
30
+ });
31
+
32
+ $('#wpo_wcpdf-data-input-box').insertAfter('#woocommerce-order-data');
33
+
34
+ // enable invoice number edit if user initiated
35
+ $( ".wpo-wcpdf-set-date-number, .wpo-wcpdf-edit-date-number" ).click(function() {
36
+ $form = $(this).closest('.wcpdf-data-fields');
37
+ $form.find(".read-only").hide();
38
+ $form.find(".editable").show();
39
+ $form.find(':input').prop('disabled', false);
40
+ });
41
+
42
+ $( ".wcpdf-data-fields .wpo-wcpdf-delete-document" ).click(function() {
43
+ if ( window.confirm( wpo_wcpdf_ajax.confirm_delete ) === false ) {
44
+ return; // having second thoughts
45
+ }
46
+
47
+ $form = $(this).closest('.wcpdf-data-fields');
48
+
49
+ //Hide regenerate button
50
+ $form.find('.wpo-wcpdf-regenerate-document').hide();
51
+
52
+ $.ajax({
53
+ url: wpo_wcpdf_ajax.ajaxurl,
54
+ data: {
55
+ action : 'wpo_wcpdf_delete_document',
56
+ security: $(this).data('nonce'),
57
+ document: $form.data('document'),
58
+ order_id: $form.data('order_id')
59
+ },
60
+ type: 'POST',
61
+ context: $form,
62
+ success: function( response ) {
63
+ if ( response.success ) {
64
+ $(this).find(':input').val("");
65
+ $(this).find('.read-only').hide();
66
+ $(this).find('.wpo-wcpdf-delete-document').hide();
67
+ }
68
+ }
69
+ });
70
+ });
71
+
72
+ $( ".wcpdf-data-fields .wpo-wcpdf-regenerate-document" ).click(function() {
73
+
74
+ if ( window.confirm( wpo_wcpdf_ajax.confirm_regenerate ) === false ) {
75
+ return; // having second thoughts
76
+ }
77
+
78
+ $(this).addClass('wcpdf-regenerate-spin');
79
+ $form = $(this).closest('.wcpdf-data-fields');
80
+
81
+ // Make sure all feedback icons are hidden before each call
82
+ $form.find('.document-action-success, .document-action-failed').hide();
83
+
84
+ $.ajax({
85
+ url: wpo_wcpdf_ajax.ajaxurl,
86
+ data: {
87
+ action : 'wpo_wcpdf_regenerate_document',
88
+ security: $(this).data('nonce'),
89
+ document: $form.data('document'),
90
+ order_id: $form.data('order_id')
91
+ },
92
+ type: 'POST',
93
+ context: $form,
94
+ success: function( response ) {
95
+ if ( response.success ) {
96
+ $(this).find('.document-action-success').show();
97
+ } else {
98
+ $error = $(this).find('.document-action-failed').show();
99
+ }
100
+ $(this).find('.wpo-wcpdf-regenerate-document').removeClass('wcpdf-regenerate-spin');
101
+ }
102
+ });
103
+
104
+ });
105
+
106
+ });
107
+
includes/class-wcpdf-admin.php CHANGED
@@ -46,8 +46,12 @@ class Admin {
46
  add_filter( 'pre_get_posts', array( $this, 'pre_get_posts_sort_by_invoice_number' ) );
47
  }
48
 
49
- // AJAX action for deleting document data
50
- add_action( 'wp_ajax_wpo_wcpdf_delete_document', array($this, 'delete_document' ) );
 
 
 
 
51
  }
52
 
53
  // display review admin notice after 100 pdf downloads
@@ -432,6 +436,18 @@ class Admin {
432
  do_action( 'wpo_wcpdf_meta_box_end', $post->ID );
433
  }
434
 
 
 
 
 
 
 
 
 
 
 
 
 
435
  /**
436
  * Add actions to menu, WP3.5+
437
  */
@@ -672,6 +688,46 @@ class Admin {
672
  }
673
  }
674
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
675
  public function debug_enabled_warning( $wp_admin_bar ) {
676
  if ( isset(WPO_WCPDF()->settings->debug_settings['enable_debug']) && current_user_can( 'administrator' ) ) {
677
  $status_settings_url = 'admin.php?page=wpo_wcpdf_options_page&tab=debug';
46
  add_filter( 'pre_get_posts', array( $this, 'pre_get_posts_sort_by_invoice_number' ) );
47
  }
48
 
49
+ // AJAX actions for deleting and regenerating document data
50
+ add_action( 'wp_ajax_wpo_wcpdf_delete_document', array( $this, 'delete_document' ) );
51
+ add_action( 'wp_ajax_wpo_wcpdf_regenerate_document', array( $this, 'regenerate_document' ) );
52
+
53
+ add_action( 'wpo_wcpdf_document_actions', array( $this, 'add_regenerate_document_button' ) );
54
+ add_action( 'wpo_wcpdf_document_actions', array( $this, 'add_document_action_feedback_icons' ) );
55
  }
56
 
57
  // display review admin notice after 100 pdf downloads
436
  do_action( 'wpo_wcpdf_meta_box_end', $post->ID );
437
  }
438
 
439
+ public function add_regenerate_document_button( $document ) {
440
+ $document_settings = $document->get_settings( true );
441
+ if ( $document->use_historical_settings() == true || isset( $document_settings['archive_pdf'] ) ) {
442
+ printf( '<span class="wpo-wcpdf-regenerate-document dashicons dashicons-update-alt" data-nonce="%s"></span>', wp_create_nonce( "wpo_wcpdf_regenerate_document" ) );
443
+ }
444
+ }
445
+
446
+ public function add_document_action_feedback_icons( $document ) {
447
+ echo '<span class="dashicons dashicons-yes document-action-success"></span>';
448
+ echo '<span class="dashicons dashicons-no document-action-failed"></span>';
449
+ }
450
+
451
  /**
452
  * Add actions to menu, WP3.5+
453
  */
688
  }
689
  }
690
 
691
+ public function regenerate_document() {
692
+ if ( check_ajax_referer( "wpo_wcpdf_regenerate_document", 'security', false ) === false ) {
693
+ wp_send_json_error( array(
694
+ 'message' => 'nonce expired',
695
+ ) );
696
+ }
697
+ if ( empty($_POST['order_id']) || empty($_POST['document']) ) {
698
+ wp_send_json_error( array(
699
+ 'message' => 'incomplete request',
700
+ ) );
701
+ }
702
+ if ( !current_user_can('manage_woocommerce') ) {
703
+ wp_send_json_error( array(
704
+ 'message' => 'no permissions',
705
+ ) );
706
+ }
707
+
708
+ $order_id = absint($_POST['order_id']);
709
+ $document = sanitize_text_field($_POST['document']);
710
+
711
+ try {
712
+ $document = wcpdf_get_document( $document, wc_get_order( $order_id ) );
713
+ if ( !empty($document) && $document->exists() ) {
714
+ $document->regenerate();
715
+ $response = array(
716
+ 'message' => $document->get_type()." regenerated",
717
+ );
718
+ wp_send_json_success($response);
719
+ } else {
720
+ wp_send_json_error( array(
721
+ 'message' => 'document does not exist',
722
+ ) );
723
+ }
724
+ } catch (\Exception $e) {
725
+ wp_send_json_error( array(
726
+ 'message' => 'error: '.$e->getMessage(),
727
+ ) );
728
+ }
729
+ }
730
+
731
  public function debug_enabled_warning( $wp_admin_bar ) {
732
  if ( isset(WPO_WCPDF()->settings->debug_settings['enable_debug']) && current_user_can( 'administrator' ) ) {
733
  $status_settings_url = 'admin.php?page=wpo_wcpdf_options_page&tab=debug';
includes/class-wcpdf-assets.php CHANGED
@@ -89,6 +89,7 @@ class Assets {
89
  'nonce' => wp_create_nonce('generate_wpo_wcpdf'),
90
  'bulk_actions' => array_keys( $bulk_actions ),
91
  'confirm_delete' => __( 'Are you sure you want to delete this document? This cannot be undone.', 'woocommerce-pdf-invoices-packing-slips'),
 
92
  )
93
  );
94
  }
89
  'nonce' => wp_create_nonce('generate_wpo_wcpdf'),
90
  'bulk_actions' => array_keys( $bulk_actions ),
91
  'confirm_delete' => __( 'Are you sure you want to delete this document? This cannot be undone.', 'woocommerce-pdf-invoices-packing-slips'),
92
+ 'confirm_regenerate' => __( 'Are you sure you want to regenerate this document? This will make the document reflect the most current settings (such as footer text, document name, etc.) rather than using historical settings.', 'woocommerce-pdf-invoices-packing-slips'),
93
  )
94
  );
95
  }
includes/class-wcpdf-frontend.php CHANGED
@@ -16,6 +16,7 @@ class Frontend {
16
  function __construct() {
17
  add_filter( 'woocommerce_my_account_my_orders_actions', array( $this, 'my_account_pdf_link' ), 10, 2 );
18
  add_filter( 'woocommerce_api_order_response', array( $this, 'woocommerce_api_invoice_number' ), 10, 2 );
 
19
  }
20
 
21
  /**
@@ -79,6 +80,50 @@ class Frontend {
79
  $this->restore_storing_document_settings();
80
  }
81
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
82
  /**
83
  * Document objects are created in order to check for existence and retrieve data,
84
  * but we don't want to store the settings for uninitialized documents.
16
  function __construct() {
17
  add_filter( 'woocommerce_my_account_my_orders_actions', array( $this, 'my_account_pdf_link' ), 10, 2 );
18
  add_filter( 'woocommerce_api_order_response', array( $this, 'woocommerce_api_invoice_number' ), 10, 2 );
19
+ add_shortcode( 'wcpdf_download_invoice', array($this, 'download_invoice_shortcode') );
20
  }
21
 
22
  /**
80
  $this->restore_storing_document_settings();
81
  }
82
 
83
+ /**
84
+ * Download invoice frontend shortcode
85
+ */
86
+ public function download_invoice_shortcode( $atts ) {
87
+
88
+ if( is_admin() ) return;
89
+
90
+ // Default values
91
+ $values = shortcode_atts(array(
92
+ 'order_id' => '',
93
+ 'link_text' => ''
94
+ ), $atts);
95
+ if( !$values ) return;
96
+
97
+ // Get $order
98
+ if( is_checkout() && !empty(is_wc_endpoint_url('order-received')) && empty($values['order_id']) ) {
99
+ $order = wc_get_order( $_GET['order-received'] );
100
+ } elseif( is_account_page() && !empty(is_wc_endpoint_url('view-order')) && empty($values['order_id']) ) {
101
+ $order = wc_get_order( $_GET['view-order'] );
102
+ } elseif( !empty($values['order_id']) ) {
103
+ $order = wc_get_order( $values['order_id'] );
104
+ }
105
+ if( !is_object($order) || !isset($order) || empty($order) ) return;
106
+
107
+ // Link text
108
+ $link_text = __('Download invoice (PDF)', 'woocommerce-pdf-invoices-packing-slips');
109
+ if( ! empty($values['link_text']) ) {
110
+ $link_text = $values['link_text'];
111
+ }
112
+
113
+ // User permissions
114
+ $debug_settings = get_option('wpo_wcpdf_settings_debug', array());
115
+ if( is_user_logged_in() ) {
116
+ $pdf_url = wp_nonce_url( admin_url( 'admin-ajax.php?action=generate_wpo_wcpdf&template_type=invoice&order_ids=' . $order->get_id() . '&my-account'), 'generate_wpo_wcpdf' );
117
+ $text .= '<p><a href="'.esc_attr($pdf_url).'" target="_blank">'.$link_text.'</a></p>';
118
+ } elseif( ! is_user_logged_in() && isset($debug_settings['guest_access']) ) {
119
+ $pdf_url = admin_url( 'admin-ajax.php?action=generate_wpo_wcpdf&template_type=invoice&order_ids=' . $order->get_id() . '&order_key=' . $order->get_order_key() );
120
+ $text .= '<p><a href="'.esc_attr($pdf_url).'" target="_blank">'.$link_text.'</a></p>';
121
+ }
122
+
123
+ return $text;
124
+
125
+ }
126
+
127
  /**
128
  * Document objects are created in order to check for existence and retrieve data,
129
  * but we don't want to store the settings for uninitialized documents.
includes/class-wcpdf-main.php CHANGED
@@ -50,6 +50,9 @@ class Main {
50
  add_action( 'woocommerce_privacy_remove_order_personal_data', array( $this, 'remove_order_personal_data' ), 10, 1 );
51
  // export private data
52
  add_action( 'woocommerce_privacy_export_order_personal_data_meta', array( $this, 'export_order_personal_data_meta' ), 10, 1 );
 
 
 
53
  }
54
 
55
  /**
@@ -616,6 +619,19 @@ class Main {
616
  <?php
617
  }
618
 
 
 
 
 
 
 
 
 
 
 
 
 
 
619
  /**
620
  * Remove attachments older than 1 week (daily, hooked into wp_scheduled_delete )
621
  */
50
  add_action( 'woocommerce_privacy_remove_order_personal_data', array( $this, 'remove_order_personal_data' ), 10, 1 );
51
  // export private data
52
  add_action( 'woocommerce_privacy_export_order_personal_data_meta', array( $this, 'export_order_personal_data_meta' ), 10, 1 );
53
+
54
+ // apply header logo height
55
+ add_action( 'wpo_wcpdf_custom_styles', array( $this, 'set_header_logo_height' ), 9, 2 );
56
  }
57
 
58
  /**
619
  <?php
620
  }
621
 
622
+ /**
623
+ * Apply header logo height from settings
624
+ */
625
+ public function set_header_logo_height( $document_type, $document = null ) {
626
+ if ( !empty($document) && $header_logo_height = $document->get_header_logo_height() ) {
627
+ ?>
628
+ td.header img {
629
+ max-height: <?php echo $header_logo_height; ?>;
630
+ }
631
+ <?php
632
+ }
633
+ }
634
+
635
  /**
636
  * Remove attachments older than 1 week (daily, hooked into wp_scheduled_delete )
637
  */
includes/class-wcpdf-settings-callbacks.php CHANGED
@@ -355,16 +355,29 @@ class Settings_Callbacks {
355
  public function media_upload( $args ) {
356
  extract( $this->normalize_settings_args( $args ) );
357
 
358
- if( !empty($current) ) {
359
- $attachment = wp_get_attachment_image_src( $current, 'full', false );
360
-
361
  $attachment_src = $attachment[0];
362
  $attachment_width = $attachment[1];
363
  $attachment_height = $attachment[2];
364
- $attachment_resolution = round($attachment_height/(3/2.54));
365
-
 
 
 
 
 
 
 
 
 
 
366
  printf('<img src="%1$s" style="display:block" id="img-%4$s"/>', $attachment_src, $attachment_width, $attachment_height, $id );
367
- printf('<div class="attachment-resolution"><p class="description">%s: %sdpi (default height = 3cm)</p></div>', __('Image resolution','woocommerce-pdf-invoices-packing-slips'), $attachment_resolution );
 
 
 
 
368
  printf('<span class="button wpo_remove_image_button" data-input_id="%1$s">%2$s</span>', $id, $remove_button_text );
369
  }
370
 
@@ -531,6 +544,8 @@ class Settings_Callbacks {
531
  // falback to default or empty if no value in option
532
  if ( !isset($args['current']) ) {
533
  $args['current'] = isset( $args['default'] ) ? $args['default'] : '';
 
 
534
  }
535
 
536
  return $args;
355
  public function media_upload( $args ) {
356
  extract( $this->normalize_settings_args( $args ) );
357
 
358
+ if( !empty($current) && $attachment = wp_get_attachment_image_src( $current, 'full', false ) ) {
359
+ $general_settings = get_option('wpo_wcpdf_settings_general');
 
360
  $attachment_src = $attachment[0];
361
  $attachment_width = $attachment[1];
362
  $attachment_height = $attachment[2];
363
+ // check if we have the height saved on settings
364
+ $header_logo_height = !empty($general_settings['header_logo_height']) ? $general_settings['header_logo_height'] : '3cm';
365
+ if ( stripos( $header_logo_height, 'mm' ) != false ) {
366
+ $in_height = floatval($header_logo_height)/25.4;
367
+ } elseif ( stripos( $header_logo_height, 'cm' ) != false ) {
368
+ $in_height = floatval($header_logo_height)/2.54;
369
+ } elseif ( stripos( $header_logo_height, 'in' ) != false ) {
370
+ $in_height = floatval($header_logo_height);
371
+ } else {
372
+ // don't display resolution
373
+ }
374
+
375
  printf('<img src="%1$s" style="display:block" id="img-%4$s"/>', $attachment_src, $attachment_width, $attachment_height, $id );
376
+ if ( !empty($attachment_height) && !empty($in_height) ) {
377
+ $attachment_resolution = round(absint($attachment_height)/$in_height);
378
+ printf('<div class="attachment-resolution"><p class="description">%s: %sdpi</p></div>', __('Image resolution','woocommerce-pdf-invoices-packing-slips'), $attachment_resolution );
379
+ }
380
+
381
  printf('<span class="button wpo_remove_image_button" data-input_id="%1$s">%2$s</span>', $id, $remove_button_text );
382
  }
383
 
544
  // falback to default or empty if no value in option
545
  if ( !isset($args['current']) ) {
546
  $args['current'] = isset( $args['default'] ) ? $args['default'] : '';
547
+ } elseif ( empty($args['current']) && isset($args['default_if_empty']) && $args['default_if_empty'] == true ) { // force fallback if empty 'current' and 'default_if_empty' equals to true
548
+ $args['current'] = isset( $args['default'] ) ? $args['default'] : '';
549
  }
550
 
551
  return $args;
includes/class-wcpdf-settings-documents.php CHANGED
@@ -1,63 +1,76 @@
1
- <?php
2
- namespace WPO\WC\PDF_Invoices;
3
-
4
- if ( ! defined( 'ABSPATH' ) ) {
5
- exit; // Exit if accessed directly
6
- }
7
-
8
- if ( !class_exists( '\\WPO\\WC\\PDF_Invoices\\Settings_Documents' ) ) :
9
-
10
- class Settings_Documents {
11
-
12
- function __construct() {
13
- add_action( 'admin_init', array( $this, 'init_settings' ) );
14
- add_action( 'wpo_wcpdf_settings_output_documents', array( $this, 'output' ), 10, 1 );
15
- }
16
-
17
- public function init_settings() {
18
- $documents = WPO_WCPDF()->documents->get_documents('all');
19
- foreach ($documents as $document) {
20
- $document->init_settings();
21
- }
22
- }
23
-
24
- public function output( $section ) {
25
- $section = !empty($section) ? $section : 'invoice';
26
- if ( !empty( $section ) ) {
27
- $documents = WPO_WCPDF()->documents->get_documents('all');
28
- ?>
29
- <div class="wcpdf_document_settings_sections">
30
- <?php _e( 'Documents', 'woocommerce-pdf-invoices-packing-slips' ); ?>:
31
- <ul>
32
- <?php
33
- foreach ($documents as $document) {
34
- printf('<li><a href="%s" class="%s">%s</a></li>', add_query_arg( 'section', $document->get_type() ), $document->get_type() == $section ? 'active' : '', $document->get_title() );
35
- }
36
- ?>
37
- </ul>
38
- </div>
39
- <?php
40
- settings_fields( "wpo_wcpdf_documents_settings_{$section}" );
41
- do_settings_sections( "wpo_wcpdf_documents_settings_{$section}" );
42
- submit_button();
43
- } else {
44
- $documents = WPO_WCPDF()->documents->get_documents('all');
45
- ?>
46
- <p><?php _e('All available documents are listed below. Click on a document to configure it.', 'woocommerce-pdf-invoices-packing-slips' ); ?></p>
47
- <table class="wcpdf_documents_settings_list">
48
- <?php $c = false; foreach ($documents as $document): ?>
49
- <tr class="<?php echo (($c = !$c)?"odd":"even"); ?>">
50
- <td class="title"><a href="<?php echo add_query_arg( 'section', $document->get_type() ); ?>"><?php echo $document->get_title(); ?></a></td>
51
- <td class="settings-icon"><a href="<?php echo add_query_arg( 'section', $document->get_type() ); ?>"><span class="dashicons dashicons-admin-settings"></span></a></td>
52
- </tr>
53
- <?php endforeach ?>
54
- </table>
55
- <?php
56
- }
57
- }
58
-
59
- }
60
-
61
- endif; // class_exists
62
-
 
 
 
 
 
 
 
 
 
 
 
 
 
63
  return new Settings_Documents();
1
+ <?php
2
+ namespace WPO\WC\PDF_Invoices;
3
+
4
+ if ( ! defined( 'ABSPATH' ) ) {
5
+ exit; // Exit if accessed directly
6
+ }
7
+
8
+ if ( !class_exists( '\\WPO\\WC\\PDF_Invoices\\Settings_Documents' ) ) :
9
+
10
+ class Settings_Documents {
11
+
12
+ function __construct() {
13
+ add_action( 'admin_init', array( $this, 'init_settings' ) );
14
+ add_action( 'wpo_wcpdf_settings_output_documents', array( $this, 'output' ), 10, 1 );
15
+ }
16
+
17
+ public function init_settings() {
18
+ $documents = WPO_WCPDF()->documents->get_documents('all');
19
+ foreach ($documents as $document) {
20
+ $document->init_settings();
21
+ }
22
+ }
23
+
24
+ public function output( $section ) {
25
+ $section = !empty($section) ? $section : 'invoice';
26
+ if ( !empty( $section ) ) {
27
+ $documents = WPO_WCPDF()->documents->get_documents('all');
28
+ ?>
29
+ <div class="wcpdf_document_settings_sections">
30
+ <?php _e( 'Documents', 'woocommerce-pdf-invoices-packing-slips' ); ?>:
31
+ <ul>
32
+ <?php
33
+ foreach ($documents as $document) {
34
+ $title = strip_tags($document->get_title());
35
+ if (empty(trim($title))) {
36
+ $title = '['.__( 'untitled', 'woocommerce-pdf-invoices-packing-slips' ).']';
37
+ }
38
+ printf('<li><a href="%s" class="%s">%s</a></li>', add_query_arg( 'section', $document->get_type() ), $document->get_type() == $section ? 'active' : '', $title );
39
+ }
40
+ ?>
41
+ </ul>
42
+ </div>
43
+ <?php
44
+ settings_fields( "wpo_wcpdf_documents_settings_{$section}" );
45
+ do_settings_sections( "wpo_wcpdf_documents_settings_{$section}" );
46
+ submit_button();
47
+ } else {
48
+ $documents = WPO_WCPDF()->documents->get_documents('all');
49
+ ?>
50
+ <p><?php _e('All available documents are listed below. Click on a document to configure it.', 'woocommerce-pdf-invoices-packing-slips' ); ?></p>
51
+ <table class="wcpdf_documents_settings_list">
52
+ <?php
53
+ $c = false;
54
+ foreach ($documents as $document) {
55
+ $title = strip_tags($document->get_title());
56
+ if (empty(trim($title))) {
57
+ $title = __( 'untitled', 'woocommerce-pdf-invoices-packing-slips' );
58
+ }
59
+ ?>
60
+ <tr class="<?php echo (($c = !$c)?"odd":"even"); ?>">
61
+ <td class="title"><a href="<?php echo add_query_arg( 'section', $document->get_type() ); ?>"><?php echo $title; ?></a></td>
62
+ <td class="settings-icon"><a href="<?php echo add_query_arg( 'section', $document->get_type() ); ?>"><span class="dashicons dashicons-admin-settings"></span></a></td>
63
+ </tr>
64
+ <?php
65
+ }
66
+ ?>
67
+ </table>
68
+ <?php
69
+ }
70
+ }
71
+
72
+ }
73
+
74
+ endif; // class_exists
75
+
76
  return new Settings_Documents();
includes/class-wcpdf-settings-general.php CHANGED
@@ -1,311 +1,327 @@
1
- <?php
2
- namespace WPO\WC\PDF_Invoices;
3
-
4
- if ( ! defined( 'ABSPATH' ) ) {
5
- exit; // Exit if accessed directly
6
- }
7
-
8
- if ( !class_exists( '\\WPO\\WC\\PDF_Invoices\\Settings_General' ) ) :
9
-
10
- class Settings_General {
11
-
12
- function __construct() {
13
- add_action( 'admin_init', array( $this, 'init_settings' ) );
14
- add_action( 'wpo_wcpdf_settings_output_general', array( $this, 'output' ), 10, 1 );
15
- add_action( 'wpo_wcpdf_before_settings', array( $this, 'attachment_settings_hint' ), 10, 2 );
16
- }
17
-
18
- public function output( $section ) {
19
- settings_fields( "wpo_wcpdf_settings_general" );
20
- do_settings_sections( "wpo_wcpdf_settings_general" );
21
-
22
- submit_button();
23
- }
24
-
25
- public function init_settings() {
26
- $page = $option_group = $option_name = 'wpo_wcpdf_settings_general';
27
-
28
- $template_base_path = ( defined( 'WC_TEMPLATE_PATH' ) ? WC_TEMPLATE_PATH : $GLOBALS['woocommerce']->template_url );
29
- $theme_template_path = get_stylesheet_directory() . '/' . $template_base_path;
30
- $wp_content_dir = str_replace( ABSPATH, '', WP_CONTENT_DIR );
31
- $theme_template_path = substr($theme_template_path, strpos($theme_template_path, $wp_content_dir)) . 'pdf/yourtemplate';
32
- $plugin_template_path = "{$wp_content_dir}/plugins/woocommerce-pdf-invoices-packing-slips/templates/Simple";
33
-
34
- $settings_fields = array(
35
- array(
36
- 'type' => 'section',
37
- 'id' => 'general_settings',
38
- 'title' => __( 'General settings', 'woocommerce-pdf-invoices-packing-slips' ),
39
- 'callback' => 'section',
40
- ),
41
- array(
42
- 'type' => 'setting',
43
- 'id' => 'download_display',
44
- 'title' => __( 'How do you want to view the PDF?', 'woocommerce-pdf-invoices-packing-slips' ),
45
- 'callback' => 'select',
46
- 'section' => 'general_settings',
47
- 'args' => array(
48
- 'option_name' => $option_name,
49
- 'id' => 'download_display',
50
- 'options' => array(
51
- 'download' => __( 'Download the PDF' , 'woocommerce-pdf-invoices-packing-slips' ),
52
- 'display' => __( 'Open the PDF in a new browser tab/window' , 'woocommerce-pdf-invoices-packing-slips' ),
53
- ),
54
- )
55
- ),
56
- array(
57
- 'type' => 'setting',
58
- 'id' => 'template_path',
59
- 'title' => __( 'Choose a template', 'woocommerce-pdf-invoices-packing-slips' ),
60
- 'callback' => 'select',
61
- 'section' => 'general_settings',
62
- 'args' => array(
63
- 'option_name' => $option_name,
64
- 'id' => 'template_path',
65
- 'options' => $this->find_templates(),
66
- 'description' => sprintf( __( 'Want to use your own template? Copy all the files from <code>%s</code> to your (child) theme in <code>%s</code> to customize them' , 'woocommerce-pdf-invoices-packing-slips' ), $plugin_template_path, $theme_template_path),
67
- )
68
- ),
69
- array(
70
- 'type' => 'setting',
71
- 'id' => 'paper_size',
72
- 'title' => __( 'Paper size', 'woocommerce-pdf-invoices-packing-slips' ),
73
- 'callback' => 'select',
74
- 'section' => 'general_settings',
75
- 'args' => array(
76
- 'option_name' => $option_name,
77
- 'id' => 'paper_size',
78
- 'options' => apply_filters( 'wpo_wcpdf_template_settings_paper_size', array(
79
- 'a4' => __( 'A4' , 'woocommerce-pdf-invoices-packing-slips' ),
80
- 'letter' => __( 'Letter' , 'woocommerce-pdf-invoices-packing-slips' ),
81
- ) ),
82
- )
83
- ),
84
- array(
85
- 'type' => 'setting',
86
- 'id' => 'test_mode',
87
- 'title' => __( 'Test mode', 'woocommerce-pdf-invoices-packing-slips' ),
88
- 'callback' => 'checkbox',
89
- 'section' => 'general_settings',
90
- 'args' => array(
91
- 'option_name' => $option_name,
92
- 'id' => 'test_mode',
93
- 'description' => __( 'With test mode enabled, any document generated will always use the latest settings, rather than using the settings as configured at the time the document was first created.' , 'woocommerce-pdf-invoices-packing-slips' ) . '<br>'. __( '<strong>Note:</strong> invoice numbers and dates are not affected by this setting and will still be generated.' , 'woocommerce-pdf-invoices-packing-slips' ),
94
- )
95
- ),
96
- array(
97
- 'type' => 'setting',
98
- 'id' => 'currency_font',
99
- 'title' => __( 'Extended currency symbol support', 'woocommerce-pdf-invoices-packing-slips' ),
100
- 'callback' => 'checkbox',
101
- 'section' => 'general_settings',
102
- 'args' => array(
103
- 'option_name' => $option_name,
104
- 'id' => 'currency_font',
105
- 'description' => __( 'Enable this if your currency symbol is not displaying properly' , 'woocommerce-pdf-invoices-packing-slips' ),
106
- )
107
- ),
108
- array(
109
- 'type' => 'setting',
110
- 'id' => 'font_subsetting',
111
- 'title' => __( 'Enable font subsetting', 'woocommerce-pdf-invoices-packing-slips' ),
112
- 'callback' => 'checkbox',
113
- 'section' => 'general_settings',
114
- 'args' => array(
115
- 'option_name' => $option_name,
116
- 'id' => 'font_subsetting',
117
- 'description' => __( "Font subsetting can reduce file size by only including the characters that are used in the PDF, but limits the ability to edit PDF files later. Recommended if you're using an Asian font." , 'woocommerce-pdf-invoices-packing-slips' ),
118
- )
119
- ),
120
- array(
121
- 'type' => 'setting',
122
- 'id' => 'header_logo',
123
- 'title' => __( 'Shop header/logo', 'woocommerce-pdf-invoices-packing-slips' ),
124
- 'callback' => 'media_upload',
125
- 'section' => 'general_settings',
126
- 'args' => array(
127
- 'option_name' => $option_name,
128
- 'id' => 'header_logo',
129
- 'uploader_title' => __( 'Select or upload your invoice header/logo', 'woocommerce-pdf-invoices-packing-slips' ),
130
- 'uploader_button_text' => __( 'Set image', 'woocommerce-pdf-invoices-packing-slips' ),
131
- 'remove_button_text' => __( 'Remove image', 'woocommerce-pdf-invoices-packing-slips' ),
132
- //'description' => __( '...', 'woocommerce-pdf-invoices-packing-slips' ),
133
- )
134
- ),
135
- array(
136
- 'type' => 'setting',
137
- 'id' => 'shop_name',
138
- 'title' => __( 'Shop Name', 'woocommerce-pdf-invoices-packing-slips' ),
139
- 'callback' => 'text_input',
140
- 'section' => 'general_settings',
141
- 'args' => array(
142
- 'option_name' => $option_name,
143
- 'id' => 'shop_name',
144
- 'size' => '72',
145
- 'translatable' => true,
146
- )
147
- ),
148
- array(
149
- 'type' => 'setting',
150
- 'id' => 'shop_address',
151
- 'title' => __( 'Shop Address', 'woocommerce-pdf-invoices-packing-slips' ),
152
- 'callback' => 'textarea',
153
- 'section' => 'general_settings',
154
- 'args' => array(
155
- 'option_name' => $option_name,
156
- 'id' => 'shop_address',
157
- 'width' => '72',
158
- 'height' => '8',
159
- 'translatable' => true,
160
- //'description' => __( '...', 'woocommerce-pdf-invoices-packing-slips' ),
161
- )
162
- ),
163
- array(
164
- 'type' => 'setting',
165
- 'id' => 'footer',
166
- 'title' => __( 'Footer: terms & conditions, policies, etc.', 'woocommerce-pdf-invoices-packing-slips' ),
167
- 'callback' => 'textarea',
168
- 'section' => 'general_settings',
169
- 'args' => array(
170
- 'option_name' => $option_name,
171
- 'id' => 'footer',
172
- 'width' => '72',
173
- 'height' => '4',
174
- 'translatable' => true,
175
- //'description' => __( '...', 'woocommerce-pdf-invoices-packing-slips' ),
176
- )
177
- ),
178
- array(
179
- 'type' => 'section',
180
- 'id' => 'extra_template_fields',
181
- 'title' => __( 'Extra template fields', 'woocommerce-pdf-invoices-packing-slips' ),
182
- 'callback' => 'custom_fields_section',
183
- ),
184
- array(
185
- 'type' => 'setting',
186
- 'id' => 'extra_1',
187
- 'title' => __( 'Extra field 1', 'woocommerce-pdf-invoices-packing-slips' ),
188
- 'callback' => 'textarea',
189
- 'section' => 'extra_template_fields',
190
- 'args' => array(
191
- 'option_name' => $option_name,
192
- 'id' => 'extra_1',
193
- 'width' => '72',
194
- 'height' => '8',
195
- 'description' => __( 'This is footer column 1 in the <i>Modern (Premium)</i> template', 'woocommerce-pdf-invoices-packing-slips' ),
196
- 'translatable' => true,
197
- )
198
- ),
199
- array(
200
- 'type' => 'setting',
201
- 'id' => 'extra_2',
202
- 'title' => __( 'Extra field 2', 'woocommerce-pdf-invoices-packing-slips' ),
203
- 'callback' => 'textarea',
204
- 'section' => 'extra_template_fields',
205
- 'args' => array(
206
- 'option_name' => $option_name,
207
- 'id' => 'extra_2',
208
- 'width' => '72',
209
- 'height' => '8',
210
- 'description' => __( 'This is footer column 2 in the <i>Modern (Premium)</i> template', 'woocommerce-pdf-invoices-packing-slips' ),
211
- 'translatable' => true,
212
- )
213
- ),
214
- array(
215
- 'type' => 'setting',
216
- 'id' => 'extra_3',
217
- 'title' => __( 'Extra field 3', 'woocommerce-pdf-invoices-packing-slips' ),
218
- 'callback' => 'textarea',
219
- 'section' => 'extra_template_fields',
220
- 'args' => array(
221
- 'option_name' => $option_name,
222
- 'id' => 'extra_3',
223
- 'width' => '72',
224
- 'height' => '8',
225
- 'description' => __( 'This is footer column 3 in the <i>Modern (Premium)</i> template', 'woocommerce-pdf-invoices-packing-slips' ),
226
- 'translatable' => true,
227
- )
228
- ),
229
- );
230
-
231
- // allow plugins to alter settings fields
232
- $settings_fields = apply_filters( 'wpo_wcpdf_settings_fields_general', $settings_fields, $page, $option_group, $option_name );
233
- WPO_WCPDF()->settings->add_settings_fields( $settings_fields, $page, $option_group, $option_name );
234
- return;
235
- }
236
-
237
- public function attachment_settings_hint( $active_tab, $active_section ) {
238
- // save or check option to hide attachments settings hint
239
- if ( isset( $_GET['wpo_wcpdf_hide_attachments_hint'] ) ) {
240
- update_option( 'wpo_wcpdf_hide_attachments_hint', true );
241
- $hide_hint = true;
242
- } else {
243
- $hide_hint = get_option( 'wpo_wcpdf_hide_attachments_hint' );
244
- }
245
-
246
- if ( $active_tab == 'general' && !$hide_hint ) {
247
- $documents = WPO_WCPDF()->documents->get_documents();
248
-
249
- foreach ($documents as $document) {
250
- if ( $document->get_type() == 'invoice' ) {
251
- $invoice_email_ids = $document->get_attach_to_email_ids();
252
- if (empty($invoice_email_ids)) {
253
- include_once( WPO_WCPDF()->plugin_path() . '/includes/views/attachment-settings-hint.php' );
254
- }
255
- }
256
- }
257
- }
258
- }
259
-
260
- /**
261
- * List templates in plugin folder, theme folder & child theme folder
262
- * @return array template path => template name
263
- */
264
- public function find_templates() {
265
- $installed_templates = array();
266
-
267
- // get base paths
268
- $template_base_path = ( defined( 'WC_TEMPLATE_PATH' ) ? WC_TEMPLATE_PATH : $GLOBALS['woocommerce']->template_url );
269
- $template_base_path = untrailingslashit( $template_base_path );
270
- $template_paths = array (
271
- // note the order: child-theme before theme, so that array_unique filters out parent doubles
272
- 'default' => WPO_WCPDF()->plugin_path() . '/templates/',
273
- 'child-theme' => get_stylesheet_directory() . "/{$template_base_path}/pdf/",
274
- 'theme' => get_template_directory() . "/{$template_base_path}/pdf/",
275
- );
276
-
277
- $template_paths = apply_filters( 'wpo_wcpdf_template_paths', $template_paths );
278
-
279
- if ( defined('WP_CONTENT_DIR') && strpos( WP_CONTENT_DIR, ABSPATH ) !== false ) {
280
- $forwardslash_basepath = str_replace('\\','/', ABSPATH);
281
- } else {
282
- $forwardslash_basepath = str_replace('\\','/', WP_CONTENT_DIR);
283
- }
284
-
285
- foreach ($template_paths as $template_source => $template_path) {
286
- $dirs = (array) glob( $template_path . '*' , GLOB_ONLYDIR);
287
-
288
- foreach ($dirs as $dir) {
289
- // we're stripping abspath to make the plugin settings more portable
290
- $forwardslash_dir = str_replace('\\','/', $dir);
291
- $installed_templates[ str_replace( $forwardslash_basepath, '', $forwardslash_dir ) ] = basename($dir);
292
- }
293
- }
294
-
295
- // remove parent doubles
296
- $installed_templates = array_unique($installed_templates);
297
-
298
- if (empty($installed_templates)) {
299
- // fallback to Simple template for servers with glob() disabled
300
- $simple_template_path = str_replace( ABSPATH, '', $template_paths['default'] . 'Simple' );
301
- $installed_templates[$simple_template_path] = 'Simple';
302
- }
303
-
304
- return apply_filters( 'wpo_wcpdf_templates', $installed_templates );
305
- }
306
-
307
- }
308
-
309
- endif; // class_exists
310
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
311
  return new Settings_General();
1
+ <?php
2
+ namespace WPO\WC\PDF_Invoices;
3
+
4
+ if ( ! defined( 'ABSPATH' ) ) {
5
+ exit; // Exit if accessed directly
6
+ }
7
+
8
+ if ( !class_exists( '\\WPO\\WC\\PDF_Invoices\\Settings_General' ) ) :
9
+
10
+ class Settings_General {
11
+
12
+ protected $option_name = 'wpo_wcpdf_settings_general';
13
+
14
+ function __construct() {
15
+ add_action( 'admin_init', array( $this, 'init_settings' ) );
16
+ add_action( 'wpo_wcpdf_settings_output_general', array( $this, 'output' ), 10, 1 );
17
+ add_action( 'wpo_wcpdf_before_settings', array( $this, 'attachment_settings_hint' ), 10, 2 );
18
+ }
19
+
20
+ public function output( $section ) {
21
+ settings_fields( $this->option_name );
22
+ do_settings_sections( $this->option_name );
23
+
24
+ submit_button();
25
+ }
26
+
27
+ public function init_settings() {
28
+ $page = $option_group = $option_name = $this->option_name;
29
+
30
+ $template_base_path = ( defined( 'WC_TEMPLATE_PATH' ) ? WC_TEMPLATE_PATH : $GLOBALS['woocommerce']->template_url );
31
+ $theme_template_path = get_stylesheet_directory() . '/' . $template_base_path;
32
+ $wp_content_dir = str_replace( ABSPATH, '', WP_CONTENT_DIR );
33
+ $theme_template_path = substr($theme_template_path, strpos($theme_template_path, $wp_content_dir)) . 'pdf/yourtemplate';
34
+ $plugin_template_path = "{$wp_content_dir}/plugins/woocommerce-pdf-invoices-packing-slips/templates/Simple";
35
+
36
+ $settings_fields = array(
37
+ array(
38
+ 'type' => 'section',
39
+ 'id' => 'general_settings',
40
+ 'title' => __( 'General settings', 'woocommerce-pdf-invoices-packing-slips' ),
41
+ 'callback' => 'section',
42
+ ),
43
+ array(
44
+ 'type' => 'setting',
45
+ 'id' => 'download_display',
46
+ 'title' => __( 'How do you want to view the PDF?', 'woocommerce-pdf-invoices-packing-slips' ),
47
+ 'callback' => 'select',
48
+ 'section' => 'general_settings',
49
+ 'args' => array(
50
+ 'option_name' => $option_name,
51
+ 'id' => 'download_display',
52
+ 'options' => array(
53
+ 'download' => __( 'Download the PDF' , 'woocommerce-pdf-invoices-packing-slips' ),
54
+ 'display' => __( 'Open the PDF in a new browser tab/window' , 'woocommerce-pdf-invoices-packing-slips' ),
55
+ ),
56
+ )
57
+ ),
58
+ array(
59
+ 'type' => 'setting',
60
+ 'id' => 'template_path',
61
+ 'title' => __( 'Choose a template', 'woocommerce-pdf-invoices-packing-slips' ),
62
+ 'callback' => 'select',
63
+ 'section' => 'general_settings',
64
+ 'args' => array(
65
+ 'option_name' => $option_name,
66
+ 'id' => 'template_path',
67
+ 'options' => $this->find_templates(),
68
+ 'description' => sprintf( __( 'Want to use your own template? Copy all the files from <code>%s</code> to your (child) theme in <code>%s</code> to customize them' , 'woocommerce-pdf-invoices-packing-slips' ), $plugin_template_path, $theme_template_path),
69
+ )
70
+ ),
71
+ array(
72
+ 'type' => 'setting',
73
+ 'id' => 'paper_size',
74
+ 'title' => __( 'Paper size', 'woocommerce-pdf-invoices-packing-slips' ),
75
+ 'callback' => 'select',
76
+ 'section' => 'general_settings',
77
+ 'args' => array(
78
+ 'option_name' => $option_name,
79
+ 'id' => 'paper_size',
80
+ 'options' => apply_filters( 'wpo_wcpdf_template_settings_paper_size', array(
81
+ 'a4' => __( 'A4' , 'woocommerce-pdf-invoices-packing-slips' ),
82
+ 'letter' => __( 'Letter' , 'woocommerce-pdf-invoices-packing-slips' ),
83
+ ) ),
84
+ )
85
+ ),
86
+ array(
87
+ 'type' => 'setting',
88
+ 'id' => 'test_mode',
89
+ 'title' => __( 'Test mode', 'woocommerce-pdf-invoices-packing-slips' ),
90
+ 'callback' => 'checkbox',
91
+ 'section' => 'general_settings',
92
+ 'args' => array(
93
+ 'option_name' => $option_name,
94
+ 'id' => 'test_mode',
95
+ 'description' => __( 'With test mode enabled, any document generated will always use the latest settings, rather than using the settings as configured at the time the document was first created.' , 'woocommerce-pdf-invoices-packing-slips' ) . '<br>'. __( '<strong>Note:</strong> invoice numbers and dates are not affected by this setting and will still be generated.' , 'woocommerce-pdf-invoices-packing-slips' ),
96
+ )
97
+ ),
98
+ array(
99
+ 'type' => 'setting',
100
+ 'id' => 'currency_font',
101
+ 'title' => __( 'Extended currency symbol support', 'woocommerce-pdf-invoices-packing-slips' ),
102
+ 'callback' => 'checkbox',
103
+ 'section' => 'general_settings',
104
+ 'args' => array(
105
+ 'option_name' => $option_name,
106
+ 'id' => 'currency_font',
107
+ 'description' => __( 'Enable this if your currency symbol is not displaying properly' , 'woocommerce-pdf-invoices-packing-slips' ),
108
+ )
109
+ ),
110
+ array(
111
+ 'type' => 'setting',
112
+ 'id' => 'font_subsetting',
113
+ 'title' => __( 'Enable font subsetting', 'woocommerce-pdf-invoices-packing-slips' ),
114
+ 'callback' => 'checkbox',
115
+ 'section' => 'general_settings',
116
+ 'args' => array(
117
+ 'option_name' => $option_name,
118
+ 'id' => 'font_subsetting',
119
+ 'description' => __( "Font subsetting can reduce file size by only including the characters that are used in the PDF, but limits the ability to edit PDF files later. Recommended if you're using an Asian font." , 'woocommerce-pdf-invoices-packing-slips' ),
120
+ )
121
+ ),
122
+ array(
123
+ 'type' => 'setting',
124
+ 'id' => 'header_logo',
125
+ 'title' => __( 'Shop header/logo', 'woocommerce-pdf-invoices-packing-slips' ),
126
+ 'callback' => 'media_upload',
127
+ 'section' => 'general_settings',
128
+ 'args' => array(
129
+ 'option_name' => $option_name,
130
+ 'id' => 'header_logo',
131
+ 'uploader_title' => __( 'Select or upload your invoice header/logo', 'woocommerce-pdf-invoices-packing-slips' ),
132
+ 'uploader_button_text' => __( 'Set image', 'woocommerce-pdf-invoices-packing-slips' ),
133
+ 'remove_button_text' => __( 'Remove image', 'woocommerce-pdf-invoices-packing-slips' ),
134
+ //'description' => __( '...', 'woocommerce-pdf-invoices-packing-slips' ),
135
+ )
136
+ ),
137
+ array(
138
+ 'type' => 'setting',
139
+ 'id' => 'header_logo_height',
140
+ 'title' => __( 'Logo height', 'woocommerce-pdf-invoices-packing-slips' ),
141
+ 'callback' => 'text_input',
142
+ 'section' => 'general_settings',
143
+ 'args' => array(
144
+ 'option_name' => $option_name,
145
+ 'id' => 'header_logo_height',
146
+ 'size' => '5',
147
+ 'placeholder' => '3cm',
148
+ 'description' => __( 'Enter the total height of the logo in mm, cm or in and use a dot for decimals.<br/>For example: 1.15in or 40mm', 'woocommerce-pdf-invoices-packing-slips' ),
149
+ )
150
+ ),
151
+ array(
152
+ 'type' => 'setting',
153
+ 'id' => 'shop_name',
154
+ 'title' => __( 'Shop Name', 'woocommerce-pdf-invoices-packing-slips' ),
155
+ 'callback' => 'text_input',
156
+ 'section' => 'general_settings',
157
+ 'args' => array(
158
+ 'option_name' => $option_name,
159
+ 'id' => 'shop_name',
160
+ 'size' => '72',
161
+ 'translatable' => true,
162
+ )
163
+ ),
164
+ array(
165
+ 'type' => 'setting',
166
+ 'id' => 'shop_address',
167
+ 'title' => __( 'Shop Address', 'woocommerce-pdf-invoices-packing-slips' ),
168
+ 'callback' => 'textarea',
169
+ 'section' => 'general_settings',
170
+ 'args' => array(
171
+ 'option_name' => $option_name,
172
+ 'id' => 'shop_address',
173
+ 'width' => '72',
174
+ 'height' => '8',
175
+ 'translatable' => true,
176
+ //'description' => __( '...', 'woocommerce-pdf-invoices-packing-slips' ),
177
+ )
178
+ ),
179
+ array(
180
+ 'type' => 'setting',
181
+ 'id' => 'footer',
182
+ 'title' => __( 'Footer: terms & conditions, policies, etc.', 'woocommerce-pdf-invoices-packing-slips' ),
183
+ 'callback' => 'textarea',
184
+ 'section' => 'general_settings',
185
+ 'args' => array(
186
+ 'option_name' => $option_name,
187
+ 'id' => 'footer',
188
+ 'width' => '72',
189
+ 'height' => '4',
190
+ 'translatable' => true,
191
+ //'description' => __( '...', 'woocommerce-pdf-invoices-packing-slips' ),
192
+ )
193
+ ),
194
+ array(
195
+ 'type' => 'section',
196
+ 'id' => 'extra_template_fields',
197
+ 'title' => __( 'Extra template fields', 'woocommerce-pdf-invoices-packing-slips' ),
198
+ 'callback' => 'custom_fields_section',
199
+ ),
200
+ array(
201
+ 'type' => 'setting',
202
+ 'id' => 'extra_1',
203
+ 'title' => __( 'Extra field 1', 'woocommerce-pdf-invoices-packing-slips' ),
204
+ 'callback' => 'textarea',
205
+ 'section' => 'extra_template_fields',
206
+ 'args' => array(
207
+ 'option_name' => $option_name,
208
+ 'id' => 'extra_1',
209
+ 'width' => '72',
210
+ 'height' => '8',
211
+ 'description' => __( 'This is footer column 1 in the <i>Modern (Premium)</i> template', 'woocommerce-pdf-invoices-packing-slips' ),
212
+ 'translatable' => true,
213
+ )
214
+ ),
215
+ array(
216
+ 'type' => 'setting',
217
+ 'id' => 'extra_2',
218
+ 'title' => __( 'Extra field 2', 'woocommerce-pdf-invoices-packing-slips' ),
219
+ 'callback' => 'textarea',
220
+ 'section' => 'extra_template_fields',
221
+ 'args' => array(
222
+ 'option_name' => $option_name,
223
+ 'id' => 'extra_2',
224
+ 'width' => '72',
225
+ 'height' => '8',
226
+ 'description' => __( 'This is footer column 2 in the <i>Modern (Premium)</i> template', 'woocommerce-pdf-invoices-packing-slips' ),
227
+ 'translatable' => true,
228
+ )
229
+ ),
230
+ array(
231
+ 'type' => 'setting',
232
+ 'id' => 'extra_3',
233
+ 'title' => __( 'Extra field 3', 'woocommerce-pdf-invoices-packing-slips' ),
234
+ 'callback' => 'textarea',
235
+ 'section' => 'extra_template_fields',
236
+ 'args' => array(
237
+ 'option_name' => $option_name,
238
+ 'id' => 'extra_3',
239
+ 'width' => '72',
240
+ 'height' => '8',
241
+ 'description' => __( 'This is footer column 3 in the <i>Modern (Premium)</i> template', 'woocommerce-pdf-invoices-packing-slips' ),
242
+ 'translatable' => true,
243
+ )
244
+ ),
245
+ );
246
+
247
+ // allow plugins to alter settings fields
248
+ $settings_fields = apply_filters( 'wpo_wcpdf_settings_fields_general', $settings_fields, $page, $option_group, $option_name );
249
+ WPO_WCPDF()->settings->add_settings_fields( $settings_fields, $page, $option_group, $option_name );
250
+ return;
251
+ }
252
+
253
+ public function attachment_settings_hint( $active_tab, $active_section ) {
254
+ // save or check option to hide attachments settings hint
255
+ if ( isset( $_GET['wpo_wcpdf_hide_attachments_hint'] ) ) {
256
+ update_option( 'wpo_wcpdf_hide_attachments_hint', true );
257
+ $hide_hint = true;
258
+ } else {
259
+ $hide_hint = get_option( 'wpo_wcpdf_hide_attachments_hint' );
260
+ }
261
+
262
+ if ( $active_tab == 'general' && !$hide_hint ) {
263
+ $documents = WPO_WCPDF()->documents->get_documents();
264
+
265
+ foreach ($documents as $document) {
266
+ if ( $document->get_type() == 'invoice' ) {
267
+ $invoice_email_ids = $document->get_attach_to_email_ids();
268
+ if (empty($invoice_email_ids)) {
269
+ include_once( WPO_WCPDF()->plugin_path() . '/includes/views/attachment-settings-hint.php' );
270
+ }
271
+ }
272
+ }
273
+ }
274
+ }
275
+
276
+ /**
277
+ * List templates in plugin folder, theme folder & child theme folder
278
+ * @return array template path => template name
279
+ */
280
+ public function find_templates() {
281
+ $installed_templates = array();
282
+
283
+ // get base paths
284
+ $template_base_path = ( defined( 'WC_TEMPLATE_PATH' ) ? WC_TEMPLATE_PATH : $GLOBALS['woocommerce']->template_url );
285
+ $template_base_path = untrailingslashit( $template_base_path );
286
+ $template_paths = array (
287
+ // note the order: child-theme before theme, so that array_unique filters out parent doubles
288
+ 'default' => WPO_WCPDF()->plugin_path() . '/templates/',
289
+ 'child-theme' => get_stylesheet_directory() . "/{$template_base_path}/pdf/",
290
+ 'theme' => get_template_directory() . "/{$template_base_path}/pdf/",
291
+ );
292
+
293
+ $template_paths = apply_filters( 'wpo_wcpdf_template_paths', $template_paths );
294
+
295
+ if ( defined('WP_CONTENT_DIR') && strpos( WP_CONTENT_DIR, ABSPATH ) !== false ) {
296
+ $forwardslash_basepath = str_replace('\\','/', ABSPATH);
297
+ } else {
298
+ $forwardslash_basepath = str_replace('\\','/', WP_CONTENT_DIR);
299
+ }
300
+
301
+ foreach ($template_paths as $template_source => $template_path) {
302
+ $dirs = (array) glob( $template_path . '*' , GLOB_ONLYDIR);
303
+
304
+ foreach ($dirs as $dir) {
305
+ // we're stripping abspath to make the plugin settings more portable
306
+ $forwardslash_dir = str_replace('\\','/', $dir);
307
+ $installed_templates[ str_replace( $forwardslash_basepath, '', $forwardslash_dir ) ] = basename($dir);
308
+ }
309
+ }
310
+
311
+ // remove parent doubles
312
+ $installed_templates = array_unique($installed_templates);
313
+
314
+ if (empty($installed_templates)) {
315
+ // fallback to Simple template for servers with glob() disabled
316
+ $simple_template_path = str_replace( ABSPATH, '', $template_paths['default'] . 'Simple' );
317
+ $installed_templates[$simple_template_path] = 'Simple';
318
+ }
319
+
320
+ return apply_filters( 'wpo_wcpdf_templates', $installed_templates );
321
+ }
322
+
323
+ }
324
+
325
+ endif; // class_exists
326
+
327
  return new Settings_General();
includes/class-wcpdf-settings.php CHANGED
@@ -1,260 +1,261 @@
1
- <?php
2
- namespace WPO\WC\PDF_Invoices;
3
-
4
- use WPO\WC\PDF_Invoices\Documents\Sequential_Number_Store;
5
-
6
- if ( ! defined( 'ABSPATH' ) ) {
7
- exit; // Exit if accessed directly
8
- }
9
-
10
- if ( !class_exists( '\\WPO\\WC\\PDF_Invoices\\Settings' ) ) :
11
-
12
- class Settings {
13
- public $options_page_hook;
14
-
15
- function __construct() {
16
- $this->callbacks = include( 'class-wcpdf-settings-callbacks.php' );
17
-
18
- // include settings classes
19
- $this->general = include( 'class-wcpdf-settings-general.php' );
20
- $this->documents = include( 'class-wcpdf-settings-documents.php' );
21
- $this->debug = include( 'class-wcpdf-settings-debug.php' );
22
-
23
-
24
- // Settings menu item
25
- add_action( 'admin_menu', array( $this, 'menu' ), 999 ); // Add menu
26
- // Links on plugin page
27
- add_filter( 'plugin_action_links_'.WPO_WCPDF()->plugin_basename, array( $this, 'add_settings_link' ) );
28
- add_filter( 'plugin_row_meta', array( $this, 'add_support_links' ), 10, 2 );
29
-
30
- // settings capabilities
31
- add_filter( 'option_page_capability_wpo_wcpdf_general_settings', array( $this, 'settings_capabilities' ) );
32
-
33
- $this->general_settings = get_option('wpo_wcpdf_settings_general');
34
- $this->debug_settings = get_option('wpo_wcpdf_settings_debug');
35
-
36
- // admin notice for auto_increment_increment
37
- // add_action( 'admin_notices', array( $this, 'check_auto_increment_increment') );
38
-
39
- // AJAX set number store
40
- add_action( 'wp_ajax_wpo_wcpdf_set_next_number', array($this, 'set_number_store' ));
41
- }
42
-
43
- public function menu() {
44
- $parent_slug = 'woocommerce';
45
-
46
- $this->options_page_hook = add_submenu_page(
47
- $parent_slug,
48
- __( 'PDF Invoices', 'woocommerce-pdf-invoices-packing-slips' ),
49
- __( 'PDF Invoices', 'woocommerce-pdf-invoices-packing-slips' ),
50
- 'manage_woocommerce',
51
- 'wpo_wcpdf_options_page',
52
- array( $this, 'settings_page' )
53
- );
54
- }
55
-
56
- /**
57
- * Add settings link to plugins page
58
- */
59
- public function add_settings_link( $links ) {
60
- $action_links = array(
61
- 'settings' => '<a href="admin.php?page=wpo_wcpdf_options_page">'. __( 'Settings', 'woocommerce' ) . '</a>',
62
- );
63
-
64
- return array_merge( $action_links, $links );
65
- }
66
-
67
- /**
68
- * Add various support links to plugin page
69
- * after meta (version, authors, site)
70
- */
71
- public function add_support_links( $links, $file ) {
72
- if ( $file == WPO_WCPDF()->plugin_basename ) {
73
- $row_meta = array(
74
- 'docs' => '<a href="http://docs.wpovernight.com/woocommerce-pdf-invoices-packing-slips/" target="_blank" title="' . __( 'Documentation', 'woocommerce-pdf-invoices-packing-slips' ) . '">' . __( 'Documentation', 'woocommerce-pdf-invoices-packing-slips' ) . '</a>',
75
- 'support' => '<a href="https://wordpress.org/support/plugin/woocommerce-pdf-invoices-packing-slips" target="_blank" title="' . __( 'Support Forum', 'woocommerce-pdf-invoices-packing-slips' ) . '">' . __( 'Support Forum', 'woocommerce-pdf-invoices-packing-slips' ) . '</a>',
76
- );
77
-
78
- return array_merge( $links, $row_meta );
79
- }
80
- return (array) $links;
81
- }
82
-
83
- function check_auto_increment_increment() {
84
- global $wpdb;
85
- $row = $wpdb->get_row("SHOW VARIABLES LIKE 'auto_increment_increment'");
86
- if ( !empty($row) && !empty($row->Value) && $row->Value != 1 ) {
87
- $error = sprintf( __( "<strong>Warning!</strong> Your database has an AUTO_INCREMENT step size of %s, your invoice numbers may not be sequential. Enable the 'Calculate document numbers (slow)' setting in the Status tab to use an alternate method." , 'woocommerce-pdf-invoices-packing-slips' ), $row->Value );
88
- printf( '<div class="error"><p>%s</p></div>', $error );
89
- }
90
- }
91
-
92
-
93
- public function settings_page() {
94
- $settings_tabs = apply_filters( 'wpo_wcpdf_settings_tabs', array (
95
- 'general' => __('General', 'woocommerce-pdf-invoices-packing-slips' ),
96
- 'documents' => __('Documents', 'woocommerce-pdf-invoices-packing-slips' ),
97
- )
98
- );
99
-
100
- // add status tab last in row
101
- $settings_tabs['debug'] = __('Status', 'woocommerce-pdf-invoices-packing-slips' );
102
-
103
- $active_tab = isset( $_GET[ 'tab' ] ) ? sanitize_text_field( $_GET[ 'tab' ] ) : 'general';
104
- $active_section = isset( $_GET[ 'section' ] ) ? sanitize_text_field( $_GET[ 'section' ] ) : '';
105
-
106
- include('views/wcpdf-settings-page.php');
107
- }
108
-
109
- public function add_settings_fields( $settings_fields, $page, $option_group, $option_name ) {
110
- foreach ( $settings_fields as $settings_field ) {
111
- if (!isset($settings_field['callback'])) {
112
- continue;
113
- } elseif ( is_callable( array( $this->callbacks, $settings_field['callback'] ) ) ) {
114
- $callback = array( $this->callbacks, $settings_field['callback'] );
115
- } elseif ( is_callable( $settings_field['callback'] ) ) {
116
- $callback = $settings_field['callback'];
117
- } else {
118
- continue;
119
- }
120
-
121
- if ( $settings_field['type'] == 'section' ) {
122
- add_settings_section(
123
- $settings_field['id'],
124
- $settings_field['title'],
125
- $callback,
126
- $page
127
- );
128
- } else {
129
- add_settings_field(
130
- $settings_field['id'],
131
- $settings_field['title'],
132
- $callback,
133
- $page,
134
- $settings_field['section'],
135
- $settings_field['args']
136
- );
137
- // register option separately for singular options
138
- if (is_string($settings_field['callback']) && $settings_field['callback'] == 'singular_text_element') {
139
- register_setting( $option_group, $settings_field['args']['option_name'], array( $this->callbacks, 'validate' ) );
140
- }
141
- }
142
- }
143
- // $page, $option_group & $option_name are all the same...
144
- register_setting( $option_group, $option_name, array( $this->callbacks, 'validate' ) );
145
- add_filter( 'option_page_capability_'.$page, array( $this, 'settings_capabilities' ) );
146
-
147
- }
148
-
149
- /**
150
- * Set capability for settings page
151
- */
152
- public function settings_capabilities() {
153
- return 'manage_woocommerce';
154
- }
155
-
156
- public function get_common_document_settings() {
157
- $common_settings = array(
158
- 'paper_size' => isset( $this->general_settings['paper_size'] ) ? $this->general_settings['paper_size'] : '',
159
- 'font_subsetting' => isset( $this->general_settings['font_subsetting'] ) || ( defined("DOMPDF_ENABLE_FONTSUBSETTING") && DOMPDF_ENABLE_FONTSUBSETTING === true ) ? true : false,
160
- 'header_logo' => isset( $this->general_settings['header_logo'] ) ? $this->general_settings['header_logo'] : '',
161
- 'shop_name' => isset( $this->general_settings['shop_name'] ) ? $this->general_settings['shop_name'] : '',
162
- 'shop_address' => isset( $this->general_settings['shop_address'] ) ? $this->general_settings['shop_address'] : '',
163
- 'footer' => isset( $this->general_settings['footer'] ) ? $this->general_settings['footer'] : '',
164
- 'extra_1' => isset( $this->general_settings['extra_1'] ) ? $this->general_settings['extra_1'] : '',
165
- 'extra_2' => isset( $this->general_settings['extra_2'] ) ? $this->general_settings['extra_2'] : '',
166
- 'extra_3' => isset( $this->general_settings['extra_3'] ) ? $this->general_settings['extra_3'] : '',
167
- );
168
- return $common_settings;
169
- }
170
-
171
- public function get_document_settings( $document_type ) {
172
- $documents = WPO_WCPDF()->documents->get_documents('all');
173
- foreach ($documents as $document) {
174
- if ( $document->get_type() == $document_type ) {
175
- return $document->settings;
176
- }
177
- }
178
- return false;
179
- }
180
-
181
- public function get_output_format( $document_type = null ) {
182
- if ( isset( $this->debug_settings['html_output'] ) ) {
183
- $output_format = 'html';
184
- } else {
185
- $output_format = 'pdf';
186
- }
187
- return apply_filters( 'wpo_wcpdf_output_format', $output_format, $document_type );
188
- }
189
-
190
- public function get_output_mode() {
191
- if ( isset( WPO_WCPDF()->settings->general_settings['download_display'] ) ) {
192
- switch ( WPO_WCPDF()->settings->general_settings['download_display'] ) {
193
- case 'display':
194
- $output_mode = 'inline';
195
- break;
196
- case 'download':
197
- default:
198
- $output_mode = 'download';
199
- break;
200
- }
201
- } else {
202
- $output_mode = 'download';
203
- }
204
- return $output_mode;
205
- }
206
-
207
- public function get_template_path( $document_type = NULL ) {
208
- $template_path = isset( $this->general_settings['template_path'] )?$this->general_settings['template_path']:'';
209
- // forward slash for consistency
210
- $template_path = str_replace('\\','/', $template_path);
211
-
212
- // add base path, checking if it's not already there
213
- // alternative setups like Bedrock have WP_CONTENT_DIR & ABSPATH separated
214
- if ( defined('WP_CONTENT_DIR') && strpos( WP_CONTENT_DIR, ABSPATH ) !== false ) {
215
- $forwardslash_basepath = str_replace('\\','/', ABSPATH);
216
- } else {
217
- // bedrock e.a
218
- $forwardslash_basepath = str_replace('\\','/', WP_CONTENT_DIR);
219
- }
220
-
221
- if ( strpos( $template_path, $forwardslash_basepath ) === false ) {
222
- $template_path = $forwardslash_basepath . $template_path;
223
- }
224
-
225
- return $template_path;
226
- }
227
-
228
- public function set_number_store() {
229
- check_ajax_referer( "wpo_wcpdf_next_{$_POST['store']}", 'security' );
230
- // check permissions
231
- if ( !current_user_can('manage_woocommerce') ) {
232
- die();
233
- }
234
-
235
- $number = isset( $_POST['number'] ) ? (int) $_POST['number'] : 0;
236
- $number_store_method = $this->get_sequential_number_store_method();
237
- $number_store = new Sequential_Number_Store( $_POST['store'], $number_store_method );
238
- $number_store->set_next( $number );
239
- echo "next number ({$_POST['store']}) set to {$number}";
240
- die();
241
- }
242
-
243
- public function get_sequential_number_store_method() {
244
- global $wpdb;
245
- $method = isset( $this->debug_settings['calculate_document_numbers'] ) ? 'calculate' : 'auto_increment';
246
-
247
- // safety first - always use calculate when auto_increment_increment is not 1
248
- $row = $wpdb->get_row("SHOW VARIABLES LIKE 'auto_increment_increment'");
249
- if ( !empty($row) && !empty($row->Value) && $row->Value != 1 ) {
250
- $method = 'calculate';
251
- }
252
-
253
- return $method;
254
- }
255
-
256
- }
257
-
258
- endif; // class_exists
259
-
 
260
  return new Settings();
1
+ <?php
2
+ namespace WPO\WC\PDF_Invoices;
3
+
4
+ use WPO\WC\PDF_Invoices\Documents\Sequential_Number_Store;
5
+
6
+ if ( ! defined( 'ABSPATH' ) ) {
7
+ exit; // Exit if accessed directly
8
+ }
9
+
10
+ if ( !class_exists( '\\WPO\\WC\\PDF_Invoices\\Settings' ) ) :
11
+
12
+ class Settings {
13
+ public $options_page_hook;
14
+
15
+ function __construct() {
16
+ $this->callbacks = include( 'class-wcpdf-settings-callbacks.php' );
17
+
18
+ // include settings classes
19
+ $this->general = include( 'class-wcpdf-settings-general.php' );
20
+ $this->documents = include( 'class-wcpdf-settings-documents.php' );
21
+ $this->debug = include( 'class-wcpdf-settings-debug.php' );
22
+
23
+
24
+ // Settings menu item
25
+ add_action( 'admin_menu', array( $this, 'menu' ), 999 ); // Add menu
26
+ // Links on plugin page
27
+ add_filter( 'plugin_action_links_'.WPO_WCPDF()->plugin_basename, array( $this, 'add_settings_link' ) );
28
+ add_filter( 'plugin_row_meta', array( $this, 'add_support_links' ), 10, 2 );
29
+
30
+ // settings capabilities
31
+ add_filter( 'option_page_capability_wpo_wcpdf_general_settings', array( $this, 'settings_capabilities' ) );
32
+
33
+ $this->general_settings = get_option('wpo_wcpdf_settings_general');
34
+ $this->debug_settings = get_option('wpo_wcpdf_settings_debug');
35
+
36
+ // admin notice for auto_increment_increment
37
+ // add_action( 'admin_notices', array( $this, 'check_auto_increment_increment') );
38
+
39
+ // AJAX set number store
40
+ add_action( 'wp_ajax_wpo_wcpdf_set_next_number', array($this, 'set_number_store' ));
41
+ }
42
+
43
+ public function menu() {
44
+ $parent_slug = 'woocommerce';
45
+
46
+ $this->options_page_hook = add_submenu_page(
47
+ $parent_slug,
48
+ __( 'PDF Invoices', 'woocommerce-pdf-invoices-packing-slips' ),
49
+ __( 'PDF Invoices', 'woocommerce-pdf-invoices-packing-slips' ),
50
+ 'manage_woocommerce',
51
+ 'wpo_wcpdf_options_page',
52
+ array( $this, 'settings_page' )
53
+ );
54
+ }
55
+
56
+ /**
57
+ * Add settings link to plugins page
58
+ */
59
+ public function add_settings_link( $links ) {
60
+ $action_links = array(
61
+ 'settings' => '<a href="admin.php?page=wpo_wcpdf_options_page">'. __( 'Settings', 'woocommerce' ) . '</a>',
62
+ );
63
+
64
+ return array_merge( $action_links, $links );
65
+ }
66
+
67
+ /**
68
+ * Add various support links to plugin page
69
+ * after meta (version, authors, site)
70
+ */
71
+ public function add_support_links( $links, $file ) {
72
+ if ( $file == WPO_WCPDF()->plugin_basename ) {
73
+ $row_meta = array(
74
+ 'docs' => '<a href="http://docs.wpovernight.com/woocommerce-pdf-invoices-packing-slips/" target="_blank" title="' . __( 'Documentation', 'woocommerce-pdf-invoices-packing-slips' ) . '">' . __( 'Documentation', 'woocommerce-pdf-invoices-packing-slips' ) . '</a>',
75
+ 'support' => '<a href="https://wordpress.org/support/plugin/woocommerce-pdf-invoices-packing-slips" target="_blank" title="' . __( 'Support Forum', 'woocommerce-pdf-invoices-packing-slips' ) . '">' . __( 'Support Forum', 'woocommerce-pdf-invoices-packing-slips' ) . '</a>',
76
+ );
77
+
78
+ return array_merge( $links, $row_meta );
79
+ }
80
+ return (array) $links;
81
+ }
82
+
83
+ function check_auto_increment_increment() {
84
+ global $wpdb;
85
+ $row = $wpdb->get_row("SHOW VARIABLES LIKE 'auto_increment_increment'");
86
+ if ( !empty($row) && !empty($row->Value) && $row->Value != 1 ) {
87
+ $error = sprintf( __( "<strong>Warning!</strong> Your database has an AUTO_INCREMENT step size of %s, your invoice numbers may not be sequential. Enable the 'Calculate document numbers (slow)' setting in the Status tab to use an alternate method." , 'woocommerce-pdf-invoices-packing-slips' ), $row->Value );
88
+ printf( '<div class="error"><p>%s</p></div>', $error );
89
+ }
90
+ }
91
+
92
+
93
+ public function settings_page() {
94
+ $settings_tabs = apply_filters( 'wpo_wcpdf_settings_tabs', array (
95
+ 'general' => __('General', 'woocommerce-pdf-invoices-packing-slips' ),
96
+ 'documents' => __('Documents', 'woocommerce-pdf-invoices-packing-slips' ),
97
+ )
98
+ );
99
+
100
+ // add status tab last in row
101
+ $settings_tabs['debug'] = __('Status', 'woocommerce-pdf-invoices-packing-slips' );
102
+
103
+ $active_tab = isset( $_GET[ 'tab' ] ) ? sanitize_text_field( $_GET[ 'tab' ] ) : 'general';
104
+ $active_section = isset( $_GET[ 'section' ] ) ? sanitize_text_field( $_GET[ 'section' ] ) : '';
105
+
106
+ include('views/wcpdf-settings-page.php');
107
+ }
108
+
109
+ public function add_settings_fields( $settings_fields, $page, $option_group, $option_name ) {
110
+ foreach ( $settings_fields as $settings_field ) {
111
+ if (!isset($settings_field['callback'])) {
112
+ continue;
113
+ } elseif ( is_callable( array( $this->callbacks, $settings_field['callback'] ) ) ) {
114
+ $callback = array( $this->callbacks, $settings_field['callback'] );
115
+ } elseif ( is_callable( $settings_field['callback'] ) ) {
116
+ $callback = $settings_field['callback'];
117
+ } else {
118
+ continue;
119
+ }
120
+
121
+ if ( $settings_field['type'] == 'section' ) {
122
+ add_settings_section(
123
+ $settings_field['id'],
124
+ $settings_field['title'],
125
+ $callback,
126
+ $page
127
+ );
128
+ } else {
129
+ add_settings_field(
130
+ $settings_field['id'],
131
+ $settings_field['title'],
132
+ $callback,
133
+ $page,
134
+ $settings_field['section'],
135
+ $settings_field['args']
136
+ );
137
+ // register option separately for singular options
138
+ if (is_string($settings_field['callback']) && $settings_field['callback'] == 'singular_text_element') {
139
+ register_setting( $option_group, $settings_field['args']['option_name'], array( $this->callbacks, 'validate' ) );
140
+ }
141
+ }
142
+ }
143
+ // $page, $option_group & $option_name are all the same...
144
+ register_setting( $option_group, $option_name, array( $this->callbacks, 'validate' ) );
145
+ add_filter( 'option_page_capability_'.$page, array( $this, 'settings_capabilities' ) );
146
+
147
+ }
148
+
149
+ /**
150
+ * Set capability for settings page
151
+ */
152
+ public function settings_capabilities() {
153
+ return 'manage_woocommerce';
154
+ }
155
+
156
+ public function get_common_document_settings() {
157
+ $common_settings = array(
158
+ 'paper_size' => isset( $this->general_settings['paper_size'] ) ? $this->general_settings['paper_size'] : '',
159
+ 'font_subsetting' => isset( $this->general_settings['font_subsetting'] ) || ( defined("DOMPDF_ENABLE_FONTSUBSETTING") && DOMPDF_ENABLE_FONTSUBSETTING === true ) ? true : false,
160
+ 'header_logo' => isset( $this->general_settings['header_logo'] ) ? $this->general_settings['header_logo'] : '',
161
+ 'header_logo_height' => isset( $this->general_settings['header_logo_height'] ) ? $this->general_settings['header_logo_height'] : '',
162
+ 'shop_name' => isset( $this->general_settings['shop_name'] ) ? $this->general_settings['shop_name'] : '',
163
+ 'shop_address' => isset( $this->general_settings['shop_address'] ) ? $this->general_settings['shop_address'] : '',
164
+ 'footer' => isset( $this->general_settings['footer'] ) ? $this->general_settings['footer'] : '',
165
+ 'extra_1' => isset( $this->general_settings['extra_1'] ) ? $this->general_settings['extra_1'] : '',
166
+ 'extra_2' => isset( $this->general_settings['extra_2'] ) ? $this->general_settings['extra_2'] : '',
167
+ 'extra_3' => isset( $this->general_settings['extra_3'] ) ? $this->general_settings['extra_3'] : '',
168
+ );
169
+ return $common_settings;
170
+ }
171
+
172
+ public function get_document_settings( $document_type ) {
173
+ $documents = WPO_WCPDF()->documents->get_documents('all');
174
+ foreach ($documents as $document) {
175
+ if ( $document->get_type() == $document_type ) {
176
+ return $document->settings;
177
+ }
178
+ }
179
+ return false;
180
+ }
181
+
182
+ public function get_output_format( $document_type = null ) {
183
+ if ( isset( $this->debug_settings['html_output'] ) ) {
184
+ $output_format = 'html';
185
+ } else {
186
+ $output_format = 'pdf';
187
+ }
188
+ return apply_filters( 'wpo_wcpdf_output_format', $output_format, $document_type );
189
+ }
190
+
191
+ public function get_output_mode() {
192
+ if ( isset( WPO_WCPDF()->settings->general_settings['download_display'] ) ) {
193
+ switch ( WPO_WCPDF()->settings->general_settings['download_display'] ) {
194
+ case 'display':
195
+ $output_mode = 'inline';
196
+ break;
197
+ case 'download':
198
+ default:
199
+ $output_mode = 'download';
200
+ break;
201
+ }
202
+ } else {
203
+ $output_mode = 'download';
204
+ }
205
+ return $output_mode;
206
+ }
207
+
208
+ public function get_template_path( $document_type = NULL ) {
209
+ $template_path = isset( $this->general_settings['template_path'] )?$this->general_settings['template_path']:'';
210
+ // forward slash for consistency
211
+ $template_path = str_replace('\\','/', $template_path);
212
+
213
+ // add base path, checking if it's not already there
214
+ // alternative setups like Bedrock have WP_CONTENT_DIR & ABSPATH separated
215
+ if ( defined('WP_CONTENT_DIR') && strpos( WP_CONTENT_DIR, ABSPATH ) !== false ) {
216
+ $forwardslash_basepath = str_replace('\\','/', ABSPATH);
217
+ } else {
218
+ // bedrock e.a
219
+ $forwardslash_basepath = str_replace('\\','/', WP_CONTENT_DIR);
220
+ }
221
+
222
+ if ( strpos( $template_path, $forwardslash_basepath ) === false ) {
223
+ $template_path = $forwardslash_basepath . $template_path;
224
+ }
225
+
226
+ return $template_path;
227
+ }
228
+
229
+ public function set_number_store() {
230
+ check_ajax_referer( "wpo_wcpdf_next_{$_POST['store']}", 'security' );
231
+ // check permissions
232
+ if ( !current_user_can('manage_woocommerce') ) {
233
+ die();
234
+ }
235
+
236
+ $number = isset( $_POST['number'] ) ? (int) $_POST['number'] : 0;
237
+ $number_store_method = $this->get_sequential_number_store_method();
238
+ $number_store = new Sequential_Number_Store( $_POST['store'], $number_store_method );
239
+ $number_store->set_next( $number );
240
+ echo "next number ({$_POST['store']}) set to {$number}";
241
+ die();
242
+ }
243
+
244
+ public function get_sequential_number_store_method() {
245
+ global $wpdb;
246
+ $method = isset( $this->debug_settings['calculate_document_numbers'] ) ? 'calculate' : 'auto_increment';
247
+
248
+ // safety first - always use calculate when auto_increment_increment is not 1
249
+ $row = $wpdb->get_row("SHOW VARIABLES LIKE 'auto_increment_increment'");
250
+ if ( !empty($row) && !empty($row->Value) && $row->Value != 1 ) {
251
+ $method = 'calculate';
252
+ }
253
+
254
+ return $method;
255
+ }
256
+
257
+ }
258
+
259
+ endif; // class_exists
260
+
261
  return new Settings();
includes/documents/abstract-wcpdf-order-document.php CHANGED
@@ -138,7 +138,10 @@ abstract class Order_Document {
138
  // get historical settings if enabled
139
  if ( !empty( $this->order ) && $this->use_historical_settings() == true ) {
140
  $order_settings = WCX_Order::get_meta( $this->order, "_wcpdf_{$this->slug}_settings" );
141
- if (!empty($order_settings)) {
 
 
 
142
  // not sure what happens if combining with current settings will have unwanted side effects
143
  // like unchecked options being enabled because missing = unchecked in historical - disabled for now
144
  // $settings = (array) $order_settings + (array) $settings;
@@ -294,9 +297,38 @@ abstract class Order_Document {
294
  do_action( 'wpo_wcpdf_delete_document', $this, $order );
295
  }
296
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
297
  public function is_allowed() {
298
  $allowed = true;
299
- if ( !empty( $this->settings['disable_for_statuses'] ) && !empty( $this->order ) && is_callable( array( $this->order, 'get_status' ) ) ) {
300
  $status = $this->order->get_status();
301
 
302
  $disabled_statuses = array_map( function($status){
@@ -429,6 +461,8 @@ abstract class Order_Document {
429
  public function set_number( $value, $order = null ) {
430
  $order = empty( $order ) ? $this->order : $order;
431
 
 
 
432
  if ( is_array( $value ) ) {
433
  $filtered_value = array_filter( $value );
434
  }
@@ -494,6 +528,15 @@ abstract class Order_Document {
494
  }
495
  }
496
 
 
 
 
 
 
 
 
 
 
497
  /**
498
  * Show logo html
499
  */
@@ -503,13 +546,15 @@ abstract class Order_Document {
503
  $company = $this->get_shop_name();
504
  if( $attachment_id ) {
505
  $attachment = wp_get_attachment_image_src( $attachment_id, 'full', false );
 
 
 
 
506
 
507
  $attachment_src = $attachment[0];
508
  $attachment_width = $attachment[1];
509
  $attachment_height = $attachment[2];
510
 
511
- $attachment_path = get_attached_file( $attachment_id );
512
-
513
  if ( apply_filters('wpo_wcpdf_use_path', true) && file_exists($attachment_path) ) {
514
  $src = $attachment_path;
515
  } else {
138
  // get historical settings if enabled
139
  if ( !empty( $this->order ) && $this->use_historical_settings() == true ) {
140
  $order_settings = WCX_Order::get_meta( $this->order, "_wcpdf_{$this->slug}_settings" );
141
+ if (!empty($order_settings) && !is_array($order_settings)) {
142
+ $order_settings = maybe_unserialize( $order_settings );
143
+ }
144
+ if (!empty($order_settings) && is_array($order_settings)) {
145
  // not sure what happens if combining with current settings will have unwanted side effects
146
  // like unchecked options being enabled because missing = unchecked in historical - disabled for now
147
  // $settings = (array) $order_settings + (array) $settings;
297
  do_action( 'wpo_wcpdf_delete_document', $this, $order );
298
  }
299
 
300
+ public function regenerate( $order = null ) {
301
+ $order = empty( $order ) ? $this->order : $order;
302
+ if ( empty( $order ) ) {
303
+ return; //Nothing to update
304
+ }
305
+
306
+ //Get most current settings
307
+ $common_settings = WPO_WCPDF()->settings->get_common_document_settings();
308
+ $document_settings = get_option( 'wpo_wcpdf_documents_settings_'.$this->get_type() );
309
+ $settings = (array) $document_settings + (array) $common_settings;
310
+ //Update document settings in meta
311
+ WCX_Order::update_meta_data( $this->order, "_wcpdf_{$this->slug}_settings", $settings );
312
+
313
+ //Use most current settings from here on
314
+ $this->settings = $this->get_settings( true );
315
+
316
+ //Add order note
317
+ $parent_order = $refund_id = false;
318
+ // If credit note
319
+ if ( $this->get_type() == 'credit-note' ) {
320
+ $refund_id = $order->get_id();
321
+ $parent_order = wc_get_order( $order->get_parent_id() );
322
+ }
323
+ $note = $refund_id ? sprintf( __( '%s (refund #%s) was regenerated.', 'wpo_wcpdf_pro' ), ucfirst( $this->get_title() ), $refund_id ) : sprintf( __( '%s was regenerated', 'wpo_wcpdf_pro' ), ucfirst( $this->get_title() ) );
324
+ $parent_order ? $parent_order->add_order_note( $note ) : $order->add_order_note( $note );
325
+
326
+ do_action( 'wpo_wcpdf_regenerate_document', $this );
327
+ }
328
+
329
  public function is_allowed() {
330
  $allowed = true;
331
+ if ( !$this->exists() && !empty( $this->settings['disable_for_statuses'] ) && !empty( $this->order ) && is_callable( array( $this->order, 'get_status' ) ) ) {
332
  $status = $this->order->get_status();
333
 
334
  $disabled_statuses = array_map( function($status){
461
  public function set_number( $value, $order = null ) {
462
  $order = empty( $order ) ? $this->order : $order;
463
 
464
+ $value = maybe_unserialize( $value ); // fix incorrectly stored meta
465
+
466
  if ( is_array( $value ) ) {
467
  $filtered_value = array_filter( $value );
468
  }
528
  }
529
  }
530
 
531
+ /**
532
+ * Return logo height
533
+ */
534
+ public function get_header_logo_height() {
535
+ if ( !empty( $this->settings['header_logo_height'] ) ) {
536
+ return apply_filters( 'wpo_wcpdf_header_logo_height', str_replace( ' ', '', $this->settings['header_logo_height'] ), $this );
537
+ }
538
+ }
539
+
540
  /**
541
  * Show logo html
542
  */
546
  $company = $this->get_shop_name();
547
  if( $attachment_id ) {
548
  $attachment = wp_get_attachment_image_src( $attachment_id, 'full', false );
549
+ $attachment_path = get_attached_file( $attachment_id );
550
+ if ( empty( $attachment ) || empty( $attachment_path ) ) {
551
+ return;
552
+ }
553
 
554
  $attachment_src = $attachment[0];
555
  $attachment_width = $attachment[1];
556
  $attachment_height = $attachment[2];
557
 
 
 
558
  if ( apply_filters('wpo_wcpdf_use_path', true) && file_exists($attachment_path) ) {
559
  $src = $attachment_path;
560
  } else {
readme.txt CHANGED
@@ -5,7 +5,7 @@ Tags: woocommerce, pdf, invoices, packing slips, print, delivery notes, invoice,
5
  Requires at least: 3.5
6
  Tested up to: 5.4
7
  Requires PHP: 5.3
8
- Stable tag: 2.4.10
9
  License: GPLv2 or later
10
  License URI: http://www.gnu.org/licenses/gpl-2.0.html
11
 
@@ -102,6 +102,18 @@ There's a setting on the Status tab of the settings page that allows you to togg
102
 
103
  == Changelog ==
104
 
 
 
 
 
 
 
 
 
 
 
 
 
105
  = 2.4.10 =
106
  * Tested up to WooCommerce 4.1
107
 
5
  Requires at least: 3.5
6
  Tested up to: 5.4
7
  Requires PHP: 5.3
8
+ Stable tag: 2.5.0
9
  License: GPLv2 or later
10
  License URI: http://www.gnu.org/licenses/gpl-2.0.html
11
 
102
 
103
  == Changelog ==
104
 
105
+ = 2.5.0 =
106
+ * Feature: Manually regenerate individual documents with latest settings (shop address/footer/etc)
107
+ * Feature: Shortcode to download invoice: `[wcpdf_download_invoice]`
108
+ * Feature: Logo height setting
109
+ * Fix: textdomain fallback would fail on specific site domains including .mo
110
+ * Fix: Unnecessary extra page on edge case table heights
111
+ * Fix: Settings disappearing when overriding document titles to empty string
112
+ * Fix: check if header logo file still exists before loading
113
+ * Fix: If document is already created, disregard 'disable for:' setting
114
+ * Fix: Reading document settings & number when stored incorrectly (by external plugins)
115
+ * Tested up to WooCommerce 4.2
116
+
117
  = 2.4.10 =
118
  * Tested up to WooCommerce 4.1
119
 
templates/Simple/invoice.php CHANGED
@@ -1,149 +1,151 @@
1
- <?php if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly ?>
2
- <?php do_action( 'wpo_wcpdf_before_document', $this->type, $this->order ); ?>
3
-
4
- <table class="head container">
5
- <tr>
6
- <td class="header">
7
- <?php
8
- if( $this->has_header_logo() ) {
9
- $this->header_logo();
10
- } else {
11
- echo $this->get_title();
12
- }
13
- ?>
14
- </td>
15
- <td class="shop-info">
16
- <div class="shop-name"><h3><?php $this->shop_name(); ?></h3></div>
17
- <div class="shop-address"><?php $this->shop_address(); ?></div>
18
- </td>
19
- </tr>
20
- </table>
21
-
22
- <h1 class="document-type-label">
23
- <?php if( $this->has_header_logo() ) echo $this->get_title(); ?>
24
- </h1>
25
-
26
- <?php do_action( 'wpo_wcpdf_after_document_label', $this->type, $this->order ); ?>
27
-
28
- <table class="order-data-addresses">
29
- <tr>
30
- <td class="address billing-address">
31
- <!-- <h3><?php _e( 'Billing Address:', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3> -->
32
- <?php do_action( 'wpo_wcpdf_before_billing_address', $this->type, $this->order ); ?>
33
- <?php $this->billing_address(); ?>
34
- <?php do_action( 'wpo_wcpdf_after_billing_address', $this->type, $this->order ); ?>
35
- <?php if ( isset($this->settings['display_email']) ) { ?>
36
- <div class="billing-email"><?php $this->billing_email(); ?></div>
37
- <?php } ?>
38
- <?php if ( isset($this->settings['display_phone']) ) { ?>
39
- <div class="billing-phone"><?php $this->billing_phone(); ?></div>
40
- <?php } ?>
41
- </td>
42
- <td class="address shipping-address">
43
- <?php if ( isset($this->settings['display_shipping_address']) && $this->ships_to_different_address()) { ?>
44
- <h3><?php _e( 'Ship To:', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3>
45
- <?php do_action( 'wpo_wcpdf_before_shipping_address', $this->type, $this->order ); ?>
46
- <?php $this->shipping_address(); ?>
47
- <?php do_action( 'wpo_wcpdf_after_shipping_address', $this->type, $this->order ); ?>
48
- <?php } ?>
49
- </td>
50
- <td class="order-data">
51
- <table>
52
- <?php do_action( 'wpo_wcpdf_before_order_data', $this->type, $this->order ); ?>
53
- <?php if ( isset($this->settings['display_number']) ) { ?>
54
- <tr class="invoice-number">
55
- <th><?php _e( 'Invoice Number:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
56
- <td><?php $this->invoice_number(); ?></td>
57
- </tr>
58
- <?php } ?>
59
- <?php if ( isset($this->settings['display_date']) ) { ?>
60
- <tr class="invoice-date">
61
- <th><?php _e( 'Invoice Date:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
62
- <td><?php $this->invoice_date(); ?></td>
63
- </tr>
64
- <?php } ?>
65
- <tr class="order-number">
66
- <th><?php _e( 'Order Number:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
67
- <td><?php $this->order_number(); ?></td>
68
- </tr>
69
- <tr class="order-date">
70
- <th><?php _e( 'Order Date:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
71
- <td><?php $this->order_date(); ?></td>
72
- </tr>
73
- <tr class="payment-method">
74
- <th><?php _e( 'Payment Method:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
75
- <td><?php $this->payment_method(); ?></td>
76
- </tr>
77
- <?php do_action( 'wpo_wcpdf_after_order_data', $this->type, $this->order ); ?>
78
- </table>
79
- </td>
80
- </tr>
81
- </table>
82
-
83
- <?php do_action( 'wpo_wcpdf_before_order_details', $this->type, $this->order ); ?>
84
-
85
- <table class="order-details">
86
- <thead>
87
- <tr>
88
- <th class="product"><?php _e('Product', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
89
- <th class="quantity"><?php _e('Quantity', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
90
- <th class="price"><?php _e('Price', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
91
- </tr>
92
- </thead>
93
- <tbody>
94
- <?php $items = $this->get_order_items(); if( sizeof( $items ) > 0 ) : foreach( $items as $item_id => $item ) : ?>
95
- <tr class="<?php echo apply_filters( 'wpo_wcpdf_item_row_class', $item_id, $this->type, $this->order, $item_id ); ?>">
96
- <td class="product">
97
- <?php $description_label = __( 'Description', 'woocommerce-pdf-invoices-packing-slips' ); // registering alternate label translation ?>
98
- <span class="item-name"><?php echo $item['name']; ?></span>
99
- <?php do_action( 'wpo_wcpdf_before_item_meta', $this->type, $item, $this->order ); ?>
100
- <span class="item-meta"><?php echo $item['meta']; ?></span>
101
- <dl class="meta">
102
- <?php $description_label = __( 'SKU', 'woocommerce-pdf-invoices-packing-slips' ); // registering alternate label translation ?>
103
- <?php if( !empty( $item['sku'] ) ) : ?><dt class="sku"><?php _e( 'SKU:', 'woocommerce-pdf-invoices-packing-slips' ); ?></dt><dd class="sku"><?php echo $item['sku']; ?></dd><?php endif; ?>
104
- <?php if( !empty( $item['weight'] ) ) : ?><dt class="weight"><?php _e( 'Weight:', 'woocommerce-pdf-invoices-packing-slips' ); ?></dt><dd class="weight"><?php echo $item['weight']; ?><?php echo get_option('woocommerce_weight_unit'); ?></dd><?php endif; ?>
105
- </dl>
106
- <?php do_action( 'wpo_wcpdf_after_item_meta', $this->type, $item, $this->order ); ?>
107
- </td>
108
- <td class="quantity"><?php echo $item['quantity']; ?></td>
109
- <td class="price"><?php echo $item['order_price']; ?></td>
110
- </tr>
111
- <?php endforeach; endif; ?>
112
- </tbody>
113
- <tfoot>
114
- <tr class="no-borders">
115
- <td class="no-borders">
116
- <div class="customer-notes">
117
- <?php do_action( 'wpo_wcpdf_before_customer_notes', $this->type, $this->order ); ?>
118
- <?php if ( $this->get_shipping_notes() ) : ?>
119
- <h3><?php _e( 'Customer Notes', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3>
120
- <?php $this->shipping_notes(); ?>
121
- <?php endif; ?>
122
- <?php do_action( 'wpo_wcpdf_after_customer_notes', $this->type, $this->order ); ?>
123
- </div>
124
- </td>
125
- <td class="no-borders" colspan="2">
126
- <table class="totals">
127
- <tfoot>
128
- <?php foreach( $this->get_woocommerce_totals() as $key => $total ) : ?>
129
- <tr class="<?php echo $key; ?>">
130
- <td class="no-borders"></td>
131
- <th class="description"><?php echo $total['label']; ?></th>
132
- <td class="price"><span class="totals-price"><?php echo $total['value']; ?></span></td>
133
- </tr>
134
- <?php endforeach; ?>
135
- </tfoot>
136
- </table>
137
- </td>
138
- </tr>
139
- </tfoot>
140
- </table>
141
-
142
- <?php do_action( 'wpo_wcpdf_after_order_details', $this->type, $this->order ); ?>
143
-
144
- <?php if ( $this->get_footer() ): ?>
145
- <div id="footer">
146
- <?php $this->footer(); ?>
147
- </div><!-- #letter-footer -->
148
- <?php endif; ?>
149
- <?php do_action( 'wpo_wcpdf_after_document', $this->type, $this->order ); ?>
 
 
1
+ <?php if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly ?>
2
+ <?php do_action( 'wpo_wcpdf_before_document', $this->type, $this->order ); ?>
3
+
4
+ <table class="head container">
5
+ <tr>
6
+ <td class="header">
7
+ <?php
8
+ if( $this->has_header_logo() ) {
9
+ $this->header_logo();
10
+ } else {
11
+ echo $this->get_title();
12
+ }
13
+ ?>
14
+ </td>
15
+ <td class="shop-info">
16
+ <div class="shop-name"><h3><?php $this->shop_name(); ?></h3></div>
17
+ <div class="shop-address"><?php $this->shop_address(); ?></div>
18
+ </td>
19
+ </tr>
20
+ </table>
21
+
22
+ <h1 class="document-type-label">
23
+ <?php if( $this->has_header_logo() ) echo $this->get_title(); ?>
24
+ </h1>
25
+
26
+ <?php do_action( 'wpo_wcpdf_after_document_label', $this->type, $this->order ); ?>
27
+
28
+ <table class="order-data-addresses">
29
+ <tr>
30
+ <td class="address billing-address">
31
+ <!-- <h3><?php _e( 'Billing Address:', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3> -->
32
+ <?php do_action( 'wpo_wcpdf_before_billing_address', $this->type, $this->order ); ?>
33
+ <?php $this->billing_address(); ?>
34
+ <?php do_action( 'wpo_wcpdf_after_billing_address', $this->type, $this->order ); ?>
35
+ <?php if ( isset($this->settings['display_email']) ) { ?>
36
+ <div class="billing-email"><?php $this->billing_email(); ?></div>
37
+ <?php } ?>
38
+ <?php if ( isset($this->settings['display_phone']) ) { ?>
39
+ <div class="billing-phone"><?php $this->billing_phone(); ?></div>
40
+ <?php } ?>
41
+ </td>
42
+ <td class="address shipping-address">
43
+ <?php if ( isset($this->settings['display_shipping_address']) && $this->ships_to_different_address()) { ?>
44
+ <h3><?php _e( 'Ship To:', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3>
45
+ <?php do_action( 'wpo_wcpdf_before_shipping_address', $this->type, $this->order ); ?>
46
+ <?php $this->shipping_address(); ?>
47
+ <?php do_action( 'wpo_wcpdf_after_shipping_address', $this->type, $this->order ); ?>
48
+ <?php } ?>
49
+ </td>
50
+ <td class="order-data">
51
+ <table>
52
+ <?php do_action( 'wpo_wcpdf_before_order_data', $this->type, $this->order ); ?>
53
+ <?php if ( isset($this->settings['display_number']) ) { ?>
54
+ <tr class="invoice-number">
55
+ <th><?php _e( 'Invoice Number:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
56
+ <td><?php $this->invoice_number(); ?></td>
57
+ </tr>
58
+ <?php } ?>
59
+ <?php if ( isset($this->settings['display_date']) ) { ?>
60
+ <tr class="invoice-date">
61
+ <th><?php _e( 'Invoice Date:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
62
+ <td><?php $this->invoice_date(); ?></td>
63
+ </tr>
64
+ <?php } ?>
65
+ <tr class="order-number">
66
+ <th><?php _e( 'Order Number:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
67
+ <td><?php $this->order_number(); ?></td>
68
+ </tr>
69
+ <tr class="order-date">
70
+ <th><?php _e( 'Order Date:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
71
+ <td><?php $this->order_date(); ?></td>
72
+ </tr>
73
+ <tr class="payment-method">
74
+ <th><?php _e( 'Payment Method:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
75
+ <td><?php $this->payment_method(); ?></td>
76
+ </tr>
77
+ <?php do_action( 'wpo_wcpdf_after_order_data', $this->type, $this->order ); ?>
78
+ </table>
79
+ </td>
80
+ </tr>
81
+ </table>
82
+
83
+ <?php do_action( 'wpo_wcpdf_before_order_details', $this->type, $this->order ); ?>
84
+
85
+ <table class="order-details">
86
+ <thead>
87
+ <tr>
88
+ <th class="product"><?php _e('Product', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
89
+ <th class="quantity"><?php _e('Quantity', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
90
+ <th class="price"><?php _e('Price', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
91
+ </tr>
92
+ </thead>
93
+ <tbody>
94
+ <?php $items = $this->get_order_items(); if( sizeof( $items ) > 0 ) : foreach( $items as $item_id => $item ) : ?>
95
+ <tr class="<?php echo apply_filters( 'wpo_wcpdf_item_row_class', $item_id, $this->type, $this->order, $item_id ); ?>">
96
+ <td class="product">
97
+ <?php $description_label = __( 'Description', 'woocommerce-pdf-invoices-packing-slips' ); // registering alternate label translation ?>
98
+ <span class="item-name"><?php echo $item['name']; ?></span>
99
+ <?php do_action( 'wpo_wcpdf_before_item_meta', $this->type, $item, $this->order ); ?>
100
+ <span class="item-meta"><?php echo $item['meta']; ?></span>
101
+ <dl class="meta">
102
+ <?php $description_label = __( 'SKU', 'woocommerce-pdf-invoices-packing-slips' ); // registering alternate label translation ?>
103
+ <?php if( !empty( $item['sku'] ) ) : ?><dt class="sku"><?php _e( 'SKU:', 'woocommerce-pdf-invoices-packing-slips' ); ?></dt><dd class="sku"><?php echo $item['sku']; ?></dd><?php endif; ?>
104
+ <?php if( !empty( $item['weight'] ) ) : ?><dt class="weight"><?php _e( 'Weight:', 'woocommerce-pdf-invoices-packing-slips' ); ?></dt><dd class="weight"><?php echo $item['weight']; ?><?php echo get_option('woocommerce_weight_unit'); ?></dd><?php endif; ?>
105
+ </dl>
106
+ <?php do_action( 'wpo_wcpdf_after_item_meta', $this->type, $item, $this->order ); ?>
107
+ </td>
108
+ <td class="quantity"><?php echo $item['quantity']; ?></td>
109
+ <td class="price"><?php echo $item['order_price']; ?></td>
110
+ </tr>
111
+ <?php endforeach; endif; ?>
112
+ </tbody>
113
+ <tfoot>
114
+ <tr class="no-borders">
115
+ <td class="no-borders">
116
+ <div class="customer-notes">
117
+ <?php do_action( 'wpo_wcpdf_before_customer_notes', $this->type, $this->order ); ?>
118
+ <?php if ( $this->get_shipping_notes() ) : ?>
119
+ <h3><?php _e( 'Customer Notes', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3>
120
+ <?php $this->shipping_notes(); ?>
121
+ <?php endif; ?>
122
+ <?php do_action( 'wpo_wcpdf_after_customer_notes', $this->type, $this->order ); ?>
123
+ </div>
124
+ </td>
125
+ <td class="no-borders" colspan="2">
126
+ <table class="totals">
127
+ <tfoot>
128
+ <?php foreach( $this->get_woocommerce_totals() as $key => $total ) : ?>
129
+ <tr class="<?php echo $key; ?>">
130
+ <td class="no-borders"></td>
131
+ <th class="description"><?php echo $total['label']; ?></th>
132
+ <td class="price"><span class="totals-price"><?php echo $total['value']; ?></span></td>
133
+ </tr>
134
+ <?php endforeach; ?>
135
+ </tfoot>
136
+ </table>
137
+ </td>
138
+ </tr>
139
+ </tfoot>
140
+ </table>
141
+
142
+ <div class="bottom-spacer"></div>
143
+
144
+ <?php do_action( 'wpo_wcpdf_after_order_details', $this->type, $this->order ); ?>
145
+
146
+ <?php if ( $this->get_footer() ): ?>
147
+ <div id="footer">
148
+ <?php $this->footer(); ?>
149
+ </div><!-- #letter-footer -->
150
+ <?php endif; ?>
151
+ <?php do_action( 'wpo_wcpdf_after_document', $this->type, $this->order ); ?>
templates/Simple/packing-slip.php CHANGED
@@ -1,118 +1,120 @@
1
- <?php if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly ?>
2
- <?php do_action( 'wpo_wcpdf_before_document', $this->type, $this->order ); ?>
3
-
4
- <table class="head container">
5
- <tr>
6
- <td class="header">
7
- <?php
8
- if( $this->has_header_logo() ) {
9
- $this->header_logo();
10
- } else {
11
- echo $this->get_title();
12
- }
13
- ?>
14
- </td>
15
- <td class="shop-info">
16
- <div class="shop-name"><h3><?php $this->shop_name(); ?></h3></div>
17
- <div class="shop-address"><?php $this->shop_address(); ?></div>
18
- </td>
19
- </tr>
20
- </table>
21
-
22
- <h1 class="document-type-label">
23
- <?php if( $this->has_header_logo() ) echo $this->get_title(); ?>
24
- </h1>
25
-
26
- <?php do_action( 'wpo_wcpdf_after_document_label', $this->type, $this->order ); ?>
27
-
28
- <table class="order-data-addresses">
29
- <tr>
30
- <td class="address shipping-address">
31
- <!-- <h3><?php _e( 'Shipping Address:', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3> -->
32
- <?php do_action( 'wpo_wcpdf_before_shipping_address', $this->type, $this->order ); ?>
33
- <?php $this->shipping_address(); ?>
34
- <?php do_action( 'wpo_wcpdf_after_shipping_address', $this->type, $this->order ); ?>
35
- <?php if ( isset($this->settings['display_email']) ) { ?>
36
- <div class="billing-email"><?php $this->billing_email(); ?></div>
37
- <?php } ?>
38
- <?php if ( isset($this->settings['display_phone']) ) { ?>
39
- <div class="billing-phone"><?php $this->billing_phone(); ?></div>
40
- <?php } ?>
41
- </td>
42
- <td class="address billing-address">
43
- <?php if ( isset($this->settings['display_billing_address']) && $this->ships_to_different_address()) { ?>
44
- <h3><?php _e( 'Billing Address:', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3>
45
- <?php do_action( 'wpo_wcpdf_before_billing_address', $this->type, $this->order ); ?>
46
- <?php $this->billing_address(); ?>
47
- <?php do_action( 'wpo_wcpdf_after_billing_address', $this->type, $this->order ); ?>
48
- <?php } ?>
49
- </td>
50
- <td class="order-data">
51
- <table>
52
- <?php do_action( 'wpo_wcpdf_before_order_data', $this->type, $this->order ); ?>
53
- <tr class="order-number">
54
- <th><?php _e( 'Order Number:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
55
- <td><?php $this->order_number(); ?></td>
56
- </tr>
57
- <tr class="order-date">
58
- <th><?php _e( 'Order Date:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
59
- <td><?php $this->order_date(); ?></td>
60
- </tr>
61
- <tr class="shipping-method">
62
- <th><?php _e( 'Shipping Method:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
63
- <td><?php $this->shipping_method(); ?></td>
64
- </tr>
65
- <?php do_action( 'wpo_wcpdf_after_order_data', $this->type, $this->order ); ?>
66
- </table>
67
- </td>
68
- </tr>
69
- </table>
70
-
71
- <?php do_action( 'wpo_wcpdf_before_order_details', $this->type, $this->order ); ?>
72
-
73
- <table class="order-details">
74
- <thead>
75
- <tr>
76
- <th class="product"><?php _e('Product', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
77
- <th class="quantity"><?php _e('Quantity', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
78
- </tr>
79
- </thead>
80
- <tbody>
81
- <?php $items = $this->get_order_items(); if( sizeof( $items ) > 0 ) : foreach( $items as $item_id => $item ) : ?>
82
- <tr class="<?php echo apply_filters( 'wpo_wcpdf_item_row_class', $item_id, $this->type, $this->order, $item_id ); ?>">
83
- <td class="product">
84
- <?php $description_label = __( 'Description', 'woocommerce-pdf-invoices-packing-slips' ); // registering alternate label translation ?>
85
- <span class="item-name"><?php echo $item['name']; ?></span>
86
- <?php do_action( 'wpo_wcpdf_before_item_meta', $this->type, $item, $this->order ); ?>
87
- <span class="item-meta"><?php echo $item['meta']; ?></span>
88
- <dl class="meta">
89
- <?php $description_label = __( 'SKU', 'woocommerce-pdf-invoices-packing-slips' ); // registering alternate label translation ?>
90
- <?php if( !empty( $item['sku'] ) ) : ?><dt class="sku"><?php _e( 'SKU:', 'woocommerce-pdf-invoices-packing-slips' ); ?></dt><dd class="sku"><?php echo $item['sku']; ?></dd><?php endif; ?>
91
- <?php if( !empty( $item['weight'] ) ) : ?><dt class="weight"><?php _e( 'Weight:', 'woocommerce-pdf-invoices-packing-slips' ); ?></dt><dd class="weight"><?php echo $item['weight']; ?><?php echo get_option('woocommerce_weight_unit'); ?></dd><?php endif; ?>
92
- </dl>
93
- <?php do_action( 'wpo_wcpdf_after_item_meta', $this->type, $item, $this->order ); ?>
94
- </td>
95
- <td class="quantity"><?php echo $item['quantity']; ?></td>
96
- </tr>
97
- <?php endforeach; endif; ?>
98
- </tbody>
99
- </table>
100
-
101
- <?php do_action( 'wpo_wcpdf_after_order_details', $this->type, $this->order ); ?>
102
-
103
- <?php do_action( 'wpo_wcpdf_before_customer_notes', $this->type, $this->order ); ?>
104
- <div class="customer-notes">
105
- <?php if ( $this->get_shipping_notes() ) : ?>
106
- <h3><?php _e( 'Customer Notes', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3>
107
- <?php $this->shipping_notes(); ?>
108
- <?php endif; ?>
109
- </div>
110
- <?php do_action( 'wpo_wcpdf_after_customer_notes', $this->type, $this->order ); ?>
111
-
112
- <?php if ( $this->get_footer() ): ?>
113
- <div id="footer">
114
- <?php $this->footer(); ?>
115
- </div><!-- #letter-footer -->
116
- <?php endif; ?>
117
-
 
 
118
  <?php do_action( 'wpo_wcpdf_after_document', $this->type, $this->order ); ?>
1
+ <?php if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly ?>
2
+ <?php do_action( 'wpo_wcpdf_before_document', $this->type, $this->order ); ?>
3
+
4
+ <table class="head container">
5
+ <tr>
6
+ <td class="header">
7
+ <?php
8
+ if( $this->has_header_logo() ) {
9
+ $this->header_logo();
10
+ } else {
11
+ echo $this->get_title();
12
+ }
13
+ ?>
14
+ </td>
15
+ <td class="shop-info">
16
+ <div class="shop-name"><h3><?php $this->shop_name(); ?></h3></div>
17
+ <div class="shop-address"><?php $this->shop_address(); ?></div>
18
+ </td>
19
+ </tr>
20
+ </table>
21
+
22
+ <h1 class="document-type-label">
23
+ <?php if( $this->has_header_logo() ) echo $this->get_title(); ?>
24
+ </h1>
25
+
26
+ <?php do_action( 'wpo_wcpdf_after_document_label', $this->type, $this->order ); ?>
27
+
28
+ <table class="order-data-addresses">
29
+ <tr>
30
+ <td class="address shipping-address">
31
+ <!-- <h3><?php _e( 'Shipping Address:', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3> -->
32
+ <?php do_action( 'wpo_wcpdf_before_shipping_address', $this->type, $this->order ); ?>
33
+ <?php $this->shipping_address(); ?>
34
+ <?php do_action( 'wpo_wcpdf_after_shipping_address', $this->type, $this->order ); ?>
35
+ <?php if ( isset($this->settings['display_email']) ) { ?>
36
+ <div class="billing-email"><?php $this->billing_email(); ?></div>
37
+ <?php } ?>
38
+ <?php if ( isset($this->settings['display_phone']) ) { ?>
39
+ <div class="billing-phone"><?php $this->billing_phone(); ?></div>
40
+ <?php } ?>
41
+ </td>
42
+ <td class="address billing-address">
43
+ <?php if ( isset($this->settings['display_billing_address']) && $this->ships_to_different_address()) { ?>
44
+ <h3><?php _e( 'Billing Address:', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3>
45
+ <?php do_action( 'wpo_wcpdf_before_billing_address', $this->type, $this->order ); ?>
46
+ <?php $this->billing_address(); ?>
47
+ <?php do_action( 'wpo_wcpdf_after_billing_address', $this->type, $this->order ); ?>
48
+ <?php } ?>
49
+ </td>
50
+ <td class="order-data">
51
+ <table>
52
+ <?php do_action( 'wpo_wcpdf_before_order_data', $this->type, $this->order ); ?>
53
+ <tr class="order-number">
54
+ <th><?php _e( 'Order Number:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
55
+ <td><?php $this->order_number(); ?></td>
56
+ </tr>
57
+ <tr class="order-date">
58
+ <th><?php _e( 'Order Date:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
59
+ <td><?php $this->order_date(); ?></td>
60
+ </tr>
61
+ <tr class="shipping-method">
62
+ <th><?php _e( 'Shipping Method:', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
63
+ <td><?php $this->shipping_method(); ?></td>
64
+ </tr>
65
+ <?php do_action( 'wpo_wcpdf_after_order_data', $this->type, $this->order ); ?>
66
+ </table>
67
+ </td>
68
+ </tr>
69
+ </table>
70
+
71
+ <?php do_action( 'wpo_wcpdf_before_order_details', $this->type, $this->order ); ?>
72
+
73
+ <table class="order-details">
74
+ <thead>
75
+ <tr>
76
+ <th class="product"><?php _e('Product', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
77
+ <th class="quantity"><?php _e('Quantity', 'woocommerce-pdf-invoices-packing-slips' ); ?></th>
78
+ </tr>
79
+ </thead>
80
+ <tbody>
81
+ <?php $items = $this->get_order_items(); if( sizeof( $items ) > 0 ) : foreach( $items as $item_id => $item ) : ?>
82
+ <tr class="<?php echo apply_filters( 'wpo_wcpdf_item_row_class', $item_id, $this->type, $this->order, $item_id ); ?>">
83
+ <td class="product">
84
+ <?php $description_label = __( 'Description', 'woocommerce-pdf-invoices-packing-slips' ); // registering alternate label translation ?>
85
+ <span class="item-name"><?php echo $item['name']; ?></span>
86
+ <?php do_action( 'wpo_wcpdf_before_item_meta', $this->type, $item, $this->order ); ?>
87
+ <span class="item-meta"><?php echo $item['meta']; ?></span>
88
+ <dl class="meta">
89
+ <?php $description_label = __( 'SKU', 'woocommerce-pdf-invoices-packing-slips' ); // registering alternate label translation ?>
90
+ <?php if( !empty( $item['sku'] ) ) : ?><dt class="sku"><?php _e( 'SKU:', 'woocommerce-pdf-invoices-packing-slips' ); ?></dt><dd class="sku"><?php echo $item['sku']; ?></dd><?php endif; ?>
91
+ <?php if( !empty( $item['weight'] ) ) : ?><dt class="weight"><?php _e( 'Weight:', 'woocommerce-pdf-invoices-packing-slips' ); ?></dt><dd class="weight"><?php echo $item['weight']; ?><?php echo get_option('woocommerce_weight_unit'); ?></dd><?php endif; ?>
92
+ </dl>
93
+ <?php do_action( 'wpo_wcpdf_after_item_meta', $this->type, $item, $this->order ); ?>
94
+ </td>
95
+ <td class="quantity"><?php echo $item['quantity']; ?></td>
96
+ </tr>
97
+ <?php endforeach; endif; ?>
98
+ </tbody>
99
+ </table>
100
+
101
+ <div class="bottom-spacer"></div>
102
+
103
+ <?php do_action( 'wpo_wcpdf_after_order_details', $this->type, $this->order ); ?>
104
+
105
+ <?php do_action( 'wpo_wcpdf_before_customer_notes', $this->type, $this->order ); ?>
106
+ <div class="customer-notes">
107
+ <?php if ( $this->get_shipping_notes() ) : ?>
108
+ <h3><?php _e( 'Customer Notes', 'woocommerce-pdf-invoices-packing-slips' ); ?></h3>
109
+ <?php $this->shipping_notes(); ?>
110
+ <?php endif; ?>
111
+ </div>
112
+ <?php do_action( 'wpo_wcpdf_after_customer_notes', $this->type, $this->order ); ?>
113
+
114
+ <?php if ( $this->get_footer() ): ?>
115
+ <div id="footer">
116
+ <?php $this->footer(); ?>
117
+ </div><!-- #letter-footer -->
118
+ <?php endif; ?>
119
+
120
  <?php do_action( 'wpo_wcpdf_after_document', $this->type, $this->order ); ?>
templates/Simple/style.css CHANGED
@@ -1,270 +1,275 @@
1
- /* Main Body */
2
- @page {
3
- margin-top: 1cm;
4
- margin-bottom: 3cm;
5
- margin-left: 2cm;
6
- margin-right: 2cm;
7
- }
8
- body {
9
- background: #fff;
10
- color: #000;
11
- margin: 0cm;
12
- font-family: 'Open Sans', sans-serif;
13
- /* want to use custom fonts? http://docs.wpovernight.com/woocommerce-pdf-invoices-packing-slips/using-custom-fonts/ */
14
- font-size: 9pt;
15
- line-height: 100%; /* fixes inherit dompdf bug */
16
- }
17
-
18
- h1, h2, h3, h4 {
19
- font-weight: bold;
20
- margin: 0;
21
- }
22
-
23
- h1 {
24
- font-size: 16pt;
25
- margin: 5mm 0;
26
- }
27
-
28
- h2 {
29
- font-size: 14pt;
30
- }
31
-
32
- h3, h4 {
33
- font-size: 9pt;
34
- }
35
-
36
-
37
- ol,
38
- ul {
39
- list-style: none;
40
- margin: 0;
41
- padding: 0;
42
- }
43
-
44
- li,
45
- ul {
46
- margin-bottom: 0.75em;
47
- }
48
-
49
- p {
50
- margin: 0;
51
- padding: 0;
52
- }
53
-
54
- p + p {
55
- margin-top: 1.25em;
56
- }
57
-
58
- a {
59
- border-bottom: 1px solid;
60
- text-decoration: none;
61
- }
62
-
63
- /* Basic Table Styling */
64
- table {
65
- border-collapse: collapse;
66
- border-spacing: 0;
67
- page-break-inside: always;
68
- border: 0;
69
- margin: 0;
70
- padding: 0;
71
- }
72
-
73
- th, td {
74
- vertical-align: top;
75
- text-align: left;
76
- }
77
-
78
- table.container {
79
- width:100%;
80
- border: 0;
81
- }
82
-
83
- tr.no-borders,
84
- td.no-borders {
85
- border: 0 !important;
86
- border-top: 0 !important;
87
- border-bottom: 0 !important;
88
- padding: 0 !important;
89
- width: auto;
90
- }
91
-
92
- /* Header */
93
- table.head {
94
- margin-bottom: 12mm;
95
- }
96
-
97
- td.header img {
98
- max-height: 3cm;
99
- width: auto;
100
- }
101
-
102
- td.header {
103
- font-size: 16pt;
104
- font-weight: 700;
105
- }
106
-
107
- td.shop-info {
108
- width: 40%;
109
- }
110
- .document-type-label {
111
- text-transform: uppercase;
112
- }
113
-
114
- /* Recipient addressses & order data */
115
- table.order-data-addresses {
116
- width: 100%;
117
- margin-bottom: 10mm;
118
- }
119
-
120
- td.order-data {
121
- width: 40%;
122
- }
123
-
124
- .invoice .shipping-address {
125
- width: 30%;
126
- }
127
-
128
- .packing-slip .billing-address {
129
- width: 30%;
130
- }
131
-
132
- td.order-data table th {
133
- font-weight: normal;
134
- padding-right: 2mm;
135
- }
136
-
137
- /* Order details */
138
- table.order-details {
139
- width:100%;
140
- margin-bottom: 8mm;
141
- }
142
-
143
- .quantity,
144
- .price {
145
- width: 20%;
146
- }
147
-
148
- .order-details tr {
149
- page-break-inside: always;
150
- page-break-after: auto;
151
- }
152
-
153
- .order-details td,
154
- .order-details th {
155
- border-bottom: 1px #ccc solid;
156
- border-top: 1px #ccc solid;
157
- padding: 0.375em;
158
- }
159
-
160
- .order-details th {
161
- font-weight: bold;
162
- text-align: left;
163
- }
164
-
165
- .order-details thead th {
166
- color: white;
167
- background-color: black;
168
- border-color: black;
169
- }
170
-
171
- /* product bundles compatibility */
172
- .order-details tr.bundled-item td.product {
173
- padding-left: 5mm;
174
- }
175
-
176
- .order-details tr.product-bundle td,
177
- .order-details tr.bundled-item td {
178
- border: 0;
179
- }
180
-
181
- .order-details tr.bundled-item.hidden {
182
- display: none;
183
- }
184
-
185
- /* item meta formatting for WC2.6 and older */
186
- dl {
187
- margin: 4px 0;
188
- }
189
-
190
- dt, dd, dd p {
191
- display: inline;
192
- font-size: 7pt;
193
- line-height: 7pt;
194
- }
195
-
196
- dd {
197
- margin-left: 5px;
198
- }
199
-
200
- dd:after {
201
- content: "\A";
202
- white-space: pre;
203
- }
204
- /* item-meta formatting for WC3.0+ */
205
- .wc-item-meta {
206
- margin: 4px 0;
207
- font-size: 7pt;
208
- line-height: 7pt;
209
- }
210
- .wc-item-meta p {
211
- display: inline;
212
- }
213
- .wc-item-meta li {
214
- margin: 0;
215
- margin-left: 5px;
216
- }
217
-
218
- /* Notes & Totals */
219
- .customer-notes {
220
- margin-top: 5mm;
221
- }
222
-
223
- table.totals {
224
- width: 100%;
225
- margin-top: 5mm;
226
- }
227
-
228
- table.totals th,
229
- table.totals td {
230
- border: 0;
231
- border-top: 1px solid #ccc;
232
- border-bottom: 1px solid #ccc;
233
- }
234
-
235
- table.totals th.description,
236
- table.totals td.price {
237
- width: 50%;
238
- }
239
-
240
- table.totals tr.order_total td,
241
- table.totals tr.order_total th {
242
- border-top: 2px solid #000;
243
- border-bottom: 2px solid #000;
244
- font-weight: bold;
245
- }
246
-
247
- table.totals tr.payment_method {
248
- display: none;
249
- }
250
-
251
- /* Footer Imprint */
252
- #footer {
253
- position: absolute;
254
- bottom: -2cm;
255
- left: 0;
256
- right: 0;
257
- height: 2cm; /* if you change the footer height, don't forget to change the bottom (=negative height) and the @page margin-bottom as well! */
258
- text-align: center;
259
- border-top: 0.1mm solid gray;
260
- margin-bottom: 0;
261
- padding-top: 2mm;
262
- }
263
-
264
- /* page numbers */
265
- .pagenum:before {
266
- content: counter(page);
267
- }
268
- .pagenum,.pagecount {
269
- font-family: sans-serif;
 
 
 
 
 
270
  }
1
+ /* Main Body */
2
+ @page {
3
+ margin-top: 1cm;
4
+ margin-bottom: 3cm;
5
+ margin-left: 2cm;
6
+ margin-right: 2cm;
7
+ }
8
+ body {
9
+ background: #fff;
10
+ color: #000;
11
+ margin: 0cm;
12
+ font-family: 'Open Sans', sans-serif;
13
+ /* want to use custom fonts? http://docs.wpovernight.com/woocommerce-pdf-invoices-packing-slips/using-custom-fonts/ */
14
+ font-size: 9pt;
15
+ line-height: 100%; /* fixes inherit dompdf bug */
16
+ }
17
+
18
+ h1, h2, h3, h4 {
19
+ font-weight: bold;
20
+ margin: 0;
21
+ }
22
+
23
+ h1 {
24
+ font-size: 16pt;
25
+ margin: 5mm 0;
26
+ }
27
+
28
+ h2 {
29
+ font-size: 14pt;
30
+ }
31
+
32
+ h3, h4 {
33
+ font-size: 9pt;
34
+ }
35
+
36
+
37
+ ol,
38
+ ul {
39
+ list-style: none;
40
+ margin: 0;
41
+ padding: 0;
42
+ }
43
+
44
+ li,
45
+ ul {
46
+ margin-bottom: 0.75em;
47
+ }
48
+
49
+ p {
50
+ margin: 0;
51
+ padding: 0;
52
+ }
53
+
54
+ p + p {
55
+ margin-top: 1.25em;
56
+ }
57
+
58
+ a {
59
+ border-bottom: 1px solid;
60
+ text-decoration: none;
61
+ }
62
+
63
+ /* Basic Table Styling */
64
+ table {
65
+ border-collapse: collapse;
66
+ border-spacing: 0;
67
+ page-break-inside: always;
68
+ border: 0;
69
+ margin: 0;
70
+ padding: 0;
71
+ }
72
+
73
+ th, td {
74
+ vertical-align: top;
75
+ text-align: left;
76
+ }
77
+
78
+ table.container {
79
+ width:100%;
80
+ border: 0;
81
+ }
82
+
83
+ tr.no-borders,
84
+ td.no-borders {
85
+ border: 0 !important;
86
+ border-top: 0 !important;
87
+ border-bottom: 0 !important;
88
+ padding: 0 !important;
89
+ width: auto;
90
+ }
91
+
92
+ div.bottom-spacer {
93
+ clear: both;
94
+ height: 8mm;
95
+ }
96
+
97
+ /* Header */
98
+ table.head {
99
+ margin-bottom: 12mm;
100
+ }
101
+
102
+ td.header img {
103
+ max-height: 3cm; /* may be overriden by the settings */
104
+ width: auto;
105
+ }
106
+
107
+ td.header {
108
+ font-size: 16pt;
109
+ font-weight: 700;
110
+ }
111
+
112
+ td.shop-info {
113
+ width: 40%;
114
+ }
115
+ .document-type-label {
116
+ text-transform: uppercase;
117
+ }
118
+
119
+ /* Recipient addressses & order data */
120
+ table.order-data-addresses {
121
+ width: 100%;
122
+ margin-bottom: 10mm;
123
+ }
124
+
125
+ td.order-data {
126
+ width: 40%;
127
+ }
128
+
129
+ .invoice .shipping-address {
130
+ width: 30%;
131
+ }
132
+
133
+ .packing-slip .billing-address {
134
+ width: 30%;
135
+ }
136
+
137
+ td.order-data table th {
138
+ font-weight: normal;
139
+ padding-right: 2mm;
140
+ }
141
+
142
+ /* Order details */
143
+ table.order-details {
144
+ width:100%;
145
+ margin-bottom: 0mm;
146
+ }
147
+
148
+ .quantity,
149
+ .price {
150
+ width: 20%;
151
+ }
152
+
153
+ .order-details tr {
154
+ page-break-inside: always;
155
+ page-break-after: auto;
156
+ }
157
+
158
+ .order-details td,
159
+ .order-details th {
160
+ border-bottom: 1px #ccc solid;
161
+ border-top: 1px #ccc solid;
162
+ padding: 0.375em;
163
+ }
164
+
165
+ .order-details th {
166
+ font-weight: bold;
167
+ text-align: left;
168
+ }
169
+
170
+ .order-details thead th {
171
+ color: white;
172
+ background-color: black;
173
+ border-color: black;
174
+ }
175
+
176
+ /* product bundles compatibility */
177
+ .order-details tr.bundled-item td.product {
178
+ padding-left: 5mm;
179
+ }
180
+
181
+ .order-details tr.product-bundle td,
182
+ .order-details tr.bundled-item td {
183
+ border: 0;
184
+ }
185
+
186
+ .order-details tr.bundled-item.hidden {
187
+ display: none;
188
+ }
189
+
190
+ /* item meta formatting for WC2.6 and older */
191
+ dl {
192
+ margin: 4px 0;
193
+ }
194
+
195
+ dt, dd, dd p {
196
+ display: inline;
197
+ font-size: 7pt;
198
+ line-height: 7pt;
199
+ }
200
+
201
+ dd {
202
+ margin-left: 5px;
203
+ }
204
+
205
+ dd:after {
206
+ content: "\A";
207
+ white-space: pre;
208
+ }
209
+ /* item-meta formatting for WC3.0+ */
210
+ .wc-item-meta {
211
+ margin: 4px 0;
212
+ font-size: 7pt;
213
+ line-height: 7pt;
214
+ }
215
+ .wc-item-meta p {
216
+ display: inline;
217
+ }
218
+ .wc-item-meta li {
219
+ margin: 0;
220
+ margin-left: 5px;
221
+ }
222
+
223
+ /* Notes & Totals */
224
+ .customer-notes {
225
+ margin-top: 5mm;
226
+ }
227
+
228
+ table.totals {
229
+ width: 100%;
230
+ margin-top: 5mm;
231
+ }
232
+
233
+ table.totals th,
234
+ table.totals td {
235
+ border: 0;
236
+ border-top: 1px solid #ccc;
237
+ border-bottom: 1px solid #ccc;
238
+ }
239
+
240
+ table.totals th.description,
241
+ table.totals td.price {
242
+ width: 50%;
243
+ }
244
+
245
+ table.totals tr.order_total td,
246
+ table.totals tr.order_total th {
247
+ border-top: 2px solid #000;
248
+ border-bottom: 2px solid #000;
249
+ font-weight: bold;
250
+ }
251
+
252
+ table.totals tr.payment_method {
253
+ display: none;
254
+ }
255
+
256
+ /* Footer Imprint */
257
+ #footer {
258
+ position: absolute;
259
+ bottom: -2cm;
260
+ left: 0;
261
+ right: 0;
262
+ height: 2cm; /* if you change the footer height, don't forget to change the bottom (=negative height) and the @page margin-bottom as well! */
263
+ text-align: center;
264
+ border-top: 0.1mm solid gray;
265
+ margin-bottom: 0;
266
+ padding-top: 2mm;
267
+ }
268
+
269
+ /* page numbers */
270
+ .pagenum:before {
271
+ content: counter(page);
272
+ }
273
+ .pagenum,.pagecount {
274
+ font-family: sans-serif;
275
  }
templates/Simple/template-functions.php CHANGED
@@ -1,7 +1,6 @@
1
- <?php
2
- /**
3
- * Use this file for all your template filters and actions.
4
- * Requires WooCommerce PDF Invoices & Packing Slips 1.4.13 or higher
5
- */
6
- if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly
7
-
1
+ <?php
2
+ /**
3
+ * Use this file for all your template filters and actions.
4
+ * Requires WooCommerce PDF Invoices & Packing Slips 1.4.13 or higher
5
+ */
6
+ if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly
 
woocommerce-pdf-invoices-packingslips.php CHANGED
@@ -3,14 +3,14 @@
3
  * Plugin Name: WooCommerce PDF Invoices & Packing Slips
4
  * Plugin URI: http://www.wpovernight.com
5
  * Description: Create, print & email PDF invoices & packing slips for WooCommerce orders.
6
- * Version: 2.4.10
7
  * Author: Ewout Fernhout
8
  * Author URI: http://www.wpovernight.com
9
  * License: GPLv2 or later
10
  * License URI: http://www.opensource.org/licenses/gpl-license.php
11
  * Text Domain: woocommerce-pdf-invoices-packing-slips
12
  * WC requires at least: 2.2.0
13
- * WC tested up to: 4.1.0
14
  */
15
 
16
  if ( ! defined( 'ABSPATH' ) ) {
@@ -105,39 +105,46 @@ class WPO_WCPDF {
105
  * Maintain backwards compatibility with old translation files
106
  * Uses old .mo file if it exists in any of the override locations
107
  */
108
- public function textdomain_fallback( $mofile, $textdomain ) {
109
  $plugin_domain = 'woocommerce-pdf-invoices-packing-slips';
110
  $old_domain = 'wpo_wcpdf';
111
 
112
- if ($textdomain == $old_domain) {
 
 
 
 
 
 
 
113
  $textdomain = $plugin_domain;
114
- $mofile = str_replace( "{$old_domain}-", "{$textdomain}-", $mofile ); // with trailing dash to target file and not folder
115
  }
116
 
117
  if ( $textdomain === $plugin_domain ) {
118
- $old_mofile = str_replace( "{$textdomain}-", "{$old_domain}-", $mofile ); // with trailing dash to target file and not folder
119
- if ( file_exists( $old_mofile ) ) {
120
  // we have an old override - use it
121
- return $old_mofile;
122
  }
123
 
124
  // prevent loading outdated language packs
125
- $pofile = str_replace('.mo', '.po', $mofile);
126
- if ( file_exists( $pofile ) ) {
127
  // load po file
128
- $podata = file_get_contents($pofile);
129
  // set revision date threshold
130
  $block_before = strtotime( '2017-05-15' );
131
  // read revision date
132
- preg_match('~PO-Revision-Date: (.*?)\\\n~s',$podata,$matches);
133
- if (isset($matches[1])) {
134
  $revision_date = $matches[1];
135
- if ( $revision_timestamp = strtotime($revision_date) ) {
136
  // check if revision is before threshold date
137
  if ( $revision_timestamp < $block_before ) {
138
  // try bundled
139
- $bundled_file = $this->plugin_path() . '/languages/'. basename( $mofile );
140
- if (file_exists($bundled_file)) {
141
  return $bundled_file;
142
  } else {
143
  return '';
@@ -151,7 +158,7 @@ class WPO_WCPDF {
151
  }
152
  }
153
 
154
- return $mofile;
155
  }
156
 
157
  /**
3
  * Plugin Name: WooCommerce PDF Invoices & Packing Slips
4
  * Plugin URI: http://www.wpovernight.com
5
  * Description: Create, print & email PDF invoices & packing slips for WooCommerce orders.
6
+ * Version: 2.5.0
7
  * Author: Ewout Fernhout
8
  * Author URI: http://www.wpovernight.com
9
  * License: GPLv2 or later
10
  * License URI: http://www.opensource.org/licenses/gpl-license.php
11
  * Text Domain: woocommerce-pdf-invoices-packing-slips
12
  * WC requires at least: 2.2.0
13
+ * WC tested up to: 4.2.0
14
  */
15
 
16
  if ( ! defined( 'ABSPATH' ) ) {
105
  * Maintain backwards compatibility with old translation files
106
  * Uses old .mo file if it exists in any of the override locations
107
  */
108
+ public function textdomain_fallback( $mo, $textdomain ) {
109
  $plugin_domain = 'woocommerce-pdf-invoices-packing-slips';
110
  $old_domain = 'wpo_wcpdf';
111
 
112
+ if ( $textdomain !== $plugin_domain && $textdomain !== $old_domain ) {
113
+ return $mo;
114
+ }
115
+
116
+ $mopath = trailingslashit( dirname( $mo ) );
117
+ $mofile = basename( $mo );
118
+
119
+ if ( $textdomain == $old_domain ) {
120
  $textdomain = $plugin_domain;
121
+ $mofile = str_replace( $old_domain, $textdomain, $mofile );
122
  }
123
 
124
  if ( $textdomain === $plugin_domain ) {
125
+ $old_mofile = str_replace( $textdomain, $old_domain, $mofile );
126
+ if ( file_exists( $mopath.$old_mofile ) ) {
127
  // we have an old override - use it
128
+ return $mopath.$old_mofile;
129
  }
130
 
131
  // prevent loading outdated language packs
132
+ $pofile = str_replace( '.mo', '.po', $mofile );
133
+ if ( file_exists( $mopath.$pofile ) ) {
134
  // load po file
135
+ $podata = file_get_contents( $mopath.$pofile );
136
  // set revision date threshold
137
  $block_before = strtotime( '2017-05-15' );
138
  // read revision date
139
+ preg_match( '~PO-Revision-Date: (.*?)\\\n~s', $podata, $matches );
140
+ if ( isset( $matches[1] ) ) {
141
  $revision_date = $matches[1];
142
+ if ( $revision_timestamp = strtotime( $revision_date ) ) {
143
  // check if revision is before threshold date
144
  if ( $revision_timestamp < $block_before ) {
145
  // try bundled
146
+ $bundled_file = $this->plugin_path() . '/languages/'. $mofile;
147
+ if ( file_exists( $bundled_file ) ) {
148
  return $bundled_file;
149
  } else {
150
  return '';
158
  }
159
  }
160
 
161
+ return $mopath.$mofile;
162
  }
163
 
164
  /**