From b7ab761a25a8c0879d0d466a508ee15e79d21695 Mon Sep 17 00:00:00 2001 From: Almira Krdzic Date: Wed, 17 Oct 2018 19:38:41 +0200 Subject: [PATCH 1/4] Handle bundle pricing on separate page --- .../class-wiaas-admin-package-pricing.php | 18 +- .../pricing/views/html-package-pricing.php | 167 +++++++++++------- 2 files changed, 116 insertions(+), 69 deletions(-) diff --git a/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php b/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php index f09555b..b1cee72 100644 --- a/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php +++ b/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php @@ -11,6 +11,8 @@ class Wiaas_Admin_Package_Pricing { public static function init() { + add_action( 'admin_menu', array(__CLASS__, 'add_package_pricing_editor_page') ); + add_action( 'woocommerce_product_data_tabs', array( __CLASS__, 'package_data_tabs' ) ); add_action( 'woocommerce_product_data_panels', array( __CLASS__, 'package_data_panel' ) ); @@ -19,6 +21,18 @@ class Wiaas_Admin_Package_Pricing { add_action( 'woocommerce_process_product_meta', array( __CLASS__, 'process_meta_box' ), 1, 2 ); } + public static function add_package_pricing_editor_page() { + + add_submenu_page( + 'edit.php?post_type=product', + __( 'Products', 'wiaas' ), + null, + 'create_products', + 'wiaas-package_price_editor', + array(__CLASS__, 'package_data_panel') + ); + } + /** * Creates and renders new empty package pricing rule */ @@ -54,8 +68,8 @@ class Wiaas_Admin_Package_Pricing { */ public static function package_data_panel() { - global $post; - $package = wc_get_product( $post->ID ); + $package_id = absint($_GET['id']); + $package = wc_get_product( $package_id ); $pricing_rules = Wiaas_Package_Pricing::get_package_prices($package); $commission = Wiaas_Package_Pricing::get_package_pricing_commission($package); $max_cost_margin = Wiaas_Package_Pricing::get_package_max_cost_margin($package); diff --git a/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing.php b/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing.php index ac092ff..e70628c 100644 --- a/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing.php +++ b/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing.php @@ -143,81 +143,114 @@ if ( ! defined( 'ABSPATH' ) ) { } }); + -
- '_wiaas_max_cost_margin', - 'name' => 'wiaas_max_cost_margin', - 'value' => $max_cost_margin, - 'label' => __( 'Max cost margin:', 'wiaas' ), - 'type' => 'number', - ) - ); - ?> -
+
+
+
-
- '_wiaas_price_commision', - 'name' => 'wiaas_pricing_rules_commision', - 'value' => $commission, - 'label' => __( 'Commision (Percent):', 'wiaas' ), - 'type' => 'number', - ) - ); - ?> -
+
-
-
- $pay_type) { - if (!isset($pricing_rule_sets[$name])) { - $has_available_pay_types = true; - break; - } - } +
+
+
- $class = $has_available_pay_types ? '' : 'wiaas_hidden'; +
+

Test

+
- ?> -
- - +
+
+
-
- -
+
+
+
+
+
+
+ '_wiaas_max_cost_margin', + 'name' => 'wiaas_max_cost_margin', + 'value' => $max_cost_margin, + 'label' => __( 'Max cost margin:', 'wiaas' ), + 'type' => 'number', + ) + ); + ?> +
+ +
+ '_wiaas_price_commision', + 'name' => 'wiaas_pricing_rules_commision', + 'value' => $commission, + 'label' => __( 'Commision (Percent):', 'wiaas' ), + 'type' => 'number', + ) + ); + ?> +
+ +
+
+ $pay_type) { + if (!isset($pricing_rule_sets[$name])) { + $has_available_pay_types = true; + break; + } + } + + $class = $has_available_pay_types ? '' : 'wiaas_hidden'; + + ?> +
+ + +
+ +
+ +
+ +
+
+
+
+
+
+
From 6d65a5f30cbab5dcac8b905429efcfe2ebf3d018 Mon Sep 17 00:00:00 2001 From: Almira Krdzic Date: Thu, 18 Oct 2018 09:57:38 +0200 Subject: [PATCH 2/4] handle bundle product prices editor and prices summary --- .../{package.css => wiaas-admin-package.css} | 24 +- .../js/wiaas-admin-package-edit-prices.js | 150 ++++++++++ .../wiaas/assets/js/wiaas-admin-package.js | 11 + .../admin/class-wiaas-admin-package.php | 21 ++ .../class-wiaas-admin-package-pricing.php | 138 +++++++-- .../views/html-package-pricing-page.php | 277 ++++++++++++++++++ .../views/html-package-pricing-rules-list.php | 2 +- .../pricing/views/html-package-pricing.php | 256 ---------------- .../pricing/views/html-product-pricing.php | 23 -- .../class-wiaas-template-products.php | 16 - .../class-wiaas-access-management.php | 3 +- .../wiaas/includes/class-wiaas-admin.php | 5 +- .../wiaas/includes/class-wiaas-product.php | 12 +- .../package/class-wiaas-package-status.php | 4 +- .../pricing/class-wiaas-package-pricing.php | 27 +- .../pricing/wiaas-pricing-functions.php | 76 +++++ .../product/class-wiaas-product-category.php | 24 +- frontend/src/helpers/PackageHelper.js | 2 +- 18 files changed, 702 insertions(+), 369 deletions(-) rename backend/app/plugins/wiaas/assets/css/{package.css => wiaas-admin-package.css} (87%) create mode 100644 backend/app/plugins/wiaas/assets/js/wiaas-admin-package-edit-prices.js create mode 100644 backend/app/plugins/wiaas/assets/js/wiaas-admin-package.js create mode 100644 backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing-page.php delete mode 100644 backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing.php diff --git a/backend/app/plugins/wiaas/assets/css/package.css b/backend/app/plugins/wiaas/assets/css/wiaas-admin-package.css similarity index 87% rename from backend/app/plugins/wiaas/assets/css/package.css rename to backend/app/plugins/wiaas/assets/css/wiaas-admin-package.css index 3cb3f82..811509b 100644 --- a/backend/app/plugins/wiaas/assets/css/package.css +++ b/backend/app/plugins/wiaas/assets/css/wiaas-admin-package.css @@ -30,19 +30,9 @@ } #wiaas_package_pricing_rules > .wiaas-pricing-rule { - border-color:#dfdfdf; - border-width:1px; - border-style:solid; - -moz-border-radius:3px; - -khtml-border-radius:3px; - -webkit-border-radius:3px; - border-radius:3px; - padding: 0; - border-style:solid; - border-spacing:0; - background-color:#F9F9F9; - margin-bottom: 12px; - margin-left: 12px; + border:1px #dfdfdf solid; + background-color:#fff; + width: 95%; } #wiaas_package_pricing_rules > .wiaas-pricing-rule .section { @@ -133,4 +123,12 @@ #adminmenu #toplevel_page_wiaas-cl-packages div.wp-menu-image::before { font-family: WooCommerce!important; content: '\e006'; +} + +.wiaas-package-error { + color: #a00 !important; +} + +table.wp-list-table .column-price { + width: auto !important; } \ No newline at end of file diff --git a/backend/app/plugins/wiaas/assets/js/wiaas-admin-package-edit-prices.js b/backend/app/plugins/wiaas/assets/js/wiaas-admin-package-edit-prices.js new file mode 100644 index 0000000..0482087 --- /dev/null +++ b/backend/app/plugins/wiaas/assets/js/wiaas-admin-package-edit-prices.js @@ -0,0 +1,150 @@ +jQuery(document).ready(function ($) { + $("#wiaas-add-pricing").click(function (event) { + event.preventDefault(); + + var pay_type = $('#wiaas_pay_types').val(); + + if (! pay_type) { + return; + } + + var set_index = $("#wiaas_package_pricing_rules").data('setindex') + 1; + $("#wiaas_package_pricing_rules").data('setindex', set_index); + + var data = { + 'pay_type': pay_type, + action: 'create_empty_pricing_rule' + }; + + $.post(ajaxurl, data, function (response) { + $('#wiaas_package_pricing_rules').append(response); + + $(`#wiaas_pay_type_${pay_type}`).prop( 'disabled', true ); + + $('#wiaas_pay_types').val('0'); + + }); + }); + + //Remove Pricing Type + $('#wiaas_package_pricing_rules').delegate('.delete_wiaas_pricing_rule', 'click', function (event) { + event.preventDefault(); + if (confirm('Are you sure you would like to remove this pay type?')) { + var name = $(this).data('name'); + $('#wiaas-pricing-rule-' + name).slideUp().remove(); + + // append new option to controls + $(`#wiaas_pay_type_${name}`).prop( 'disabled', false ); + } + }); + + $('#wiaas_package_pricing_rules').delegate('.wiaas_minimal_services_price', 'change', function (event) { + event.preventDefault(); + + var minimal_services_price = parseFloat($(this).val()) || 0; + var principal_amount = 0; + var name = $(this).data('name'); + + var principal_amount_input = $(`#wiaas_principal_amount_${name}`).first(); + if (principal_amount_input) { + principal_amount = parseFloat(principal_amount_input.val() / principal_amount_input.data('period')) || 0; + } + $(`#wiaas_minimal_recurrent_price_${name}`).text((minimal_services_price + principal_amount).toFixed(2)); + + var services_contract_period = $(this).data('period'); + if (services_contract_period > 0) { + var final_services_price = minimal_services_price * services_contract_period; + $(`#wiaas_minimal_services_price_${name}_final`).text(final_services_price.toFixed(2)); + } + + }); + + $('#wiaas_package_pricing_rules').delegate('.wiaas_principal_amount', 'change', function (event) { + event.preventDefault(); + + var value = parseFloat($(this).val()); + var period = parseFloat($(this).data('period')); + var interestRate = 0.58; + + + var principal_amount = wiaasCalculateFinancing(interestRate, period, value); + var minimal_services_price = 0; + var name = $(this).data('name'); + + var minimal_services_price_input = $(`#wiaas_minimal_services_price_${name}`).first(); + if (minimal_services_price_input) { + minimal_services_price = parseFloat(minimal_services_price_input.val()) || 0; + } + + $(`#wiaas_minimal_recurrent_price_${name}`).text((minimal_services_price + principal_amount).toFixed(0)); + $(`#wiaas_minimal_recurrent_package_price_${name}`).text(principal_amount.toFixed(0)); + }); + + $('#wiaas_package_pricing_editor').delegate('#wiaas_pricing_rules_commision', 'change', function(event) { + event.preventDefault(); + + var value = parseInt($(this).val()); + + $('#wiaas_pricing_rules_commission_details').text('Commercial lead: ' + (100 - value) + ' %'); + }); + + $('#wiaas_package_pricing_editor').delegate('#wiaas_pricing_rules_max_cost_margin', 'change', function(event) { + event.preventDefault(); + + var value = parseFloat($(this).val()); + var total = parseFloat($(this).data('total')); + + if (value > 0 && value < total) { + $('#wiaas_pricing_rules_max_cost_margin_error').show(); + } else { + $('#wiaas_pricing_rules_max_cost_margin_error').hide(); + } + }); + + /** + * Copy of Excel's PMT function. + * Credit: http://stackoverflow.com/questions/2094967/excel-pmt-function-in-js + * + * @param ratePerPeriod The interest rate for the loan. + * @param numberOfPayments The total number of payments for the loan in months. + * @param presentValue The present value, or the total amount that a series of future payments is worth now; + * Also known as the principal. + * @param futureValue The future value, or a cash balance you want to attain after the last payment is made. + * If fv is omitted, it is assumed to be 0 (zero), that is, the future value of a loan is 0. + * @param type Optional, defaults to 0. The number 0 (zero) or 1 and indicates when payments are due. + * 0 = At the end of period + * 1 = At the beginning of the period + * @returns {number} + */ + function wiaasCalculateFinancing(ratePerPeriod, numberOfPayments, presentValue, futureValue = 0, type = 0) { + /*var q = 0; + var c = 0; + const monthlyRatePerPeriod = ratePerPeriod / 12; + + if (monthlyRatePerPeriod !== 0.0) { + // Interest rate exists + q = Math.pow(1 + monthlyRatePerPeriod, numberOfPayments); + c = (monthlyRatePerPeriod * (futureValue + (q * presentValue))) / ((-1 + q) * (1 + monthlyRatePerPeriod * (type))); + return c.toFixed(2); + + } else if (numberOfPayments !== 0.0) { + // No interest rate, but number of payments exists + return -(futureValue + presentValue) / numberOfPayments; + } + + return 0;*/ + const rates = { + 24 : 4.282, + 30 : 3.451, + 36 : 2.896, + 42 : 2.500, + 48 : 2.223, + 54 : 2.025, + 60 : 1.834 + }; + + const interest = rates[numberOfPayments] || 10; + + return presentValue * (interest / 100); + } +}); \ No newline at end of file diff --git a/backend/app/plugins/wiaas/assets/js/wiaas-admin-package.js b/backend/app/plugins/wiaas/assets/js/wiaas-admin-package.js new file mode 100644 index 0000000..20afebd --- /dev/null +++ b/backend/app/plugins/wiaas/assets/js/wiaas-admin-package.js @@ -0,0 +1,11 @@ +jQuery(document).ready(function($) { + if ($('#product-type').val() === 'simple') { + $('#general_product_data').find('.pricing').show(); + } else { + $('#general_product_data').find('.pricing').hide(); + } + + $('#general_product_data').find('.pricing').addClass('hide_if_wiaastemplate hide_if_bundle'); + $('#general_product_data').find('.pricing').removeClass('show_if_bundle show_if_wiaastemplate'); + +}); \ No newline at end of file diff --git a/backend/app/plugins/wiaas/includes/admin/class-wiaas-admin-package.php b/backend/app/plugins/wiaas/includes/admin/class-wiaas-admin-package.php index 960555e..2f5a760 100644 --- a/backend/app/plugins/wiaas/includes/admin/class-wiaas-admin-package.php +++ b/backend/app/plugins/wiaas/includes/admin/class-wiaas-admin-package.php @@ -10,6 +10,27 @@ class Wiaas_Admin_Package { require_once dirname( __FILE__ ) . '/package/class-wiaas-admin-linked-packages.php'; require_once dirname( __FILE__ ) . '/package/class-wiaas-admin-package-types.php'; + + add_action( 'woocommerce_product_data_tabs', array( __CLASS__, 'package_data_tabs' ), 1 ); + } + + /** + * Hide default WC_Product data panels. + * + * @param array $tabs + * + * @return mixed + */ + public static function package_data_tabs($tabs) { + + $tabs['general']['class'] = array( 'show_if_simple', 'show_if_bundle'); + + unset($tabs['attribute']); + unset($tabs['variations']); + unset($tabs['advanced']); + unset($tabs['shipping']); + + return $tabs; } } diff --git a/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php b/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php index b1cee72..3c0984d 100644 --- a/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php +++ b/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php @@ -13,23 +13,60 @@ class Wiaas_Admin_Package_Pricing { add_action( 'admin_menu', array(__CLASS__, 'add_package_pricing_editor_page') ); - add_action( 'woocommerce_product_data_tabs', array( __CLASS__, 'package_data_tabs' ) ); - add_action( 'woocommerce_product_data_panels', array( __CLASS__, 'package_data_panel' ) ); - add_action( 'wp_ajax_create_empty_pricing_rule', array(__CLASS__, 'create_empty_pricing_rule') ); - add_action( 'woocommerce_process_product_meta', array( __CLASS__, 'process_meta_box' ), 1, 2 ); + add_action('woocommerce_product_options_general_product_data', array(__CLASS__, 'render_edit_prices_link')); + + add_filter('woocommerce_bundle_price_html', array( __CLASS__, 'get_package_price_html' ), 10, 2); + } + + public static function get_package_price_html($price_html, $package) { + $bundled_items = $package->get_bundled_items(); + + $recurring_price = 0; + + foreach ($bundled_items as $bundled_item) { + $product = $bundled_item->product; + $product_price = Wiaas_Product_Pricing::get_product_price($product); + if ($product_price['is_recurring']) { + $recurring_price += $product_price['price'] * $bundled_item->get_quantity(); + } + } + + $edit_link = admin_url( 'edit.php?post_type=product&page=wiaas-package_price_editor&id=' . absint( $package->get_id() ) ); + + $price_html = 'Fixed: ' . $price_html . ' and ' . $recurring_price . ' / month' . + '
Edit price'; + + return $price_html; + } + + public static function render_edit_prices_link() { + global $post; + + $edit_link = admin_url( 'edit.php?post_type=product&page=wiaas-package_price_editor&id=' . absint( $post->ID ) ); + + ?> + + __( 'Pricing', 'wiaas' ), - 'target' => 'wiaas_package_price', - 'class' => array( 'show_if_bundle', 'bundled_package_tab' ), - 'priority' => 50 - ); - - return $tabs; - } - /** * Renderes wiaas pricing tab content for package */ - public static function package_data_panel() { + public static function package_pricing_editor() { + + $plugin_url = untrailingslashit( plugins_url( '/', WIAAS_FILE ) ); + wp_enqueue_script('admin_package_edit_prices', $plugin_url . '/assets/js/wiaas-admin-package-edit-prices.js'); $package_id = absint($_GET['id']); $package = wc_get_product( $package_id ); + + if (empty($package) || $package->get_type() !== 'bundle') { + return; + } + + // save prices + if (! empty($_POST['wiaas_save_package_prices_nonce']) && + wp_verify_nonce($_POST['wiaas_save_package_prices_nonce'], 'wiaas_save_package_prices')) { + self::_save_posted_package_prices($package_id); + } + $pricing_rules = Wiaas_Package_Pricing::get_package_prices($package); $commission = Wiaas_Package_Pricing::get_package_pricing_commission($package); $max_cost_margin = Wiaas_Package_Pricing::get_package_max_cost_margin($package); + // collect package bundle items pricing info to display + $bundled_items = $package->get_bundled_items(); + $bundled_items_per_category = array(); + + foreach ($bundled_items as $bundled_item) { + $product = $bundled_item->product; + $product_cat = Wiaas_Product_Category::get_category($product); + + if ($product_cat === 'hardware' || $product_cat === 'software') { + $product_cat = 'product'; + } + + $bundled_items_per_category[$product_cat] ?: array( ); + + $bundled_items_per_category[$product_cat][] = $bundled_item; + + + } + include 'views/html-package-pricing.php'; } + + // PRIVATE HELPERS + /** - * Saves posted package pricing rules - * @param $post_id - * @param $post + * Save posted package pricing information + * + * @param int $package_id */ - public function process_meta_box( $post_id, $post ) { + private static function _save_posted_package_prices($package_id) { + $commission = wp_unslash($_POST['wiaas_pricing_rules_commision']); + $max_cost_margin = wp_unslash($_POST['wiaas_max_cost_margin']); + $pricing_rules = array(); + + $posted_pricing_rules = isset($_POST['wiaas_pricing_rules']) ? wp_unslash($_POST['wiaas_pricing_rules']) : array(); + + foreach ($posted_pricing_rules as $rule_type => $posted_prices) { + + $posted_prices = wp_unslash($posted_prices); + $prices = array(); + + foreach ($posted_prices as $posted_price_type => $posted_price) { + $prices[sanitize_key($posted_price_type)] = wp_unslash($posted_price); + } + + $pricing_rules[sanitize_key($rule_type)] = $prices; + } + Wiaas_Package_Pricing::set_package_prices( - wc_get_product( $post_id ), - $_POST['wiaas_pricing_rules'], - $_POST['wiaas_pricing_rules_commision'], - $_POST['wiaas_max_cost_margin']); + wc_get_product( $package_id ), + $pricing_rules, + $commission, + $max_cost_margin); } } diff --git a/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing-page.php b/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing-page.php new file mode 100644 index 0000000..8802d92 --- /dev/null +++ b/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing-page.php @@ -0,0 +1,277 @@ + + + + +
+ +

+ get_title(), 'wiaas'); + + $country = Wiaas_Countries::get_package_country($package); + + if (! empty($country)) { + + esc_html_e(' (sold in ' . $country['name'] . ')', 'wiaas'); + } + ?> +

+ +
+ +
+
+ +
+ +
+ +
+ + + + + $items) { + + ?> + + + + + product; + + $product_price = Wiaas_Product_Pricing::get_product_price($product); + + $total_cost = Wiaas_Pricing::get_product_total_cost($product); + + ?> + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + + +
+ + get_quantity(), 'wiaas') ?> + x + get_title(), 'wiaas') ?> + + + get_quantity(), + 'wiaas') + ?> + + + + + +
+ + '; + + esc_html_e('Recurring services: ' . $recurring_services_cost . ' / month ', 'wiaas'); + } + + if ($cat === 'installation') { + + $installation_cost = wiaas_get_package_installation_procurement_cost($package); + + esc_html_e('Installation: ' . $installation_cost, 'wiaas'); + } + ?> + +
+

TOTAL COST :

+
+ Fixed: +
+ Recurring: / month +
+ +
+
+
+ +
+ +
+
+ +

+ +
+ + + + +
+ + + +

get_id()) !== Wiaas_Package_Status::INVALID_MARGIN) echo 'style="display: none;"' ?> + class="wiaas-package-error" + >The total costs are greater than the package max margin!

+ +
+ +
+ + +

+ +

+
+ +
+ +
+ + + + + +
+
+ +
+ + + +
+ + + + +
+
+
+
+
+
+
diff --git a/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing-rules-list.php b/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing-rules-list.php index 976972c..24d04dc 100644 --- a/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing-rules-list.php +++ b/backend/app/plugins/wiaas/includes/admin/pricing/views/html-package-pricing-rules-list.php @@ -8,7 +8,7 @@ $available_pay_types = Wiaas_Package_Pricing::get_available_pay_types(); foreach ( $pricing_rules as $name => $pricing_rule ) { $pay_type = $available_pay_types[$name]; ?> -
+

- -
- -
- -
-
-
- -
- -
-
-
- -
-

Test

-
- -
-
-
-
- -
- -
-
-
-
-
- '_wiaas_max_cost_margin', - 'name' => 'wiaas_max_cost_margin', - 'value' => $max_cost_margin, - 'label' => __( 'Max cost margin:', 'wiaas' ), - 'type' => 'number', - ) - ); - ?> -
- -
- '_wiaas_price_commision', - 'name' => 'wiaas_pricing_rules_commision', - 'value' => $commission, - 'label' => __( 'Commision (Percent):', 'wiaas' ), - 'type' => 'number', - ) - ); - ?> -
- -
-
- $pay_type) { - if (!isset($pricing_rule_sets[$name])) { - $has_available_pay_types = true; - break; - } - } - - $class = $has_available_pay_types ? '' : 'wiaas_hidden'; - - ?> -
- - -
- -
- -
- -
-
-
-
-
-
-
-
-
-
diff --git a/backend/app/plugins/wiaas/includes/admin/pricing/views/html-product-pricing.php b/backend/app/plugins/wiaas/includes/admin/pricing/views/html-product-pricing.php index f852b5f..3412387 100644 --- a/backend/app/plugins/wiaas/includes/admin/pricing/views/html-product-pricing.php +++ b/backend/app/plugins/wiaas/includes/admin/pricing/views/html-product-pricing.php @@ -4,29 +4,6 @@ if ( ! defined( 'ABSPATH' ) ) { } ?> - - get_type() !== 'bundle' || - $product->get_status() !== 'publish') { + $product->get_status() !== 'publish' || + empty(Wiaas_Package_Pricing::get_package_prices($product))) { $access_group = Groups_Group::read_by_name('admin'); } else { diff --git a/backend/app/plugins/wiaas/includes/class-wiaas-admin.php b/backend/app/plugins/wiaas/includes/class-wiaas-admin.php index 096f2e4..28b321d 100644 --- a/backend/app/plugins/wiaas/includes/class-wiaas-admin.php +++ b/backend/app/plugins/wiaas/includes/class-wiaas-admin.php @@ -30,7 +30,10 @@ class Wiaas_Admin { $plugin_url = untrailingslashit( plugins_url( '/', WIAAS_FILE ) ); wp_enqueue_style( 'wiaas_admin_menu', $plugin_url . '/assets/css/menu.css' ); - wp_enqueue_style( 'wiaas_admin_packages', $plugin_url . '/assets/css/package.css' ); + + wp_enqueue_style( 'wiaas_admin_packages', $plugin_url . '/assets/css/wiaas-admin-package.css' ); + + wp_enqueue_script( 'wiaas_admin_packages', $plugin_url . '/assets/js/wiaas-admin-package.js' ); } } diff --git a/backend/app/plugins/wiaas/includes/class-wiaas-product.php b/backend/app/plugins/wiaas/includes/class-wiaas-product.php index 9bf1fc9..1360443 100644 --- a/backend/app/plugins/wiaas/includes/class-wiaas-product.php +++ b/backend/app/plugins/wiaas/includes/class-wiaas-product.php @@ -6,17 +6,19 @@ class Wiaas_Product { require_once dirname( __FILE__ ) . '/product/class-wiaas-product-category.php'; require_once dirname( __FILE__ ) . '/product/class-wiaas-product-supplier.php'; - add_filter('woocommerce_register_post_type_product', array(__CLASS__, 'define_product_capabilities')); + add_filter('woocommerce_register_post_type_product', array(__CLASS__, 'manage_product_settings')); } /** - * Define capabilities for editing products so we can easily control read/edit/create access for them + * Update product type settins before it is created: + * - Define capabilities for editing products so we can easily control read/edit/create access for them + * - Declare fields supported by product * * @param $args * * @return mixed */ - public static function define_product_capabilities($args) { + public static function manage_product_settings($args) { $args['capabilities'] = array( 'edit_post' => 'edit_product', @@ -28,6 +30,10 @@ class Wiaas_Product { 'read_private_posts' => 'read_private_products', 'create_posts' => 'create_products', // use `create_products` instead of default `edit_products` ); + + $args['supports'] = array( 'title', 'thumbnail' ); + + return $args; } } diff --git a/backend/app/plugins/wiaas/includes/package/class-wiaas-package-status.php b/backend/app/plugins/wiaas/includes/package/class-wiaas-package-status.php index 8a7cfd5..29016f2 100644 --- a/backend/app/plugins/wiaas/includes/package/class-wiaas-package-status.php +++ b/backend/app/plugins/wiaas/includes/package/class-wiaas-package-status.php @@ -56,7 +56,9 @@ class Wiaas_Package_Status { $statuses = [self::AVAILABLE, self::INVALID_MARGIN, self::INVALID_TEMPLATE]; foreach ($statuses as $status) { - wp_insert_term($status, 'package_status'); + if (! has_term($status)) { + wp_insert_term($status, 'package_status'); + } } } diff --git a/backend/app/plugins/wiaas/includes/pricing/class-wiaas-package-pricing.php b/backend/app/plugins/wiaas/includes/pricing/class-wiaas-package-pricing.php index 7c9fd30..b681f7f 100644 --- a/backend/app/plugins/wiaas/includes/pricing/class-wiaas-package-pricing.php +++ b/backend/app/plugins/wiaas/includes/pricing/class-wiaas-package-pricing.php @@ -49,30 +49,10 @@ class Wiaas_Package_Pricing { ); public static function init() { - - add_filter('woocommerce_bundle_price_html', array( __CLASS__, 'get_package_price_html' ), 10, 2); add_action('woocommerce_update_product', array(__CLASS__, 'on_product_update' ), 10, 1 ); } - public static function get_package_price_html($price_html, $package) { - $bundled_items = $package->get_bundled_items(); - - $recurring_price = 0; - - foreach ($bundled_items as $bundled_item) { - $product = $bundled_item->product; - $product_price = Wiaas_Product_Pricing::get_product_price($product); - if ($product_price['is_recurring']) { - $recurring_price += $product_price['price'] * $bundled_item->get_quantity(); - } - } - - $price_html = 'Fixed: ' . $price_html . ' and ' . $recurring_price . ' / month'; - - return $price_html; - } - /** * Get configuration for available payment types * @return array @@ -121,6 +101,8 @@ class Wiaas_Package_Pricing { $package->delete_meta_data( '_wiaas_pricing_rules' ); } $package->save_meta_data(); + + self::_validate_package($package); } /** @@ -147,6 +129,11 @@ class Wiaas_Package_Pricing { private static function _get_package_prices($package) { $pricing_rules = $package->get_meta( '_wiaas_pricing_rules' ); + + if (empty($pricing_rules)) { + return null; + } + $commision = self::_get_package_pricing_commision($package); $prices = array(); diff --git a/backend/app/plugins/wiaas/includes/pricing/wiaas-pricing-functions.php b/backend/app/plugins/wiaas/includes/pricing/wiaas-pricing-functions.php index 1a2baef..a9ba343 100644 --- a/backend/app/plugins/wiaas/includes/pricing/wiaas-pricing-functions.php +++ b/backend/app/plugins/wiaas/includes/pricing/wiaas-pricing-functions.php @@ -48,4 +48,80 @@ function wiaas_get_recurrent_price_mortage($principal_amount, $pay_period, $marg function wiaas_get_price_margin($fixed_price, $principal_amount, $total_cost) { $total_gain = $fixed_price + $principal_amount; return $total_gain - $total_cost; +} + +function wiaas_get_package_hardware_procurement_cost($package) { + $bundled_items = $package->get_bundled_items(); + $total_cost = 0; + + foreach ($bundled_items as $bundled_item) { + $product = $bundled_item->product; + + if (Wiaas_Product_Category::get_category($product) === 'hardware') { + $total_cost += Wiaas_Pricing::get_product_total_cost($product) * $bundled_item->get_quantity(); + } + } + + return $total_cost; +} + +function wiaas_get_package_software_procurement_cost($package) { + $bundled_items = $package->get_bundled_items(); + $total_cost = 0; + + foreach ($bundled_items as $bundled_item) { + if (Wiaas_Product_Category::is_hardware($bundled_item->product)) { + $total_cost += Wiaas_Pricing::get_product_total_cost($bundled_item->product) * $bundled_item->get_quantity(); + } + } + + return $total_cost; +} + +function wiaas_get_package_installation_procurement_cost($package) { + $bundled_items = $package->get_bundled_items(); + $total_cost = 0; + + foreach ($bundled_items as $bundled_item) { + if (Wiaas_Product_Category::is_installation($bundled_item->product)) { + $installation_cost = Wiaas_Pricing::get_product_total_cost($bundled_item->product); + $total_cost = $total_cost > $installation_cost ? $total_cost : $installation_cost; + } + } + + return $total_cost; +} + +function wiaas_get_package_one_time_services_procurement_cost($package) { + $bundled_items = $package->get_bundled_items(); + $total_cost = 0; + + foreach ($bundled_items as $bundled_item) { + if (Wiaas_Product_Category::is_service($bundled_item->product)) { + + $price = Wiaas_Product_Pricing::get_product_price($bundled_item->product); + if (! $price['is_recurring']) { + $total_cost += Wiaas_Pricing::get_product_total_cost($bundled_item->product) * $bundled_item->get_quantity(); + } + } + } + + return $total_cost; +} + +function wiaas_get_package_recurring_services_procurement_cost($package) { + $bundled_items = $package->get_bundled_items(); + $total_cost = 0; + + foreach ($bundled_items as $bundled_item) { + if (Wiaas_Product_Category::is_service($bundled_item->product)) { + + $price = Wiaas_Product_Pricing::get_product_price($bundled_item->product); + if ( $price['is_recurring']) { + $total_cost += $price['price'] * $bundled_item->get_quantity(); + } + } + } + + return $total_cost; } \ No newline at end of file diff --git a/backend/app/plugins/wiaas/includes/product/class-wiaas-product-category.php b/backend/app/plugins/wiaas/includes/product/class-wiaas-product-category.php index fe7e70e..4e981c3 100644 --- a/backend/app/plugins/wiaas/includes/product/class-wiaas-product-category.php +++ b/backend/app/plugins/wiaas/includes/product/class-wiaas-product-category.php @@ -46,7 +46,9 @@ class Wiaas_Product_Category { public static function register_product_categories() { foreach (self::$available_product_categories as $key => $available_product_category) { - wp_insert_term($key, 'product_cat'); + if (! has_term_meta($key)) { + wp_insert_term($key, 'product_cat'); + } } } @@ -83,6 +85,26 @@ class Wiaas_Product_Category { return self::_get_product_category_type($product) === 'service'; } + /** + * Determines if provided product is hardware + * @param $product + * + * @return bool + */ + public static function is_hardware($product) { + return self::_get_product_category_type($product) === 'hardware'; + } + + /** + * Determines if provided product is software + * @param $product + * + * @return bool + */ + public static function is_software($product) { + return self::_get_product_category_type($product) === 'software'; + } + // PRIVATE diff --git a/frontend/src/helpers/PackageHelper.js b/frontend/src/helpers/PackageHelper.js index c59d6c6..ba3fde4 100644 --- a/frontend/src/helpers/PackageHelper.js +++ b/frontend/src/helpers/PackageHelper.js @@ -54,7 +54,7 @@ export const fromWCPackage = wcPackage => { document.icon = getDocumentIcon(document.extension); return document; }) : [], - shortDescription: wcPackage.description, + shortDescription: wcPackage['short_description'], prices: extractPrices(wcPackage.id, wcPackage.prices || []), groups: extractGroups(wcPackage.groups || {}), additionalPackages: wcPackage['additional_packages'] ? wcPackage['additional_packages'].map(additionalPackage =>({ From 6b0dd0b5a91865aa0629c4f0ed4f001cf00c51c2 Mon Sep 17 00:00:00 2001 From: Almira Krdzic Date: Thu, 18 Oct 2018 09:57:44 +0200 Subject: [PATCH 3/4] handle bundle product prices editor and prices summary --- .../admin/pricing/class-wiaas-admin-package-pricing.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php b/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php index 3c0984d..8ac582c 100644 --- a/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php +++ b/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php @@ -127,7 +127,7 @@ class Wiaas_Admin_Package_Pricing { } - include 'views/html-package-pricing.php'; + include 'views/html-package-pricing-page.php'; } From 67dc8d7d69960a0993b140da92af9d10e0e8758e Mon Sep 17 00:00:00 2001 From: Almira Krdzic Date: Thu, 18 Oct 2018 20:02:12 +0200 Subject: [PATCH 4/4] Hide unused tabs and render only edit link for package prices --- .../includes/admin/class-wiaas-admin-package.php | 3 ++- .../class-wiaas-admin-package-pricing.php | 16 +--------------- 2 files changed, 3 insertions(+), 16 deletions(-) diff --git a/backend/app/plugins/wiaas/includes/admin/class-wiaas-admin-package.php b/backend/app/plugins/wiaas/includes/admin/class-wiaas-admin-package.php index 2f5a760..18d0e54 100644 --- a/backend/app/plugins/wiaas/includes/admin/class-wiaas-admin-package.php +++ b/backend/app/plugins/wiaas/includes/admin/class-wiaas-admin-package.php @@ -11,7 +11,7 @@ class Wiaas_Admin_Package { require_once dirname( __FILE__ ) . '/package/class-wiaas-admin-linked-packages.php'; require_once dirname( __FILE__ ) . '/package/class-wiaas-admin-package-types.php'; - add_action( 'woocommerce_product_data_tabs', array( __CLASS__, 'package_data_tabs' ), 1 ); + add_action( 'woocommerce_product_data_tabs', array( __CLASS__, 'package_data_tabs' ), 999); } /** @@ -29,6 +29,7 @@ class Wiaas_Admin_Package { unset($tabs['variations']); unset($tabs['advanced']); unset($tabs['shipping']); + unset($tabs['inventory']); return $tabs; } diff --git a/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php b/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php index 8ac582c..2db6915 100644 --- a/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php +++ b/backend/app/plugins/wiaas/includes/admin/pricing/class-wiaas-admin-package-pricing.php @@ -21,24 +21,10 @@ class Wiaas_Admin_Package_Pricing { } public static function get_package_price_html($price_html, $package) { - $bundled_items = $package->get_bundled_items(); - - $recurring_price = 0; - - foreach ($bundled_items as $bundled_item) { - $product = $bundled_item->product; - $product_price = Wiaas_Product_Pricing::get_product_price($product); - if ($product_price['is_recurring']) { - $recurring_price += $product_price['price'] * $bundled_item->get_quantity(); - } - } $edit_link = admin_url( 'edit.php?post_type=product&page=wiaas-package_price_editor&id=' . absint( $package->get_id() ) ); - $price_html = 'Fixed: ' . $price_html . ' and ' . $recurring_price . ' / month' . - '
Edit price'; - - return $price_html; + return 'Edit price'; } public static function render_edit_prices_link() {