From 67225624f77ea2891aa141db6d679f6171ee03d3 Mon Sep 17 00:00:00 2001
From: Reinhold Kainhofer <reinhold@kainhofer.com>
Date: Mon, 19 Oct 2015 02:15:58 +0200
Subject: [PATCH] Split the plugin into a free and a paid version, add a nag
 box.

---
 Makefile                                      |  10 +-
 advanced-shipping-by-rules.php                | 284 ++++++++++++++++++
 assets/css/admin-styles.css                   |  40 +++
 assets/css/shipping-rules-config.css          |   0
 assets/images/advlogo100.png                  | Bin 0 -> 9521 bytes
 .../settings/settings-shipping-rules.php      |   0
 includes/rules-shipping-method.php            |  61 +++-
 includes/rules-shipping-post-type.php         |  72 +++--
 .../rules_shipping_framework_woocommerce.php  |  68 ++++-
 ...hipping_framework_woocommerce_advanced.php |  51 ++++
 library/rules_shipping_framework.php          |  42 +++
 shipping-by-rules.php                         |  36 ++-
 12 files changed, 605 insertions(+), 59 deletions(-)
 create mode 100644 advanced-shipping-by-rules.php
 delete mode 100644 assets/css/shipping-rules-config.css
 create mode 100644 assets/images/advlogo100.png
 delete mode 100644 includes/admin/settings/settings-shipping-rules.php
 create mode 100644 includes/rules_shipping_framework_woocommerce_advanced.php

diff --git a/Makefile b/Makefile
index 5ac1bf5..b0a5abe 100644
--- a/Makefile
+++ b/Makefile
@@ -1,7 +1,7 @@
-BASE=ordernumbers
+BASE=shippingbyrules
 PLATTFORM=woocommerce
 VENDOR=opentools
-VERSION=1.1
+VERSION=1.0
 DIR = $(shell pwd)
 SVNDIR=wordpress-plugin-svn
 
@@ -9,9 +9,9 @@ BUILDDIR=.build/
 BASICBUILDDIR=$(VENDOR)-$(PLATTFORM)-$(BASE)-basic
 ADVBUILDDIR=$(VENDOR)-$(PLATTFORM)-$(BASE)-advanced
 
-PLUGINFILES=library assets ordernumber_helper_woocommerce.php ordernumbers_woocommerce_basic.php readme.txt LICENSE.txt
-BASICPLUGINFILES=woocommerce-basic-ordernumbers.php
-ADVPLUGINFILES=woocommerce-advanced-ordernumbers.php ordernumbers_woocommerce.php
+PLUGINFILES=library assets includes LICENSE.txt
+BASICPLUGINFILES=shipping-by-rules.php readme.txt 
+ADVPLUGINFILES=advanced-shipping-by-rules.php readme-adv.txt 
 
 TRANSLATIONS=
 
diff --git a/advanced-shipping-by-rules.php b/advanced-shipping-by-rules.php
new file mode 100644
index 0000000..cb798a9
--- /dev/null
+++ b/advanced-shipping-by-rules.php
@@ -0,0 +1,284 @@
+<?php
+/**
+ * Plugin Name: Advanced Shipping By Rules
+ * Plugin URI: http://open-tools.net/woocommerce/
+ * Description: Define Shipping cost by very general and flexible (text-based) rules. The advanced version also provides mathematical expressions and functions
+ * Version: 1.0.0
+ * Author: Open Tools, Reinhold Kainhofer
+ * Author URI: http://open-tools.net
+ * Text Domain: woocommerce-shipping-by-rules
+ * Domain Path: 
+ * License: GPL2+
+ * WC requires at least: 2.2
+ * WC tested up to: 2.4
+ 
+
+ * Copyright (C) 2015 Reinhold Kainhofer
+ *
+ *     This file is part of WooCommerce Shipping By Rules,
+ *     a plugin for WordPress and WooCommerce.
+ *
+ *     WooCommerce Shipping By Rules is free software:
+ *     You can redistribute it and/or modify it under the terms of the
+ *     GNU General Public License as published by the Free Software
+ *     Foundation, either version 3 of the License, or (at your option)
+ *     any later version.
+ *
+ *     This software is distributed in the hope that
+ *     it will be useful, but WITHOUT ANY WARRANTY; without even the
+ *     implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
+ *     PURPOSE. See the GNU General Public License for more details.
+ *
+ *     You should have received a copy of the GNU General Public License
+ *     along with WordPress. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+/**
+ * Class WooCommerce_Shipping_By_Rules_Advanced.
+ *
+ * Main Shipping by Rules class, add filters and handling all other files.
+ *
+ * @class       WooCommerce_Shipping_By_Rules_Advanced
+ * @version     1.0.0
+ * @author      Reinhold Kainhofer
+ */
+class WooCommerce_Shipping_By_Rules_Advanced {
+	/**
+	 * Version.
+	 *
+	 * @since 1.0.0
+	 * @var string $version Plugin version number.
+	 */
+	public $version = '1.0.0';
+
+
+	/**
+	 * Instance of WooCommerce_Shipping_By_Rules.
+	 *
+	 * @since 1.0.0
+	 * @access private
+	 * @var object $instance The instance of WooCommerce_Shipping_By_Rules.
+	 */
+	private static $instance;
+
+
+	/**
+	 * Constructor.
+	 *
+	 * @since 1.0.0
+	 */
+	public function __construct() {
+
+		if ( ! function_exists( 'is_plugin_active_for_network' ) )
+			require_once( ABSPATH . '/wp-admin/includes/plugin.php' );
+
+		// Check if WooCommerce is active
+		if ( ! in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', get_option( 'active_plugins' ) ) ) ) :
+			if ( ! is_plugin_active_for_network( 'woocommerce/woocommerce.php' ) ) :
+				return;
+			endif;
+		endif;
+
+		$this->init();
+
+	}
+
+
+	/**
+	 * Instance.
+	 *
+	 * An global instance of the class. Used to retrieve the instance
+	 * to use on other files/plugins/themes.
+	 *
+	 * @since 1.0.0
+	 *
+	 * @return object Instance of the class.
+	 */
+	public static function instance() {
+		if ( is_null( self::$instance ) ) {
+			self::$instance = new self();
+		}
+		return self::$instance;
+	}
+
+
+	/**
+	 * Init.
+	 *
+	 * Initialize plugin parts.
+	 *
+	 * @since 1.0.0
+	 */
+	public function init() {
+		$this->hooks();
+		$this->load_textdomain();
+		$this->update();
+
+		if (!class_exists("RulesShippingFrameworkWooCommerceAdvanced")) {
+			require_once( plugin_dir_path( __FILE__ ) . 'includes/rules_shipping_framework_woocommerce_advanced.php');
+		}
+		$this->helper = RulesShippingFrameworkWooCommerceAdvanced::getHelper();
+		
+		// Shipping method post type definition:
+		require_once plugin_dir_path( __FILE__ ) . 'includes/rules-shipping-post-type.php';
+		$this->post_type = new Shipping_Rules_post_type($this->helper);
+
+		// Links to docs and config in the plugin page
+		add_filter( 'plugin_row_meta', array( &$this, 'shippingbyrules_row_meta' ), 30, 2 );
+		add_filter( 'plugin_action_links_'.plugin_basename(__FILE__),		array( &$this, 'shippingbyrules_add_settings_link' ) );
+	}
+
+
+	protected function shippingbyrules_row_meta($links, $file ) {
+		if ($file==plugin_basename(__FILE__)) {
+			$links['docs'] = '<a href="' . esc_url(  'http://open-tools.net/documentation/advanced-shipping-by-rules-for-woocommerce.html' ) . '" title="' . esc_attr( $this->helper->__( 'Plugin Documentation' ) ) . '">' . $this->helper->__( 'Plugin Documentation' ) . '</a>';
+			$links['support'] = '<a href="' . esc_url( 'http://open-tools.net/support-forum/shiping-by-rules-for-woocommerce.html' ) . '" title="' . esc_attr( $this->helper->__( 'Support Forum' ) ) . '">' . $this->helper->__( 'Support Forum' ) . '</a>';
+		}
+		return (array)$links;
+	}
+	/**
+	 * Add settings link to plugins page
+	 */
+	protected function shippingbyrules_add_settings_link( $links ) {
+		$link = '<a href="admin.php?page=wc-settings&tab=shipping&section=shipping_by_rules">'. $this->helper->__( 'Settings' ) . '</a>';
+		array_push( $links, $link );
+		return $links;
+	}
+	
+
+
+	/**
+	 * Update.
+	 *
+	 * Runs when the plugin is updated and checks if there should be
+	 * any data updated to be compatible for the new version.
+	 *
+	 * @since 1.0.0
+	 */
+	public function update() {
+
+		$db_version = get_option( 'shipping_by_rules_plugin_version', '1.0.0' );
+
+		// Stop current version is up to date
+		if ( $db_version >= $this->version ) :
+			return;
+		endif;
+
+		// Update functions come here:
+		// From version 1.x.x to 1.x.y
+		// From version 1.x.y to 1.x.z
+
+		update_option( 'shipping_by_rules_plugin_version', $this->version );
+
+	}
+
+
+	/**
+	 * Hooks.
+	 *
+	 * Initialize all class hooks.
+	 *
+	 * @since 1.0.0
+	 */
+	public function hooks() {
+
+		// Initialize shipping method class
+		add_action( 'woocommerce_shipping_init', array( $this, 'shipping_by_rules_init' ) );
+
+		// Add shipping method
+		add_action( 'woocommerce_shipping_methods', array( $this, 'shipping_by_rules_add_shipping_method' ) );
+
+		// Enqueue scripts
+		add_action( 'admin_enqueue_scripts', array( $this, 'shipping_by_rules_admin_enqueue_scripts' ) );
+
+	}
+
+
+	/**
+	 * Textdomain.
+	 *
+	 * Load the textdomain based on WP language.
+	 *
+	 * @since 1.0.0
+	 */
+	public function load_textdomain() {
+
+		// Load textdomain
+		load_plugin_textdomain('opentools-shippingrules', false, basename( dirname( __FILE__ ) ) . '/languages' );
+	}
+
+
+	/**
+	 * Shipping method.
+	 *
+	 * Include the WooCommerce shipping method class.
+	 *
+	 * @since 1.0.0
+	 */
+	public function shipping_by_rules_init() {
+		require_once plugin_dir_path( __FILE__ ) . 'includes/rules-shipping-method.php';
+		$this->rule_shipping_method = new Shipping_by_Rules();
+		$this->rule_shipping_method->helper = $this->helper;
+	}
+
+
+	/**
+	 * Add shipping method.
+	 *
+	 * Add shipping method to WooCommerce.
+	 *
+	 * @since 1.0.0
+	 */
+	public function shipping_by_rules_add_shipping_method( $methods ) {
+		if ( class_exists( 'Shipping_by_Rules' ) ) :
+			$methods[] = 'Shipping_by_Rules';
+		endif;
+		// TODO: Figure out a way to add each shipping by rules method as a
+		// separate WooCommerce shipping method (ie. their order can be
+		// defined in the WC configuration and not only in the Shipping by
+		// Rules Method configuration screen.
+		return $methods;
+	}
+
+
+	/**
+	 * Enqueue scripts.
+	 *
+	 * Enqueue javascript and stylesheets to the admin area.
+	 *
+	 * @since 1.0.0
+	 */
+	public function shipping_by_rules_admin_enqueue_scripts() {
+		// For some strange reason, WC does not define the select2.css style...
+		$assets_path          = str_replace( array( 'http:', 'https:' ), '', WC()->plugin_url() ) . '/assets/';
+		wp_enqueue_style( 'select2', $assets_path . 'css/select2.css' );
+
+		wp_enqueue_style( 'shipping_by_rules-style', plugins_url( 'assets/css/admin-styles.css', __FILE__ ), array('select2'), $this->version );
+		wp_enqueue_script( 'shipping-by-rules-config', plugins_url( 'assets/js/shipping-by-rules-config.js', __FILE__ ), array( 'jquery', 'jquery-ui-sortable', 'select2', 'wc-enhanced-select' ), $this->version, true );
+
+	}
+
+
+}
+
+
+/**
+ * The main function responsible for returning the WooCommerce_Shipping_By_Rules_Advanced object.
+ *
+ * Use this function like you would a global variable, except without needing to declare the global.
+ *
+ * Example: <?php OpenTools_ShippingByRules()->method_name(); ?>
+ *
+ * @since 1.0.0
+ *
+ * @return object WooCommerce_Shipping_By_Rules_Advanced class object.
+ */
+if ( ! function_exists( 'OpenTools_ShippingByRules' ) ) :
+
+ 	function OpenTools_ShippingByRules() {
+		return WooCommerce_Shipping_By_Rules_Advanced::instance();
+	}
+
+endif;
+
+OpenTools_ShippingByRules();
diff --git a/assets/css/admin-styles.css b/assets/css/admin-styles.css
index ecade0a..94ac88b 100644
--- a/assets/css/admin-styles.css
+++ b/assets/css/admin-styles.css
@@ -101,3 +101,43 @@ div.shipping_rules_ruleset {
 		<h3 class="hndle ui-sortable-handle">Ruleset: 
 			<span class="input-wrap"><input type='text' class='ruleset_name' name='<?php echo $id; ?>[name]' placeholder='<?php _e('Name of the Ruleset', 'opentools-shippingrules'); ?>' value='<?php echo isset($ruleset['name'])?esc_attr($ruleset['name']):""; ?>'></span></h3>
 	</div>*/
+
+div#opentools-shippingbyrules-upgrade {
+/* 	margin-top: 1em; */
+/* 	padding-left: 15px; */
+/* 	border-radius: 5px; */
+/* 	border: 1px solid red; */
+/* 	background: #ff8080; */
+	padding: 5px 10px;
+}
+div#opentools-shippingbyrules-upgrade.postbox {
+  display: inline-block;
+}
+div#opentools-shippingbyrules-upgrade h3 {
+/* 	margin-top: 5px; */
+/* 	margin-bottom: 5px; */
+/* 	padding: 0px 10px 5px 10px; */
+/* 	border-bottom: 1px solid #e0e0e0; */
+}
+div#opentools-shippingbyrules-upgrade ul {
+	list-style: disc;
+/* 	list-style-position: inside; */
+	margin-left: 5px;
+	padding-left: 5px;
+}
+div#opentools-shippingbyrules-upgrade li {
+	margin-left: 2em;
+}
+div#opentools-shippingbyrules-upgrade .column1, div#opentools-shippingbyrules-upgrade .column2 {
+	float: left;
+}
+
+div#opentools-shippingbyrules-upgrade .logoleft {
+  float: left;
+  padding-right: 10px;
+  position: absolute;
+  left: 15px;
+}
+div#opentools-shippingbyrules-upgrade .contents {
+	padding-left: 120px;
+}
\ No newline at end of file
diff --git a/assets/css/shipping-rules-config.css b/assets/css/shipping-rules-config.css
deleted file mode 100644
index e69de29..0000000
diff --git a/assets/images/advlogo100.png b/assets/images/advlogo100.png
new file mode 100644
index 0000000000000000000000000000000000000000..5f2c50e3a161fba5a2d10ebe925744f93136680a
GIT binary patch
literal 9521
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

literal 0
HcmV?d00001

diff --git a/includes/admin/settings/settings-shipping-rules.php b/includes/admin/settings/settings-shipping-rules.php
deleted file mode 100644
index e69de29..0000000
diff --git a/includes/rules-shipping-method.php b/includes/rules-shipping-method.php
index b88dd55..8d2cc10 100644
--- a/includes/rules-shipping-method.php
+++ b/includes/rules-shipping-method.php
@@ -17,11 +17,14 @@ class Shipping_by_Rules extends WC_Shipping_Method {
 	 * @return void
 	 */
 	public function __construct() {
-		if (!class_exists("RulesShippingFrameworkWooCommerce")) {
-			require_once( plugin_dir_path( __FILE__ ) . '/rules_shipping_framework_woocommerce.php');
+		if (class_exists("RulesShippingFrameworkWooCommerceAdvanced")) {
+			$this->helper = RulesShippingFrameworkWooCommerceAdvanced::getHelper();
+		} else {
+			if (!class_exists("RulesShippingFrameworkWooCommerce")) {
+				require_once( plugin_dir_path( __FILE__ ) . 'includes/rules_shipping_framework_woocommerce.php');
+			}
+			$this->helper = RulesShippingFrameworkWooCommerce::getHelper();
 		}
-		$this->helper = RulesShippingFrameworkWooCommerce::getHelper();
-		
 		$this->id						= 'shipping_by_rules'; // Id for your shipping method. Should be uunique.
 		$this->title  					= $this->helper->__( 'Shipping By Rules <small>(displayed title changes according to configured methods)</small>');
 		$this->method_title				= $this->helper->__( 'Shipping by Rules' );  // Title shown in admin
@@ -54,22 +57,26 @@ class Shipping_by_Rules extends WC_Shipping_Method {
 	* @return void
 	*/
 	public function init_form_fields() {
-		$this->form_fields = array(
-			'enabled' => array(
-				'title' 		=> __( 'Enable/Disable', 'woocommerce' ),
-				'type' 			=> 'checkbox',
-				'label' 		=> $this->helper->__( 'Enable Shipping By Rules'),
-				'default' 		=> 'yes'
-			),
-			'methods' => array(
-				'type' => 'rules_shipping_methods',
-			),
+		add_filter( 'woocommerce_admin_field_opentools_shippingbyrules_upgrade', array( &$this, 'admin_field_opentools_shippingbyrules_upgrade') );
+		$fields = array_merge(
+			$this->helper->getUpgradeNagSettings(),
+			array(
+				'enabled' => array(
+					'title' 		=> __( 'Enable/Disable', 'woocommerce' ),
+					'type' 			=> 'checkbox',
+					'label' 		=> $this->helper->__( 'Enable Shipping By Rules'),
+					'default' 		=> 'yes'
+				),
+				'methods' => array(
+					'type' => 'rules_shipping_methods',
+				),
+			)
 		);
+		$this->form_fields = $fields;
 	}
-	
 
 	/**
-	* generate_additional_costs_html function.
+	* generate_rules_shipping_methods_html function.
 	*
 	* @access public
 	* @return string
@@ -92,6 +99,28 @@ class Shipping_by_Rules extends WC_Shipping_Method {
 	public function validate_rules_shipping_methods_field( $key ) {
 		return false;
 	}
+	
+	/**
+	* generate_rules_shipping_methods_html function.
+	*
+	* @access public
+	* @return string
+	*/
+	public function generate_opentools_shippingbyrules_upgrade_html($id, $settings) {
+		if (isset($settings['name'])) {
+			$settings['title'] = $settings['name'];
+		}
+		ob_start();
+		?>
+		<tr valign="top">
+			<td colspan="2">
+				<?php $this->helper->printUpgradeNagBox($settings); ?>
+			</td>
+		</tr>
+		<?php
+		return ob_get_clean();
+	}
+
 
 	/** 
 	 * Handle shipping rules settings
diff --git a/includes/rules-shipping-post-type.php b/includes/rules-shipping-post-type.php
index a2a52d7..63b53ea 100644
--- a/includes/rules-shipping-post-type.php
+++ b/includes/rules-shipping-post-type.php
@@ -16,15 +16,16 @@ if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly
  */
 
 class Shipping_Rules_post_type {
-
+	protected $helper = null;
 
 	/**
 	 * Constructor.
 	 *
 	 * @since 1.0.0
 	 */
-	public function __construct() {
-
+	public function __construct($helper) {
+		$this->helper = $helper;
+		
 		// Register post type
 		add_action( 'init', array( $this, 'shipping_rules_register_post_type' ) );
 
@@ -55,16 +56,16 @@ class Shipping_Rules_post_type {
 	public function shipping_rules_register_post_type() {
 
 		$labels = array(
-			'name' 					=> __( 'Shipping By Rules Methods', 'opentools-shippingrules' ),
-			'singular_name' 		=> __( 'Shipping By Rules method', 'opentools-shippingrules' ),
-			'add_new' 				=> __( 'Add New', 'opentools-shippingrules' ),
-			'add_new_item' 			=> __( 'Add New Shipping by Rules method', 'opentools-shippingrules' ),
-			'edit_item' 			=> __( 'Edit Shipping by Rules method', 'opentools-shippingrules' ),
-			'new_item' 				=> __( 'New Shipping by Rules method', 'opentools-shippingrules' ),
-			'view_item' 			=> __( 'View Shipping by Rules method', 'opentools-shippingrules' ),
-			'search_items' 			=> __( 'Search Shipping by Rules methods', 'opentools-shippingrules' ),
-			'not_found' 			=> __( 'No Shipping by Rules methods', 'opentools-shippingrules' ),
-			'not_found_in_trash'	=> __( 'No Shipping by Rules methods found in Trash', 'opentools-shippingrules' ),
+			'name' 					=> $this->helper->__( 'Shipping By Rules Methods' ),
+			'singular_name' 		=> $this->helper->__( 'Shipping By Rules method' ),
+			'add_new' 				=> $this->helper->__( 'Add New' ),
+			'add_new_item' 			=> $this->helper->__( 'Add New Shipping by Rules method' ),
+			'edit_item' 			=> $this->helper->__( 'Edit Shipping by Rules method' ),
+			'new_item' 				=> $this->helper->__( 'New Shipping by Rules method' ),
+			'view_item' 			=> $this->helper->__( 'View Shipping by Rules method' ),
+			'search_items' 			=> $this->helper->__( 'Search Shipping by Rules methods' ),
+			'not_found' 			=> $this->helper->__( 'No Shipping by Rules methods' ),
+			'not_found_in_trash'	=> $this->helper->__( 'No Shipping by Rules methods found in Trash' ),
 		);
 
 		register_post_type( 'shipping_rules', array(
@@ -103,27 +104,27 @@ class Shipping_Rules_post_type {
 
 		$messages['shipping_rules'] = array(
 			0  => '',
-			1  => __( 'Shipping by Rules method updated.', 'opentools-shippingrules' ),
-			2  => __( 'Custom field updated.', 'opentools-shippingrules' ),
-			3  => __( 'Custom field deleted.', 'opentools-shippingrules' ),
-			4  => __( 'Shipping by Rules method updated.', 'opentools-shippingrules' ),
+			1  => $this->helper->__( 'Shipping by Rules method updated.' ),
+			2  => $this->helper->__( 'Custom field updated.' ),
+			3  => $this->helper->__( 'Custom field deleted.' ),
+			4  => $this->helper->__( 'Shipping by Rules method updated.' ),
 			5  => isset( $_GET['revision'] ) ?
-				sprintf( __( 'Shipping by Rules method restored to revision from %s', 'opentools-shippingrules' ), wp_post_revision_title( (int) $_GET['revision'], false ) )
+				sprintf( $this->helper->__( 'Shipping by Rules method restored to revision from %s' ), wp_post_revision_title( (int) $_GET['revision'], false ) )
 				: false,
-			6  => __( 'Shipping by Rules method published.', 'opentools-shippingrules' ),
-			7  => __( 'Shipping by Rules method saved.', 'opentools-shippingrules' ),
-			8  => __( 'Shipping by Rules method submitted.', 'opentools-shippingrules' ),
+			6  => $this->helper->__( 'Shipping by Rules method published.' ),
+			7  => $this->helper->__( 'Shipping by Rules method saved.' ),
+			8  => $this->helper->__( 'Shipping by Rules method submitted.' ),
 			9  => sprintf(
-				__( 'Shipping by Rules method scheduled for: <strong>%1$s</strong>.', 'opentools-shippingrules' ),
-				date_i18n( __( 'M j, Y @ G:i', 'opentools-shippingrules' ), strtotime( $post->post_date ) )
+				$this->helper->__( 'Shipping by Rules method scheduled for: <strong>%1$s</strong>.' ),
+				date_i18n( $this->helper->__( 'M j, Y @ G:i' ), strtotime( $post->post_date ) )
 			),
-			10 => __( 'Shipping by Rules method draft updated.', 'opentools-shippingrules' ),
+			10 => $this->helper->__( 'Shipping by Rules method draft updated.' ),
 		);
 
 		if ( 'shipping_rules' == $post_type ) :
 			$overview_link = admin_url( 'admin.php?page=wc-settings&tab=shipping&section=shipping_by_rules' );
 
-			$overview = sprintf( ' <a href="%s">%s</a>', esc_url( $overview_link ), __( 'Return to overview.', 'opentools-shippingrules' ) );
+			$overview = sprintf( ' <a href="%s">%s</a>', esc_url( $overview_link ), $this->helper->__( 'Return to overview.' ) );
 			$messages[ $post_type ][1] .= $overview;
 			$messages[ $post_type ][6] .= $overview;
 			$messages[ $post_type ][9] .= $overview;
@@ -154,16 +155,20 @@ class Shipping_Rules_post_type {
 	 */
 	public function shipping_rules_post_type_meta_box($post) {
 // my_add_notice( "shipping_rules_post_type_meta_box called", 'info');
-		add_meta_box( 'shipping_rules_settings', __( 'Shipping settings', 'opentools-shippingrules' ), array( $this, 'render_shipping_rules_settings' ), 'shipping_rules', 'normal' );
+		if (!$this->helper->isAdvanced()) {
+			add_meta_box( 'shipping_rules_upgrade', $this->helper->__( 'Upgrade to the ADVANCED VERSION of the OpenTools Shipping by Rules plugin
+			' ), array( $this, 'render_shipping_upgrade' ), 'shipping_rules', 'normal' );
+		}
+		add_meta_box( 'shipping_rules_settings', $this->helper->__( 'Shipping settings' ), array( $this, 'render_shipping_rules_settings' ), 'shipping_rules', 'normal' );
 
 		add_meta_box( 
 			/* ID */      'shipping_rules_rulesets', 
-			/* Title */   __( 'Rulesets', 'opentools-shippingrules' ), 
+			/* Title */   $this->helper->__( 'Rulesets' ), 
 			/* Callback */array( $this, 'render_shipping_rulesets' ), 
 			/* Screen */  'shipping_rules', 
 			/* Context */ 'advanced');
 
-		add_meta_box( 'shipping_rules_help', __( 'Overview of the Rules Syntax', 'opentools-shippingrules' ), array( $this, 'render_shipping_rules_help' ), 'shipping_rules', 'side' );
+		add_meta_box( 'shipping_rules_help', $this->helper->__( 'Overview of the Rules Syntax' ), array( $this, 'render_shipping_rules_help' ), 'shipping_rules', 'side' );
 	}
 
 
@@ -174,6 +179,10 @@ class Shipping_Rules_post_type {
 	 *
 	 * @since 1.0.0
 	 */
+	public function render_shipping_upgrade($post, $metabox) {
+		$this->helper->printUpgradeNagBox($this->helper->getUpgradeNagSettings()['opentools_shippingbyrules_upgrade']);
+	}
+	
 	public function render_shipping_rulesets($post, $metabox) {
 		$rulesets = $this->get_rulesets($post);
 		require_once plugin_dir_path( __FILE__ ) . 'admin/settings/meta-box-rulesets.php';
@@ -235,6 +244,12 @@ class Shipping_Rules_post_type {
 			return $post_id;
 		endif;
 
+		// Updating the method ordering should only be done when we are on the overview page and have all methods submitted as form controls.
+		// Otherwise, the update_post_meta would erase all methods!
+		if (!isset($_POST['_rules_shipping_ruleset']) or !isset($_POST['_rules_shipping_ordering'])) {
+			return $post_id;
+		}
+
 		$shipping_method_rulesets = $_POST['_rules_shipping_ruleset'];
 		$shipping_method_ordering = $_POST['_rules_shipping_ordering'];
 
@@ -242,7 +257,6 @@ class Shipping_Rules_post_type {
 		foreach ($shipping_method_ordering as $o) {
 			$rulesets[] = $shipping_method_rulesets[$o];
 		}
-
 		update_post_meta( $post_id, '_rules_shipping_ruleset', $rulesets );
 
 	}
diff --git a/includes/rules_shipping_framework_woocommerce.php b/includes/rules_shipping_framework_woocommerce.php
index e795d85..0cf67c6 100644
--- a/includes/rules_shipping_framework_woocommerce.php
+++ b/includes/rules_shipping_framework_woocommerce.php
@@ -11,6 +11,26 @@ if ( !defined( 'ABSPATH' ) ) {
 }
 require_once( plugin_dir_path( __FILE__ ) . '/../library/rules_shipping_framework.php');
 
+/**
+ * Throw debugging output into Debug My Plugin (3rd party plugin)
+ *
+ * @param string $panel the panel name, default is 'main'
+ * @param string $type the type 'pr' or 'msg'
+ * @param string $hdr the message header
+ * @param mixed $msg the variable to dump ('pr') or print ('msg')
+ * @param string $file __FILE__ from calling location
+ * @param string $line __LINE__ from calling location
+ * @return null
+ */
+function render_ToDebugBar($hdr,$msg,$file=null,$line=null) {
+    if (!isset($GLOBALS['DebugMyPlugin'])) { return; }
+    if (is_string($msg)) {
+		$GLOBALS['DebugMyPlugin']->panels['main']->addMessage($hdr,$msg,$file,$line);
+	} else {
+		$GLOBALS['DebugMyPlugin']->panels['main']->addPR($hdr,$msg,$file,$line);
+    }
+}
+
 class RulesShippingFrameworkWooCommerce extends RulesShippingFramework {
 	protected static $_method_ordering	= 'woocommerce_shipping_rules_ordering';
 	
@@ -30,16 +50,19 @@ class RulesShippingFrameworkWooCommerce extends RulesShippingFramework {
 		return plugins_url('library/' . $type . '/' . $file, __FILE__);
     }
 	
+	function isAdvanced() {
+		return false;
+	}
 	function getCustomFunctions() {
 		// Let other plugins add custom functions! 
-		// The onVmShippingRulesRegisterCustomFunctions() trigger is expected to return an array of the form:
+		// The opentools_shipping_by_rules_replacements filter is expected to return an array of the form:
 		//   array ('functionname1' => 'function-to-be-called',
 		//          'functionname2' => array($classobject, 'memberfunc')),
 		//          ...);
 		return apply_filters( 'opentools_shipping_by_rules_replacements', array());
 	}
 	
-	protected function printWarning($message) {
+	public function printWarning($message) {
 		// Keep track of warning messages, so we don't print them twice:
 		global $printed_warnings;
 		if (!isset($printed_warnings))
@@ -198,7 +221,6 @@ class RulesShippingFrameworkWooCommerce extends RulesShippingFramework {
 			'categories' => $categories,
 			'tags'       => $tags,
 			'shippingclasses' => $shipping_classes,
-			'coupons'    => $cart['applied_coupons'],
 		);
 	}
 	
@@ -311,7 +333,45 @@ class RulesShippingFrameworkWooCommerce extends RulesShippingFramework {
 	}
 
 	protected function createMethodRule ($r, $countries, $ruleinfo) {
-		return new ShippingRule_Advanced($this, $r, $countries, $ruleinfo);
+		return new ShippingRule($this, $r, $countries, $ruleinfo);
 	}
+	
+	public function getUpgradeNagSettings() {
+		$settings = array();
+		if (!$this->isAdvanced()) {
+			$settings['opentools_shippingbyrules_upgrade'] = array(
+				'name' 		=> $this->__( 'Upgrade to the ADVANCED VERSION of the OpenTools Shipping by Rules plugin'),
+				'type' 		=> 'opentools_shippingbyrules_upgrade',
+				'link'		=> 'http://open-tools.net/woocommerce/advanced-shipping-by-rules-for-woocommerce.html',
+			);
+		}
+		return $settings;
+	}
+	
+	public function printUpgradeNagBox($settings) {
+	?>
+		<div id="opentools-shippingbyrules-upgrade" class="rules_shipping rules_shipping_upgrade rules_shipping_meta_box rules_shipping_settings_meta_box postbox">
+			<?php if (isset($settings['title'])) { ?><h3><?php echo esc_html($settings['title']); ?></h3><? } ?>
+			<div class="contents">
+				<div class="logoleft"><a href="<?php echo esc_html($settings['link']); ?>"><img src="<?php echo plugins_url('../assets/images/advlogo100.png', __FILE__); ?>"></a></div>
+				<p>Advanced features not included in the free plugin include:</p>
+				<ul>
+					<li><b>Mathematical expressions</b>: shipping costs can be calculated from arbitrary mathematical expressions (depending on e.g. weight, dimensions, amount, etc.), e.g.:
+					<ul>
+						<li>Shipping costs per kg</li>
+						<li>Percentage shipping cost on the amount</li>
+					</ul>
+					<li><b>List functions</b>: conditions on certain products, categories, tags or shipping classes</li>
+					<li><b>Conditions for product subsets</b>: Conditions and shippind costs depending on values evaluated only for particular products, categories, tags or shipping classes
+					<li><b>Alphanumeric Postcodes</b>: Conditions on UK and Canadian postcodes</li>
+					<li><b>Coupon Codes</b>: conditions on coupon codes</li>
+					<li>...</li>
+				</ul>
+				<p>More information and purchase: <a class="button-primary" href="<?php echo esc_html($settings['link']); ?>" target="_blank">Get Support and advanced features</a></p>
+			</div>
+		</div>
+	<?php
+	}
+	
 
 }
diff --git a/includes/rules_shipping_framework_woocommerce_advanced.php b/includes/rules_shipping_framework_woocommerce_advanced.php
new file mode 100644
index 0000000..8db8ea5
--- /dev/null
+++ b/includes/rules_shipping_framework_woocommerce_advanced.php
@@ -0,0 +1,51 @@
+<?php
+/**
+ * Shipping by Rules generic helper class (Joomla/VM-specific)
+ * Reinhold Kainhofer, Open Tools, office@open-tools.net
+ * @copyright (C) 2012-2015 - Reinhold Kainhofer
+ * @license GNU/GPLv3 http://www.gnu.org/licenses/gpl-3.0.html
+**/
+
+if ( !defined( 'ABSPATH' ) ) { 
+	die( 'Direct Access to ' . basename( __FILE__ ) . ' is not allowed.' );
+}
+require_once( plugin_dir_path( __FILE__ ) . '/rules_shipping_framework_woocommerce.php');
+
+class RulesShippingFrameworkWooCommerceAdvanced extends RulesShippingFrameworkWooCommerce {
+	
+	static function getHelper() {
+		static $helper = null;
+		if (!$helper) {
+			$helper = new RulesShippingFrameworkWooCommerceAdvanced();
+			$helper->setup();
+		}
+		return $helper;
+    }
+	function _construct() {
+		parent::_construct();
+	}
+	function isAdvanced() {
+		return true;
+	}
+	protected function getOrderAddress ($cart, $method) {
+		$data = parent::getOrderAddress($this, $cart, $method);
+		$zip = isset($address['postcode'])?trim($address['postcode']):'';
+		if (isset($zip) && $zip!='') {
+			$data = array_merge($data, $this->getAddressZIP($zip);
+		}
+		return $data;
+	}
+	
+	protected function createMethodRule ($r, $countries, $ruleinfo) {
+		return new ShippingRule_Advanced($this, $r, $countries, $ruleinfo);
+	}
+	
+	protected function addCustomCartValues ($cart, $products, $method, &$values) {
+		$data = array(
+			'coupons'    => $cart['applied_coupons'],
+		);
+		return $data;
+	}
+	
+
+}
diff --git a/library/rules_shipping_framework.php b/library/rules_shipping_framework.php
index 71c72d1..d2bcb00 100644
--- a/library/rules_shipping_framework.php
+++ b/library/rules_shipping_framework.php
@@ -239,6 +239,46 @@ class RulesShippingFramework {
 	protected function getOrderPrices ($cart, $products, $method) {
 		return array();
 	}
+	
+	/** 
+	 * Extract information about non-numerical zip codes (UK and Canada) from the postal code
+	 */
+	protected function getAddressZIP ($zip) {
+		$values = array();
+
+		// Postal code Check for UK postal codes: Use regexp to determine if ZIP structure matches and also to extract the parts.
+		// Also handle UK overseas areas/islands that use four-letter outward codes rather than "A{1,2}0{1,2}A{0,1} 0AA"
+		$zip=strtoupper($zip);
+		if (isset($zip) and preg_match('/^\s*(([A-Z]{1,2})(\d{1,2})([A-Z]?)|[A-Z]{4}|GIR)\s*(\d[A-Z]{2})\s*$/', $zip, $match)) {
+			$values['uk_outward'] = $match[1];
+			$values['uk_area'] = $match[2];
+			$values['uk_district'] = $match[3];
+			$values['uk_subdistrict'] = $match[4];
+			$values['uk_inward'] = $match[5];
+		} else {
+			$values['uk_outward'] = NULL;
+			$values['uk_area'] = NULL;
+			$values['uk_district'] = NULL;
+			$values['uk_subdistrict'] = NULL;
+			$values['uk_inward'] = NULL;
+		}
+		// Postal code Check for Canadian postal codes: Use regexp to determine if ZIP structure matches and also to extract the parts.
+		if (isset($zip) and preg_match('/^\s*(([A-Za-z])(\d)([A-Za-z]))\s*(\d[A-Za-z]\d)\s*$/', $zip, $match)) {
+			$values['canada_fsa'] = $match[1];
+			$values['canada_area'] = $match[2];
+			$values['canada_urban'] = $match[3];
+			$values['canada_subarea'] = $match[4];
+			$values['canada_ldu'] = $match[5];
+		} else {
+			$values['canada_fsa'] = NULL;
+			$values['canada_area'] = NULL;
+			$values['canada_urban'] = NULL;
+			$values['canada_subarea'] = NULL;
+			$values['canada_ldu'] = NULL;
+		}
+		// print("<pre>values: ".print_r($values,1)."</pre>");
+		return $values;
+	}
 
 	/** Allow child classes to add additional variables for the rules or modify existing one
 	 */
@@ -702,9 +742,11 @@ class ShippingRule {
 		if (count($conditionvals)<1)
 			return $this->evaluateTerm($expr, $vals, $products, $cartvals_callback);
 
+		// TODO: Make this more general!
 		$filterkeys = array( 
 			"evaluate_for_categories" =>    'categories',
 			"evaluate_for_products" =>      'products',
+			"evaluate_for_skus" =>      'products',
 			"evaluate_for_vendors" =>       'vendors',
 			"evaluate_for_manufacturers" => 'manufacturers'
 		);
diff --git a/shipping-by-rules.php b/shipping-by-rules.php
index 5d58f96..320fe60 100644
--- a/shipping-by-rules.php
+++ b/shipping-by-rules.php
@@ -1,7 +1,7 @@
 <?php
 /**
  * Plugin Name: Shipping By Rules
- * Plugin URI: http://open-tools.net/woocommerce/
+ * Plugin URI: http://open-tools.net/woocommerce/advanced-shipping-by-rules-for-woocommerce.html
  * Description: Define Shipping cost by very general and flexible (text-based) rules.
  * Version: 1.0.0
  * Author: Open Tools, Reinhold Kainhofer
@@ -10,7 +10,7 @@
  * Domain Path: 
  * License: GPL2+
  * WC requires at least: 2.2
- * WC tested up to: 2.3
+ * WC tested up to: 2.4
  
 
  * Copyright (C) 2015 Reinhold Kainhofer
@@ -114,13 +114,40 @@ class WooCommerce_Shipping_By_Rules {
 		$this->load_textdomain();
 		$this->update();
 
+		if (!class_exists("RulesShippingFrameworkWooCommerce")) {
+			require_once( plugin_dir_path( __FILE__ ) . 'includes/rules_shipping_framework_woocommerce.php');
+		}
+		$this->helper = RulesShippingFrameworkWooCommerce::getHelper();
+		
 		// Shipping method post type definition:
 		require_once plugin_dir_path( __FILE__ ) . 'includes/rules-shipping-post-type.php';
-		$this->post_type = new Shipping_Rules_post_type();
+		$this->post_type = new Shipping_Rules_post_type($this->helper);
 
+		// Links to docs and config in the plugin page
+		add_filter( 'plugin_row_meta', array( &$this, 'shippingbyrules_row_meta' ), 30, 2 );
+		add_filter( 'plugin_action_links_'.plugin_basename(__FILE__),		array( &$this, 'shippingbyrules_add_settings_link' ) );
 	}
 
 
+	public function shippingbyrules_row_meta($links, $file ) {
+		if ($file==plugin_basename(__FILE__)) {
+			$links['docs'] = '<a href="' . esc_url(  'http://open-tools.net/documentation/advanced-shipping-by-rules-for-woocommerce.html' ) . '" title="' . esc_attr( $this->helper->__( 'Plugin Documentation' ) ) . '">' . $this->helper->__( 'Plugin Documentation' ) . '</a>';
+			$links['support'] = '<a href="' . esc_url( 'http://open-tools.net/support-forum/shiping-by-rules-for-woocommerce.html' ) . '" title="' . esc_attr( $this->helper->__( 'Support Forum' ) ) . '">' . $this->helper->__( 'Support Forum' ) . '</a>';
+			// ONLY IN BASIC VERSION: Purchase link
+			$links['advanced'] = '<a href="' . esc_url( 'http://open-tools.net/woocommerce/advanced-shipping-by-rules-for-woocommerce.html' ) . '" title="' . esc_attr( $this->helper->__('Purchase Advanced Version')) . '">' . $this->helper->__('Purchase Advanced Version') . '</a>';
+		}
+		return (array)$links;
+	}
+	/**
+	 * Add settings link to plugins page
+	 */
+	public function shippingbyrules_add_settings_link( $links ) {
+		$link = '<a href="admin.php?page=wc-settings&tab=shipping&section=shipping_by_rules">'. $this->helper->__( 'Settings' ) . '</a>';
+		array_push( $links, $link );
+		return $links;
+	}
+	
+	
 	/**
 	 * Update.
 	 *
@@ -192,7 +219,6 @@ class WooCommerce_Shipping_By_Rules {
 	public function shipping_by_rules_init() {
 		require_once plugin_dir_path( __FILE__ ) . 'includes/rules-shipping-method.php';
 		$this->rule_shipping_method = new Shipping_by_Rules();
-
 	}
 
 
@@ -247,7 +273,7 @@ class WooCommerce_Shipping_By_Rules {
  *
  * @return object WooCommerce_Shipping_By_Rules class object.
  */
-if ( ! function_exists( 'Shipping_By_Rules' ) ) :
+if ( ! function_exists( 'OpenTools_ShippingByRules' ) ) :
 
  	function OpenTools_ShippingByRules() {
 		return WooCommerce_Shipping_By_Rules::instance();
-- 
GitLab