404 to 301 - Version 3.0.2

Version Description

(26/02/2019) = ** Bug Fixes**

  • Security fix.

** Improvements**

  • Minor performance improvements.
Download this release

Release Info

Developer joelcj91
Plugin Icon 128x128 404 to 301
Version 3.0.2
Comparing to
See all releases

Code changes from version 3.0.1 to 3.0.2

Files changed (47) hide show
  1. 404-to-301.php +2 -2
  2. includes/public/class-jj4t3-404-actions.php +4 -3
  3. includes/public/class-jj4t3-404-data.php +1 -1
  4. languages/404-to-301.mo +0 -0
  5. languages/404-to-301.pot +4 -4
  6. readme.txt +16 -7
  7. vendor/freemius/assets/css/admin/common.css +2 -2
  8. vendor/freemius/assets/css/admin/deactivation-feedback.css +0 -1
  9. vendor/freemius/assets/css/admin/dialog-boxes.css +2 -2
  10. vendor/freemius/assets/css/admin/license-activation.css +0 -1
  11. vendor/freemius/assets/scss/_colors.scss +11 -0
  12. vendor/freemius/assets/scss/admin/_buttons.scss +28 -0
  13. vendor/freemius/assets/scss/admin/_plugin-upgrade-notice.scss +8 -0
  14. vendor/freemius/assets/scss/admin/_subscription-cancellation.scss +30 -0
  15. vendor/freemius/assets/scss/admin/common.scss +4 -2
  16. vendor/freemius/assets/scss/admin/dialog-boxes.scss +3 -1
  17. vendor/freemius/includes/class-freemius.php +1191 -294
  18. vendor/freemius/includes/class-fs-api.php +14 -4
  19. vendor/freemius/includes/class-fs-plugin-updater.php +318 -70
  20. vendor/freemius/includes/class-fs-storage.php +2 -2
  21. vendor/freemius/includes/entities/class-fs-plugin.php +22 -0
  22. vendor/freemius/includes/entities/class-fs-site.php +6 -1
  23. vendor/freemius/includes/fs-core-functions.php +115 -91
  24. vendor/freemius/includes/fs-essential-functions.php +4 -2
  25. vendor/freemius/includes/fs-plugin-info-dialog.php +38 -8
  26. vendor/freemius/includes/i18n.php +3 -3
  27. vendor/freemius/includes/managers/class-fs-admin-menu-manager.php +17 -5
  28. vendor/freemius/includes/managers/class-fs-admin-notice-manager.php +74 -0
  29. vendor/freemius/includes/supplements/fs-essential-functions-1.1.7.1.php +2 -6
  30. vendor/freemius/includes/supplements/fs-essential-functions-2.2.1.php +45 -0
  31. vendor/freemius/languages/freemius.pot +529 -414
  32. vendor/freemius/start.php +20 -9
  33. vendor/freemius/templates/account.php +84 -31
  34. vendor/freemius/templates/account/partials/addon.php +349 -344
  35. vendor/freemius/templates/account/partials/site.php +10 -5
  36. vendor/freemius/templates/add-ons.php +1 -1
  37. vendor/freemius/templates/admin-notice.php +29 -1
  38. vendor/freemius/templates/checkout.php +2 -2
  39. vendor/freemius/templates/connect.php +7 -5
  40. vendor/freemius/templates/contact.php +3 -3
  41. vendor/freemius/templates/debug.php +14 -2
  42. vendor/freemius/templates/forms/deactivation/form.php +98 -31
  43. vendor/freemius/templates/forms/premium-versions-upgrade-handler.php +27 -5
  44. vendor/freemius/templates/forms/premium-versions-upgrade-metadata.php +17 -1
  45. vendor/freemius/templates/forms/subscription-cancellation.php +277 -0
  46. vendor/freemius/templates/pricing.php +2 -2
  47. vendor/freemius/templates/tabs.php +4 -0
404-to-301.php CHANGED
@@ -3,7 +3,7 @@
3
  * Plugin Name: 404 to 301
4
  * Plugin URI: https://duckdev.com/products/404-to-301/
5
  * Description: Automatically redirect all <strong>404 errors</strong> to any page using <strong>301 redirect for SEO</strong>. You can <strong>redirect and log</strong> every 404 errors. No more 404 errors in Webmaster tool.
6
- * Version: 3.0.1
7
  * Author: Joel James
8
  * Author URI: https://duckdev.com/
9
  * Donate link: https://paypal.me/JoelCJ
@@ -63,7 +63,7 @@ if ( ! class_exists( 'JJ_404_to_301' ) ) :
63
  'JJ4T3_DIR' => plugin_dir_path( __FILE__ ),
64
  'JJ4T3_URL' => plugin_dir_url( __FILE__ ),
65
  'JJ4T3_BASE_FILE' => __FILE__,
66
- 'JJ4T3_VERSION' => '3.0.1',
67
  'JJ4T3_DB_VERSION' => '11.0',
68
  'JJ4T3_TABLE' => $GLOBALS['wpdb']->prefix . '404_to_301',
69
  // Set who all can access plugin settings.
3
  * Plugin Name: 404 to 301
4
  * Plugin URI: https://duckdev.com/products/404-to-301/
5
  * Description: Automatically redirect all <strong>404 errors</strong> to any page using <strong>301 redirect for SEO</strong>. You can <strong>redirect and log</strong> every 404 errors. No more 404 errors in Webmaster tool.
6
+ * Version: 3.0.2
7
  * Author: Joel James
8
  * Author URI: https://duckdev.com/
9
  * Donate link: https://paypal.me/JoelCJ
63
  'JJ4T3_DIR' => plugin_dir_path( __FILE__ ),
64
  'JJ4T3_URL' => plugin_dir_url( __FILE__ ),
65
  'JJ4T3_BASE_FILE' => __FILE__,
66
+ 'JJ4T3_VERSION' => '3.0.2',
67
  'JJ4T3_DB_VERSION' => '11.0',
68
  'JJ4T3_TABLE' => $GLOBALS['wpdb']->prefix . '404_to_301',
69
  // Set who all can access plugin settings.
includes/public/class-jj4t3-404-actions.php CHANGED
@@ -89,10 +89,8 @@ class JJ4T3_404_Actions extends JJ4T3_404_Data {
89
  */
90
  public function __construct() {
91
 
92
- parent::__construct();
93
-
94
  // Main filter that handles 404.
95
- add_filter( 'template_redirect', array( $this, 'handle_404' ) );
96
  }
97
 
98
  /**
@@ -116,6 +114,9 @@ class JJ4T3_404_Actions extends JJ4T3_404_Data {
116
  // Let's try folks.
117
  try {
118
 
 
 
 
119
  // Set options for current 404.
120
  $this->set_options();
121
 
89
  */
90
  public function __construct() {
91
 
 
 
92
  // Main filter that handles 404.
93
+ add_action( 'template_redirect', array( $this, 'handle_404' ) );
94
  }
95
 
96
  /**
114
  // Let's try folks.
115
  try {
116
 
117
+ // Initialize.
118
+ $this->init();
119
+
120
  // Set options for current 404.
121
  $this->set_options();
122
 
includes/public/class-jj4t3-404-data.php CHANGED
@@ -65,7 +65,7 @@ class JJ4T3_404_Data {
65
  * @since 3.0.0
66
  * @access private
67
  */
68
- public function __construct() {
69
 
70
  $this->set_ip();
71
  $this->set_ref();
65
  * @since 3.0.0
66
  * @access private
67
  */
68
+ public function init() {
69
 
70
  $this->set_ip();
71
  $this->set_ref();
languages/404-to-301.mo CHANGED
Binary file
languages/404-to-301.pot CHANGED
@@ -1,14 +1,14 @@
1
- # Copyright (C) 2018 Joel James
2
  # This file is distributed under the GPL-2.0+.
3
  msgid ""
4
  msgstr ""
5
- "Project-Id-Version: 404 to 301 3.0.1\n"
6
  "Report-Msgid-Bugs-To: https://duckdev.com/products/404-to-301/\n"
7
- "POT-Creation-Date: 2018-08-24 08:32:46+00:00\n"
8
  "MIME-Version: 1.0\n"
9
  "Content-Type: text/plain; charset=utf-8\n"
10
  "Content-Transfer-Encoding: 8bit\n"
11
- "PO-Revision-Date: 2018-MO-DA HO:MI+ZONE\n"
12
  "Last-Translator: Joel James <me@joelsays.com>\n"
13
  "Language-Team: Joel James <me@joelsays.com>\n"
14
  "Language: en\n"
1
+ # Copyright (C) 2019 Joel James
2
  # This file is distributed under the GPL-2.0+.
3
  msgid ""
4
  msgstr ""
5
+ "Project-Id-Version: 404 to 301 3.0.2\n"
6
  "Report-Msgid-Bugs-To: https://duckdev.com/products/404-to-301/\n"
7
+ "POT-Creation-Date: 2019-02-26 04:15:34+00:00\n"
8
  "MIME-Version: 1.0\n"
9
  "Content-Type: text/plain; charset=utf-8\n"
10
  "Content-Transfer-Encoding: 8bit\n"
11
+ "PO-Revision-Date: 2019-MO-DA HO:MI+ZONE\n"
12
  "Last-Translator: Joel James <me@joelsays.com>\n"
13
  "Language-Team: Joel James <me@joelsays.com>\n"
14
  "Language: en\n"
readme.txt CHANGED
@@ -3,8 +3,8 @@ Contributors: joelcj91,duckdev
3
  Tags: 404, 301, 302, 307, not found, 404 redirect, 404 to 301, 301 redirect, seo redirect, error redirect, 404 seo, custom 404 page
4
  Donate link: https://www.paypal.me/JoelCJ
5
  Requires at least: 3.5
6
- Tested up to: 4.9
7
- Stable tag: 3.0.1
8
  Requires PHP: 5.6
9
  License: GPLv2 or later
10
  License URI: http://www.gnu.org/licenses/gpl-2.0.html
@@ -128,6 +128,15 @@ Bug reports for 404 to 301 are always welcome. [Report here](https://duckdev.com
128
 
129
  == Changelog ==
130
 
 
 
 
 
 
 
 
 
 
131
  = 3.0.1 (24/08/2018) =
132
  **👌 Improvements**
133
 
@@ -388,11 +397,11 @@ Bug reports for 404 to 301 are always welcome. [Report here](https://duckdev.com
388
 
389
  == Upgrade Notice ==
390
 
391
- = 3.0.1 (24/08/2018) =
392
- **👌 Improvements**
393
 
394
- * Make release automated.
395
 
396
- **🐛 Bug Fixes**
397
 
398
- * Do not include exclude path items.
3
  Tags: 404, 301, 302, 307, not found, 404 redirect, 404 to 301, 301 redirect, seo redirect, error redirect, 404 seo, custom 404 page
4
  Donate link: https://www.paypal.me/JoelCJ
5
  Requires at least: 3.5
6
+ Tested up to: 5.1
7
+ Stable tag: 3.0.2
8
  Requires PHP: 5.6
9
  License: GPLv2 or later
10
  License URI: http://www.gnu.org/licenses/gpl-2.0.html
128
 
129
  == Changelog ==
130
 
131
+ = 3.0.2 (26/02/2019) =
132
+ **🐛 Bug Fixes**
133
+
134
+ * Security fix.
135
+
136
+ **👌 Improvements**
137
+
138
+ * Minor performance improvements.
139
+
140
  = 3.0.1 (24/08/2018) =
141
  **👌 Improvements**
142
 
397
 
398
  == Upgrade Notice ==
399
 
400
+ = 3.0.2 (26/02/2019) =
401
+ **🐛 Bug Fixes**
402
 
403
+ * Security fix.
404
 
405
+ **👌 Improvements**
406
 
407
+ * Minor performance improvements.
vendor/freemius/assets/css/admin/common.css CHANGED
@@ -1,2 +1,2 @@
1
- .theme-browser .theme .fs-premium-theme-badge{position:absolute;top:10px;right:0;background:#71ae00;color:#fff;text-transform:uppercase;padding:5px 10px;-moz-border-radius:3px 0 0 3px;-webkit-border-radius:3px 0 0 3px;border-radius:3px 0 0 3px;font-weight:bold;border-right:0;-moz-box-shadow:0 2px 1px -1px rgba(0,0,0,0.3);-webkit-box-shadow:0 2px 1px -1px rgba(0,0,0,0.3);box-shadow:0 2px 1px -1px rgba(0,0,0,0.3);font-size:1.1em}#iframe{line-height:0;font-size:0}.fs-full-size-wrapper{margin:40px 0 -65px -20px}@media (max-width: 600px){.fs-full-size-wrapper{margin:0 0 -65px -10px}}
2
- .fs-notice{position:relative}.fs-notice.fs-has-title{margin-bottom:30px !important}.fs-notice.success{color:green}.fs-notice.promotion{border-color:#00a0d2 !important;background-color:#f2fcff !important}.fs-notice .fs-notice-body{margin:.5em 0;padding:2px}.fs-notice .fs-close{cursor:pointer;color:#aaa;float:right}.fs-notice .fs-close:hover{color:#666}.fs-notice .fs-close>*{margin-top:7px;display:inline-block}.fs-notice label.fs-plugin-title{background:rgba(0,0,0,0.3);color:#fff;padding:2px 10px;position:absolute;top:100%;bottom:auto;right:auto;-moz-border-radius:0 0 3px 3px;-webkit-border-radius:0 0 3px 3px;border-radius:0 0 3px 3px;left:10px;font-size:12px;font-weight:bold;cursor:auto}div.fs-notice.updated,div.fs-notice.success,div.fs-notice.promotion{display:block !important}.rtl .fs-notice .fs-close{float:left}.fs-secure-notice{position:fixed;top:32px;left:160px;right:0;background:#ebfdeb;padding:10px 20px;color:green;z-index:9999;-moz-box-shadow:0 2px 2px rgba(6,113,6,0.3);-webkit-box-shadow:0 2px 2px rgba(6,113,6,0.3);box-shadow:0 2px 2px rgba(6,113,6,0.3);opacity:0.95;filter:alpha(opacity=95)}.fs-secure-notice:hover{opacity:1;filter:alpha(opacity=100)}.fs-secure-notice a.fs-security-proof{color:green;text-decoration:none}@media screen and (max-width: 960px){.fs-secure-notice{left:36px}}@media screen and (max-width: 600px){.fs-secure-notice{display:none}}@media screen and (max-width: 500px){#fs_promo_tab{display:none}}@media screen and (max-width: 782px){.fs-secure-notice{left:0;top:46px;text-align:center}}span.fs-submenu-item.fs-sub:before{content:'\21B3';padding:0 5px}.rtl span.fs-submenu-item.fs-sub:before{content:'\21B2'}.fs-submenu-item.pricing.upgrade-mode{color:greenyellow}.fs-submenu-item.pricing.trial-mode{color:#83e2ff}#adminmenu .update-plugins.fs-trial{background-color:#00b9eb}.fs-ajax-spinner{border:0;width:20px;height:20px;margin-right:5px;vertical-align:sub;display:inline-block;background:url("/wp-admin/images/wpspin_light-2x.gif");background-size:contain}.wrap.fs-section h2{text-align:left}
1
+ .theme-browser .theme .fs-premium-theme-badge{position:absolute;top:10px;right:0;background:#71ae00;color:#fff;text-transform:uppercase;padding:5px 10px;-moz-border-radius:3px 0 0 3px;-webkit-border-radius:3px 0 0 3px;border-radius:3px 0 0 3px;font-weight:bold;border-right:0;-moz-box-shadow:0 2px 1px -1px rgba(0,0,0,0.3);-webkit-box-shadow:0 2px 1px -1px rgba(0,0,0,0.3);box-shadow:0 2px 1px -1px rgba(0,0,0,0.3);font-size:1.1em}#fs_frame{line-height:0;font-size:0}.fs-full-size-wrapper{margin:40px 0 -65px -20px}@media (max-width: 600px){.fs-full-size-wrapper{margin:0 0 -65px -10px}}
2
+ .fs-notice{position:relative}.fs-notice.fs-has-title{margin-bottom:30px !important}.fs-notice.success{color:green}.fs-notice.promotion{border-color:#00a0d2 !important;background-color:#f2fcff !important}.fs-notice .fs-notice-body{margin:.5em 0;padding:2px}.fs-notice .fs-close{cursor:pointer;color:#aaa;float:right}.fs-notice .fs-close:hover{color:#666}.fs-notice .fs-close>*{margin-top:7px;display:inline-block}.fs-notice label.fs-plugin-title{background:rgba(0,0,0,0.3);color:#fff;padding:2px 10px;position:absolute;top:100%;bottom:auto;right:auto;-moz-border-radius:0 0 3px 3px;-webkit-border-radius:0 0 3px 3px;border-radius:0 0 3px 3px;left:10px;font-size:12px;font-weight:bold;cursor:auto}div.fs-notice.updated,div.fs-notice.success,div.fs-notice.promotion{display:block !important}.rtl .fs-notice .fs-close{float:left}.fs-secure-notice{position:fixed;top:32px;left:160px;right:0;background:#ebfdeb;padding:10px 20px;color:green;z-index:9999;-moz-box-shadow:0 2px 2px rgba(6,113,6,0.3);-webkit-box-shadow:0 2px 2px rgba(6,113,6,0.3);box-shadow:0 2px 2px rgba(6,113,6,0.3);opacity:0.95;filter:alpha(opacity=95)}.fs-secure-notice:hover{opacity:1;filter:alpha(opacity=100)}.fs-secure-notice a.fs-security-proof{color:green;text-decoration:none}@media screen and (max-width: 960px){.fs-secure-notice{left:36px}}@media screen and (max-width: 600px){.fs-secure-notice{display:none}}@media screen and (max-width: 500px){#fs_promo_tab{display:none}}@media screen and (max-width: 782px){.fs-secure-notice{left:0;top:46px;text-align:center}}span.fs-submenu-item.fs-sub:before{content:'\21B3';padding:0 5px}.rtl span.fs-submenu-item.fs-sub:before{content:'\21B2'}.fs-submenu-item.pricing.upgrade-mode{color:greenyellow}.fs-submenu-item.pricing.trial-mode{color:#83e2ff}#adminmenu .update-plugins.fs-trial{background-color:#00b9eb}.fs-ajax-spinner{border:0;width:20px;height:20px;margin-right:5px;vertical-align:sub;display:inline-block;background:url("/wp-admin/images/wpspin_light-2x.gif");background-size:contain}.wrap.fs-section h2{text-align:left}.plugins p.fs-upgrade-notice{border:0;background-color:#d54e21;padding:10px;color:#f9f9f9;margin-top:10px}
vendor/freemius/assets/css/admin/deactivation-feedback.css DELETED
@@ -1 +0,0 @@
1
- .fs-modal{position:fixed;overflow:auto;height:100%;width:100%;top:0;z-index:100000;display:none;background:rgba(0,0,0,0.6)}.fs-modal .fs-modal-dialog{background:transparent;position:absolute;left:50%;margin-left:-298px;padding-bottom:30px;top:-100%;z-index:100001;width:596px}@media (max-width: 650px){.fs-modal .fs-modal-dialog{margin-left:-50%;box-sizing:border-box;padding-left:10px;padding-right:10px;width:100%}.fs-modal .fs-modal-dialog .fs-modal-panel>h3>strong{font-size:1.3em}.fs-modal .fs-modal-dialog li.reason{margin-bottom:10px}.fs-modal .fs-modal-dialog li.reason .reason-input,.fs-modal .fs-modal-dialog li.reason .internal-message{margin-left:29px}.fs-modal .fs-modal-dialog li.reason label{display:table}.fs-modal .fs-modal-dialog li.reason label>span{display:table-cell;font-size:1.3em}}.fs-modal.active{display:block}.fs-modal.active:before{display:block}.fs-modal.active .fs-modal-dialog{top:10%}.fs-modal .fs-modal-body,.fs-modal .fs-modal-footer{border:0;background:#fefefe;padding:20px}.fs-modal .fs-modal-body{border-bottom:0}.fs-modal .fs-modal-body h2{font-size:20px}.fs-modal .fs-modal-body>div{margin-top:10px}.fs-modal .fs-modal-body>div h2{font-weight:bold;font-size:20px;margin-top:0}.fs-modal .fs-modal-footer{border-top:#eeeeee solid 1px;text-align:right}.fs-modal .fs-modal-footer>.button{margin:0 7px}.fs-modal .fs-modal-footer>.button:first-child{margin:0}.fs-modal .fs-modal-panel:not(.active){display:none}.fs-modal .reason-input,.fs-modal .internal-message{margin:3px 0 3px 22px}.fs-modal .reason-input input,.fs-modal .reason-input textarea,.fs-modal .internal-message input,.fs-modal .internal-message textarea{width:100%}.fs-modal li.reason.has-internal-message .internal-message{border:1px solid #ccc;padding:7px;display:none}body.has-fs-modal{overflow:hidden}#the-list .deactivate>.fs-slug{display:none}
 
vendor/freemius/assets/css/admin/dialog-boxes.css CHANGED
@@ -1,2 +1,2 @@
1
- .fs-modal{position:fixed;overflow:auto;height:100%;width:100%;top:0;z-index:100000;display:none;background:rgba(0,0,0,0.6)}.fs-modal .fs-modal-dialog{background:transparent;position:absolute;left:50%;margin-left:-298px;padding-bottom:30px;top:-100%;z-index:100001;width:596px}@media (max-width: 650px){.fs-modal .fs-modal-dialog{margin-left:-50%;box-sizing:border-box;padding-left:10px;padding-right:10px;width:100%}.fs-modal .fs-modal-dialog .fs-modal-panel>h3>strong{font-size:1.3em}}.fs-modal.active{display:block}.fs-modal.active:before{display:block}.fs-modal.active .fs-modal-dialog{top:10%}.fs-modal.fs-success .fs-modal-header{border-bottom-color:#46b450}.fs-modal.fs-success .fs-modal-body{background-color:#f7fff7}.fs-modal.fs-warn .fs-modal-header{border-bottom-color:#ffb900}.fs-modal.fs-warn .fs-modal-body{background-color:#fff8e5}.fs-modal.fs-error .fs-modal-header{border-bottom-color:#dc3232}.fs-modal.fs-error .fs-modal-body{background-color:#ffeaea}.fs-modal .fs-modal-body,.fs-modal .fs-modal-footer{border:0;background:#fefefe;padding:20px}.fs-modal .fs-modal-header{border-bottom:#eeeeee solid 1px;background:#fbfbfb;padding:15px 20px;position:relative;margin-bottom:-10px}.fs-modal .fs-modal-header h4{margin:0;padding:0;text-transform:uppercase;font-size:1.2em;font-weight:bold;color:#cacaca;text-shadow:1px 1px 1px #fff;letter-spacing:0.6px;-webkit-font-smoothing:antialiased}.fs-modal .fs-modal-header .fs-close{position:absolute;right:10px;top:12px;cursor:pointer;color:#bbb;-moz-border-radius:20px;-webkit-border-radius:20px;border-radius:20px;padding:3px;-moz-transition:all 0.2s ease-in-out;-o-transition:all 0.2s ease-in-out;-ms-transition:all 0.2s ease-in-out;-webkit-transition:all 0.2s ease-in-out;transition:all 0.2s ease-in-out}.fs-modal .fs-modal-header .fs-close:hover{color:#fff;background:#aaa}.fs-modal .fs-modal-header .fs-close .dashicons,.fs-modal .fs-modal-header .fs-close:hover .dashicons{text-decoration:none}.fs-modal .fs-modal-body{border-bottom:0}.fs-modal .fs-modal-body p{font-size:14px}.fs-modal .fs-modal-body h2{font-size:20px;line-height:1.5em}.fs-modal .fs-modal-body>div{margin-top:10px}.fs-modal .fs-modal-body>div h2{font-weight:bold;font-size:20px;margin-top:0}.fs-modal .fs-modal-footer{border-top:#eeeeee solid 1px;text-align:right}.fs-modal .fs-modal-footer>.button{margin:0 7px}.fs-modal .fs-modal-footer>.button:first-child{margin:0}.fs-modal .fs-modal-panel>.notice.inline{margin:0;display:none}.fs-modal .fs-modal-panel:not(.active){display:none}.rtl .fs-modal .fs-modal-header .fs-close{right:auto;left:20px}body.has-fs-modal{overflow:hidden}.fs-modal.fs-modal-deactivation-feedback .reason-input,.fs-modal.fs-modal-deactivation-feedback .internal-message{margin:3px 0 3px 22px}.fs-modal.fs-modal-deactivation-feedback .reason-input input,.fs-modal.fs-modal-deactivation-feedback .reason-input textarea,.fs-modal.fs-modal-deactivation-feedback .internal-message input,.fs-modal.fs-modal-deactivation-feedback .internal-message textarea{width:100%}.fs-modal.fs-modal-deactivation-feedback li.reason.has-internal-message .internal-message{border:1px solid #ccc;padding:7px;display:none}@media (max-width: 650px){.fs-modal.fs-modal-deactivation-feedback li.reason li.reason{margin-bottom:10px}.fs-modal.fs-modal-deactivation-feedback li.reason li.reason .reason-input,.fs-modal.fs-modal-deactivation-feedback li.reason li.reason .internal-message{margin-left:29px}.fs-modal.fs-modal-deactivation-feedback li.reason li.reason label{display:table}.fs-modal.fs-modal-deactivation-feedback li.reason li.reason label>span{display:table-cell;font-size:1.3em}}.fs-modal.fs-modal-deactivation-feedback .anonymous-feedback-label{float:left}.fs-modal.fs-modal-deactivation-feedback .fs-modal-panel{margin-top:0 !important}.fs-modal.fs-modal-deactivation-feedback .fs-modal-panel h3{margin-top:0;line-height:1.5em}#the-list .deactivate>.fs-slug{display:none}.fs-modal.fs-modal-license-activation .fs-modal-body input.license_key{width:100%}#license_options_container table,#license_options_container table select,#license_options_container table #available_license_key{width:100%}#license_options_container table td:first-child{width:1%}#license_options_container table #other_license_key_container label{position:relative;top:6px;float:left;margin-right:5px}#license_options_container table #other_license_key_container div{overflow:hidden;width:auto;height:30px;display:block;top:2px;position:relative}#license_options_container table #other_license_key_container div input{margin:0}#sites_list_container td{cursor:pointer}#multisite_options_container{margin-top:10px;border:1px solid #ccc;padding:5px}#multisite_options_container a{text-decoration:none}#multisite_options_container a:focus{box-shadow:none}#multisite_options_container a.selected{font-weight:bold}#multisite_options_container.apply-on-all-sites{border:0 none;padding:0}#multisite_options_container.apply-on-all-sites #all_sites_options{border-spacing:0}#multisite_options_container.apply-on-all-sites #all_sites_options td:not(:first-child){display:none}#multisite_options_container #sites_list_container{display:none;overflow:auto}#multisite_options_container #sites_list_container table td{border-top:1px solid #ccc;padding:4px 2px}.fs-modal.fs-modal-license-key-resend .email-address-container{overflow:hidden;padding-right:2px}.fs-modal.fs-modal-license-key-resend.fs-freemium input.email-address{width:300px}.fs-modal.fs-modal-license-key-resend.fs-freemium label{display:block;margin-bottom:10px}.fs-modal.fs-modal-license-key-resend.fs-premium input.email-address{width:100%}.fs-modal.fs-modal-license-key-resend.fs-premium .button-container{float:right;margin-left:7px}@media (max-width: 650px){.fs-modal.fs-modal-license-key-resend.fs-premium .button-container{margin-top:2px}}
2
- .rtl .fs-modal.fs-modal-license-key-resend .fs-modal-body .input-container>.email-address-container{padding-left:2px;padding-right:0}.rtl .fs-modal.fs-modal-license-key-resend .fs-modal-body .button-container{float:left;margin-right:7px;margin-left:0}a.show-license-resend-modal{margin-top:4px;display:inline-block}.fs-ajax-loader{position:relative;width:170px;height:20px;margin:auto}.fs-ajax-loader .fs-ajax-loader-bar{position:absolute;top:0;background-color:#0074a3;width:20px;height:20px;-webkit-animation-name:bounce_ajaxLoader;-moz-animation-name:bounce_ajaxLoader;-ms-animation-name:bounce_ajaxLoader;-o-animation-name:bounce_ajaxLoader;animation-name:bounce_ajaxLoader;-webkit-animation-duration:1.5s;-moz-animation-duration:1.5s;-ms-animation-duration:1.5s;-o-animation-duration:1.5s;animation-duration:1.5s;animation-iteration-count:infinite;-o-animation-iteration-count:infinite;-ms-animation-iteration-count:infinite;-webkit-animation-iteration-count:infinite;-moz-animation-iteration-count:infinite;-webkit-animation-direction:normal;-moz-animation-direction:normal;-ms-animation-direction:normal;-o-animation-direction:normal;animation-direction:normal;-moz-transform:0.3;-o-transform:0.3;-ms-transform:0.3;-webkit-transform:0.3;transform:0.3}.fs-ajax-loader .fs-ajax-loader-bar-1{left:0px;animation-delay:0.6s;-o-animation-delay:0.6s;-ms-animation-delay:0.6s;-webkit-animation-delay:0.6s;-moz-animation-delay:0.6s}.fs-ajax-loader .fs-ajax-loader-bar-2{left:19px;animation-delay:0.75s;-o-animation-delay:0.75s;-ms-animation-delay:0.75s;-webkit-animation-delay:0.75s;-moz-animation-delay:0.75s}.fs-ajax-loader .fs-ajax-loader-bar-3{left:38px;animation-delay:0.9s;-o-animation-delay:0.9s;-ms-animation-delay:0.9s;-webkit-animation-delay:0.9s;-moz-animation-delay:0.9s}.fs-ajax-loader .fs-ajax-loader-bar-4{left:57px;animation-delay:1.05s;-o-animation-delay:1.05s;-ms-animation-delay:1.05s;-webkit-animation-delay:1.05s;-moz-animation-delay:1.05s}.fs-ajax-loader .fs-ajax-loader-bar-5{left:76px;animation-delay:1.2s;-o-animation-delay:1.2s;-ms-animation-delay:1.2s;-webkit-animation-delay:1.2s;-moz-animation-delay:1.2s}.fs-ajax-loader .fs-ajax-loader-bar-6{left:95px;animation-delay:1.35s;-o-animation-delay:1.35s;-ms-animation-delay:1.35s;-webkit-animation-delay:1.35s;-moz-animation-delay:1.35s}.fs-ajax-loader .fs-ajax-loader-bar-7{left:114px;animation-delay:1.5s;-o-animation-delay:1.5s;-ms-animation-delay:1.5s;-webkit-animation-delay:1.5s;-moz-animation-delay:1.5s}.fs-ajax-loader .fs-ajax-loader-bar-8{left:133px;animation-delay:1.65s;-o-animation-delay:1.65s;-ms-animation-delay:1.65s;-webkit-animation-delay:1.65s;-moz-animation-delay:1.65s}@-moz-keyframes bounce_ajaxLoader{0%{-moz-transform:scale(1);-o-transform:scale(1);-ms-transform:scale(1);-webkit-transform:scale(1);transform:scale(1);background-color:#0074a3}100%{-moz-transform:scale(0.3);-o-transform:scale(0.3);-ms-transform:scale(0.3);-webkit-transform:scale(0.3);transform:scale(0.3);background-color:#fff}}@-ms-keyframes bounce_ajaxLoader{0%{-moz-transform:scale(1);-o-transform:scale(1);-ms-transform:scale(1);-webkit-transform:scale(1);transform:scale(1);background-color:#0074a3}100%{-moz-transform:scale(0.3);-o-transform:scale(0.3);-ms-transform:scale(0.3);-webkit-transform:scale(0.3);transform:scale(0.3);background-color:#fff}}@-o-keyframes bounce_ajaxLoader{0%{-moz-transform:scale(1);-o-transform:scale(1);-ms-transform:scale(1);-webkit-transform:scale(1);transform:scale(1);background-color:#0074a3}100%{-moz-transform:scale(0.3);-o-transform:scale(0.3);-ms-transform:scale(0.3);-webkit-transform:scale(0.3);transform:scale(0.3);background-color:#fff}}@-webkit-keyframes bounce_ajaxLoader{0%{-moz-transform:scale(1);-o-transform:scale(1);-ms-transform:scale(1);-webkit-transform:scale(1);transform:scale(1);background-color:#0074a3}100%{-moz-transform:scale(0.3);-o-transform:scale(0.3);-ms-transform:scale(0.3);-webkit-transform:scale(0.3);transform:scale(0.3);background-color:#fff}}@keyframes bounce_ajaxLoader{0%{-moz-transform:scale(1);-o-transform:scale(1);-ms-transform:scale(1);-webkit-transform:scale(1);transform:scale(1);background-color:#0074a3}100%{-moz-transform:scale(0.3);-o-transform:scale(0.3);-ms-transform:scale(0.3);-webkit-transform:scale(0.3);transform:scale(0.3);background-color:#fff}}.fs-modal-auto-install #request-filesystem-credentials-form h2,.fs-modal-auto-install #request-filesystem-credentials-form .request-filesystem-credentials-action-buttons{display:none}.fs-modal-auto-install #request-filesystem-credentials-form input[type=password],.fs-modal-auto-install #request-filesystem-credentials-form input[type=email],.fs-modal-auto-install #request-filesystem-credentials-form input[type=text]{-webkit-appearance:none;padding:10px 10px 5px 10px;width:300px;max-width:100%}.fs-modal-auto-install #request-filesystem-credentials-form>div,.fs-modal-auto-install #request-filesystem-credentials-form label,.fs-modal-auto-install #request-filesystem-credentials-form fieldset{width:300px;max-width:100%;margin:0 auto;display:block}
1
+ .fs-modal{position:fixed;overflow:auto;height:100%;width:100%;top:0;z-index:100000;display:none;background:rgba(0,0,0,0.6)}.fs-modal .fs-modal-dialog{background:transparent;position:absolute;left:50%;margin-left:-298px;padding-bottom:30px;top:-100%;z-index:100001;width:596px}@media (max-width: 650px){.fs-modal .fs-modal-dialog{margin-left:-50%;box-sizing:border-box;padding-left:10px;padding-right:10px;width:100%}.fs-modal .fs-modal-dialog .fs-modal-panel>h3>strong{font-size:1.3em}}.fs-modal.active{display:block}.fs-modal.active:before{display:block}.fs-modal.active .fs-modal-dialog{top:10%}.fs-modal.fs-success .fs-modal-header{border-bottom-color:#46b450}.fs-modal.fs-success .fs-modal-body{background-color:#f7fff7}.fs-modal.fs-warn .fs-modal-header{border-bottom-color:#ffb900}.fs-modal.fs-warn .fs-modal-body{background-color:#fff8e5}.fs-modal.fs-error .fs-modal-header{border-bottom-color:#dc3232}.fs-modal.fs-error .fs-modal-body{background-color:#ffeaea}.fs-modal .fs-modal-body,.fs-modal .fs-modal-footer{border:0;background:#fefefe;padding:20px}.fs-modal .fs-modal-header{border-bottom:#eeeeee solid 1px;background:#fbfbfb;padding:15px 20px;position:relative;margin-bottom:-10px}.fs-modal .fs-modal-header h4{margin:0;padding:0;text-transform:uppercase;font-size:1.2em;font-weight:bold;color:#cacaca;text-shadow:1px 1px 1px #fff;letter-spacing:0.6px;-webkit-font-smoothing:antialiased}.fs-modal .fs-modal-header .fs-close{position:absolute;right:10px;top:12px;cursor:pointer;color:#bbb;-moz-border-radius:20px;-webkit-border-radius:20px;border-radius:20px;padding:3px;-moz-transition:all 0.2s ease-in-out;-o-transition:all 0.2s ease-in-out;-ms-transition:all 0.2s ease-in-out;-webkit-transition:all 0.2s ease-in-out;transition:all 0.2s ease-in-out}.fs-modal .fs-modal-header .fs-close:hover{color:#fff;background:#aaa}.fs-modal .fs-modal-header .fs-close .dashicons,.fs-modal .fs-modal-header .fs-close:hover .dashicons{text-decoration:none}.fs-modal .fs-modal-body{border-bottom:0}.fs-modal .fs-modal-body p{font-size:14px}.fs-modal .fs-modal-body h2{font-size:20px;line-height:1.5em}.fs-modal .fs-modal-body>div{margin-top:10px}.fs-modal .fs-modal-body>div h2{font-weight:bold;font-size:20px;margin-top:0}.fs-modal .fs-modal-footer{border-top:#eeeeee solid 1px;text-align:right}.fs-modal .fs-modal-footer>.button{margin:0 7px}.fs-modal .fs-modal-footer>.button:first-child{margin:0}.fs-modal .fs-modal-panel>.notice.inline{margin:0;display:none}.fs-modal .fs-modal-panel:not(.active){display:none}.rtl .fs-modal .fs-modal-header .fs-close{right:auto;left:20px}body.has-fs-modal{overflow:hidden}.fs-modal.fs-modal-deactivation-feedback .reason-input,.fs-modal.fs-modal-deactivation-feedback .internal-message{margin:3px 0 3px 22px}.fs-modal.fs-modal-deactivation-feedback .reason-input input,.fs-modal.fs-modal-deactivation-feedback .reason-input textarea,.fs-modal.fs-modal-deactivation-feedback .internal-message input,.fs-modal.fs-modal-deactivation-feedback .internal-message textarea{width:100%}.fs-modal.fs-modal-deactivation-feedback li.reason.has-internal-message .internal-message{border:1px solid #ccc;padding:7px;display:none}@media (max-width: 650px){.fs-modal.fs-modal-deactivation-feedback li.reason li.reason{margin-bottom:10px}.fs-modal.fs-modal-deactivation-feedback li.reason li.reason .reason-input,.fs-modal.fs-modal-deactivation-feedback li.reason li.reason .internal-message{margin-left:29px}.fs-modal.fs-modal-deactivation-feedback li.reason li.reason label{display:table}.fs-modal.fs-modal-deactivation-feedback li.reason li.reason label>span{display:table-cell;font-size:1.3em}}.fs-modal.fs-modal-deactivation-feedback .anonymous-feedback-label{float:left}.fs-modal.fs-modal-deactivation-feedback .fs-modal-panel{margin-top:0 !important}.fs-modal.fs-modal-deactivation-feedback .fs-modal-panel h3{margin-top:0;line-height:1.5em}#the-list .deactivate>.fs-slug{display:none}.fs-modal.fs-modal-subscription-cancellation .fs-price-increase-warning{color:red;font-weight:bold;padding:0 25px;margin-bottom:0}.fs-modal.fs-modal-subscription-cancellation ul.subscription-actions label input{float:left;top:5px;position:relative}.rtl .fs-modal.fs-modal-subscription-cancellation ul.subscription-actions label input{float:right}.fs-modal.fs-modal-subscription-cancellation ul.subscription-actions label span{display:block;margin-left:24px}.rtl .fs-modal.fs-modal-subscription-cancellation ul.subscription-actions label span{margin-left:0;margin-right:24px}.fs-modal.fs-modal-license-activation .fs-modal-body input.license_key{width:100%}#license_options_container table,#license_options_container table select,#license_options_container table #available_license_key{width:100%}#license_options_container table td:first-child{width:1%}#license_options_container table #other_license_key_container label{position:relative;top:6px;float:left;margin-right:5px}#license_options_container table #other_license_key_container div{overflow:hidden;width:auto;height:30px;display:block;top:2px;position:relative}#license_options_container table #other_license_key_container div input{margin:0}#sites_list_container td{cursor:pointer}#multisite_options_container{margin-top:10px;border:1px solid #ccc;padding:5px}#multisite_options_container a{text-decoration:none}#multisite_options_container a:focus{box-shadow:none}#multisite_options_container a.selected{font-weight:bold}#multisite_options_container.apply-on-all-sites{border:0 none;padding:0}#multisite_options_container.apply-on-all-sites #all_sites_options{border-spacing:0}#multisite_options_container.apply-on-all-sites #all_sites_options td:not(:first-child){display:none}#multisite_options_container #sites_list_container{display:none;overflow:auto}#multisite_options_container #sites_list_container table td{border-top:1px solid #ccc;padding:4px 2px}.fs-modal.fs-modal-license-key-resend .email-address-container{overflow:hidden;padding-right:2px}.fs-modal.fs-modal-license-key-resend.fs-freemium input.email-address{width:300px}.fs-modal.fs-modal-license-key-resend.fs-freemium label{display:block;margin-bottom:10px}.fs-modal.fs-modal-license-key-resend.fs-premium input.email-address{width:100%}.fs-modal.fs-modal-license-key-resend.fs-premium .button-container{float:right;margin-left:7px}@media (max-width: 650px){.fs-modal.fs-modal-license-key-resend.fs-premium .button-container{margin-top:2px}}
2
+ .rtl .fs-modal.fs-modal-license-key-resend .fs-modal-body .input-container>.email-address-container{padding-left:2px;padding-right:0}.rtl .fs-modal.fs-modal-license-key-resend .fs-modal-body .button-container{float:left;margin-right:7px;margin-left:0}a.show-license-resend-modal{margin-top:4px;display:inline-block}.fs-ajax-loader{position:relative;width:170px;height:20px;margin:auto}.fs-ajax-loader .fs-ajax-loader-bar{position:absolute;top:0;background-color:#0074a3;width:20px;height:20px;-webkit-animation-name:bounce_ajaxLoader;-moz-animation-name:bounce_ajaxLoader;-ms-animation-name:bounce_ajaxLoader;-o-animation-name:bounce_ajaxLoader;animation-name:bounce_ajaxLoader;-webkit-animation-duration:1.5s;-moz-animation-duration:1.5s;-ms-animation-duration:1.5s;-o-animation-duration:1.5s;animation-duration:1.5s;animation-iteration-count:infinite;-o-animation-iteration-count:infinite;-ms-animation-iteration-count:infinite;-webkit-animation-iteration-count:infinite;-moz-animation-iteration-count:infinite;-webkit-animation-direction:normal;-moz-animation-direction:normal;-ms-animation-direction:normal;-o-animation-direction:normal;animation-direction:normal;-moz-transform:0.3;-o-transform:0.3;-ms-transform:0.3;-webkit-transform:0.3;transform:0.3}.fs-ajax-loader .fs-ajax-loader-bar-1{left:0px;animation-delay:0.6s;-o-animation-delay:0.6s;-ms-animation-delay:0.6s;-webkit-animation-delay:0.6s;-moz-animation-delay:0.6s}.fs-ajax-loader .fs-ajax-loader-bar-2{left:19px;animation-delay:0.75s;-o-animation-delay:0.75s;-ms-animation-delay:0.75s;-webkit-animation-delay:0.75s;-moz-animation-delay:0.75s}.fs-ajax-loader .fs-ajax-loader-bar-3{left:38px;animation-delay:0.9s;-o-animation-delay:0.9s;-ms-animation-delay:0.9s;-webkit-animation-delay:0.9s;-moz-animation-delay:0.9s}.fs-ajax-loader .fs-ajax-loader-bar-4{left:57px;animation-delay:1.05s;-o-animation-delay:1.05s;-ms-animation-delay:1.05s;-webkit-animation-delay:1.05s;-moz-animation-delay:1.05s}.fs-ajax-loader .fs-ajax-loader-bar-5{left:76px;animation-delay:1.2s;-o-animation-delay:1.2s;-ms-animation-delay:1.2s;-webkit-animation-delay:1.2s;-moz-animation-delay:1.2s}.fs-ajax-loader .fs-ajax-loader-bar-6{left:95px;animation-delay:1.35s;-o-animation-delay:1.35s;-ms-animation-delay:1.35s;-webkit-animation-delay:1.35s;-moz-animation-delay:1.35s}.fs-ajax-loader .fs-ajax-loader-bar-7{left:114px;animation-delay:1.5s;-o-animation-delay:1.5s;-ms-animation-delay:1.5s;-webkit-animation-delay:1.5s;-moz-animation-delay:1.5s}.fs-ajax-loader .fs-ajax-loader-bar-8{left:133px;animation-delay:1.65s;-o-animation-delay:1.65s;-ms-animation-delay:1.65s;-webkit-animation-delay:1.65s;-moz-animation-delay:1.65s}@-moz-keyframes bounce_ajaxLoader{0%{-moz-transform:scale(1);-o-transform:scale(1);-ms-transform:scale(1);-webkit-transform:scale(1);transform:scale(1);background-color:#0074a3}100%{-moz-transform:scale(0.3);-o-transform:scale(0.3);-ms-transform:scale(0.3);-webkit-transform:scale(0.3);transform:scale(0.3);background-color:#fff}}@-ms-keyframes bounce_ajaxLoader{0%{-moz-transform:scale(1);-o-transform:scale(1);-ms-transform:scale(1);-webkit-transform:scale(1);transform:scale(1);background-color:#0074a3}100%{-moz-transform:scale(0.3);-o-transform:scale(0.3);-ms-transform:scale(0.3);-webkit-transform:scale(0.3);transform:scale(0.3);background-color:#fff}}@-o-keyframes bounce_ajaxLoader{0%{-moz-transform:scale(1);-o-transform:scale(1);-ms-transform:scale(1);-webkit-transform:scale(1);transform:scale(1);background-color:#0074a3}100%{-moz-transform:scale(0.3);-o-transform:scale(0.3);-ms-transform:scale(0.3);-webkit-transform:scale(0.3);transform:scale(0.3);background-color:#fff}}@-webkit-keyframes bounce_ajaxLoader{0%{-moz-transform:scale(1);-o-transform:scale(1);-ms-transform:scale(1);-webkit-transform:scale(1);transform:scale(1);background-color:#0074a3}100%{-moz-transform:scale(0.3);-o-transform:scale(0.3);-ms-transform:scale(0.3);-webkit-transform:scale(0.3);transform:scale(0.3);background-color:#fff}}@keyframes bounce_ajaxLoader{0%{-moz-transform:scale(1);-o-transform:scale(1);-ms-transform:scale(1);-webkit-transform:scale(1);transform:scale(1);background-color:#0074a3}100%{-moz-transform:scale(0.3);-o-transform:scale(0.3);-ms-transform:scale(0.3);-webkit-transform:scale(0.3);transform:scale(0.3);background-color:#fff}}.fs-modal-auto-install #request-filesystem-credentials-form h2,.fs-modal-auto-install #request-filesystem-credentials-form .request-filesystem-credentials-action-buttons{display:none}.fs-modal-auto-install #request-filesystem-credentials-form input[type=password],.fs-modal-auto-install #request-filesystem-credentials-form input[type=email],.fs-modal-auto-install #request-filesystem-credentials-form input[type=text]{-webkit-appearance:none;padding:10px 10px 5px 10px;width:300px;max-width:100%}.fs-modal-auto-install #request-filesystem-credentials-form>div,.fs-modal-auto-install #request-filesystem-credentials-form label,.fs-modal-auto-install #request-filesystem-credentials-form fieldset{width:300px;max-width:100%;margin:0 auto;display:block}.button-primary.warn{box-shadow:0 1px 0 #d2593c;text-shadow:0 -1px 1px #d2593c,1px 0 1px #d2593c,0 1px 1px #d2593c,-1px 0 1px #d2593c;background:#f56a48;border-color:#ec6544 #d2593c #d2593c}.button-primary.warn:hover{background:#fd6d4a;border-color:#d2593c}.button-primary.warn:focus{box-shadow:0 1px 0 #dd6041,0 0 2px 1px #e4a796}.button-primary.warn:active{background:#dd6041;border-color:#d2593c;box-shadow:inset 0 2px 0 #d2593c}.button-primary.warn.disabled{color:#f5b3a1 !important;background:#e76444 !important;border-color:#d85e40 !important;text-shadow:0 -1px 0 rgba(0,0,0,0.1) !important}
vendor/freemius/assets/css/admin/license-activation.css DELETED
@@ -1 +0,0 @@
1
- .fs-modal{position:fixed;overflow:auto;height:100%;width:100%;top:0;z-index:100000;display:none;background:rgba(0,0,0,0.6)}.fs-modal .fs-modal-dialog{background:transparent;position:absolute;left:50%;margin-left:-298px;padding-bottom:30px;top:-100%;z-index:100001;width:596px}@media (max-width: 650px){.fs-modal .fs-modal-dialog{margin-left:-50%;box-sizing:border-box;padding-left:10px;padding-right:10px;width:100%}.fs-modal .fs-modal-dialog .fs-modal-panel>h3>strong{font-size:1.3em}}.fs-modal.active{display:block}.fs-modal.active:before{display:block}.fs-modal.active .fs-modal-dialog{top:10%}.fs-modal .fs-modal-body,.fs-modal .fs-modal-footer{border:0;background:#fefefe;padding:20px}.fs-modal .fs-modal-body{border-bottom:0}.fs-modal .fs-modal-body .license-activation-message{margin:0;display:none}.fs-modal .fs-modal-body input.license_key{width:100%}.fs-modal .fs-modal-body p{font-size:14px}.fs-modal .fs-modal-body h2{font-size:20px}.fs-modal .fs-modal-body>div{margin-top:10px}.fs-modal .fs-modal-body>div h2{font-weight:bold;font-size:20px;margin-top:0}.fs-modal .fs-modal-footer{border-top:#eeeeee solid 1px;text-align:right}.fs-modal .fs-modal-footer>.button{margin:0 7px}.fs-modal .fs-modal-footer>.button:first-child{margin:0}.fs-modal .fs-modal-panel:not(.active){display:none}body.has-fs-modal{overflow:hidden}
 
vendor/freemius/assets/scss/_colors.scss CHANGED
@@ -44,6 +44,17 @@ $button-secondary-bkg: #333;
44
  $button-secondary-color: $fms-white;
45
  $featured-color: #6bc406;
46
  $wp-selected-color: #0074a3;
 
 
 
 
 
 
 
 
 
 
 
47
 
48
  $wordpress_color: #01749A;
49
  $blogger_color: #ff8100;
44
  $button-secondary-color: $fms-white;
45
  $featured-color: #6bc406;
46
  $wp-selected-color: #0074a3;
47
+ $wp-button-alert-border-color: #d2593c;
48
+ $wp-button-alert-border-top-color: #ec6544;
49
+ $wp-button-alert-shadow-color: #d2593c;
50
+ $wp-button-alert-focused-shadow1-color: #dd6041;
51
+ $wp-button-alert-focused-shadow2-color: #e4a796;
52
+ $wp-button-alert-background-color: #f56a48;
53
+ $wp-button-alert-hovered-background-color: #fd6d4a;
54
+ $wp-button-alert-active-background-color: #dd6041;
55
+ $wp-button-alert-disabled-color: #f5b3a1;
56
+ $wp-button-alert-disabled-background-color: #e76444;
57
+ $wp-button-alert-disabled-border-color: #d85e40;
58
 
59
  $wordpress_color: #01749A;
60
  $blogger_color: #ff8100;
vendor/freemius/assets/scss/admin/_buttons.scss ADDED
@@ -0,0 +1,28 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ .button-primary.warn {
2
+ box-shadow: 0 1px 0 $wp-button-alert-shadow-color;
3
+ text-shadow: 0 -1px 1px $wp-button-alert-shadow-color, 1px 0 1px $wp-button-alert-shadow-color, 0 1px 1px $wp-button-alert-shadow-color, -1px 0 1px $wp-button-alert-shadow-color;
4
+ background: $wp-button-alert-background-color;
5
+ border-color: $wp-button-alert-border-top-color $wp-button-alert-border-color $wp-button-alert-border-color;
6
+
7
+ &:hover {
8
+ background: $wp-button-alert-hovered-background-color;
9
+ border-color: $wp-button-alert-border-color;
10
+ }
11
+
12
+ &:focus {
13
+ box-shadow: 0 1px 0 $wp-button-alert-focused-shadow1-color, 0 0 2px 1px $wp-button-alert-focused-shadow2-color;
14
+ }
15
+
16
+ &:active {
17
+ background: $wp-button-alert-active-background-color;
18
+ border-color: $wp-button-alert-border-color;
19
+ box-shadow: inset 0 2px 0 $wp-button-alert-shadow-color;
20
+ }
21
+
22
+ &.disabled {
23
+ color: $wp-button-alert-disabled-color !important;
24
+ background: $wp-button-alert-disabled-background-color !important;
25
+ border-color: $wp-button-alert-disabled-border-color !important;
26
+ text-shadow: 0 -1px 0 rgba(0,0,0,.1) !important;
27
+ }
28
+ }
vendor/freemius/assets/scss/admin/_plugin-upgrade-notice.scss ADDED
@@ -0,0 +1,8 @@
 
 
 
 
 
 
 
 
1
+ .plugins p.fs-upgrade-notice
2
+ {
3
+ border: 0;
4
+ background-color: #d54e21;
5
+ padding: 10px;
6
+ color: #f9f9f9;
7
+ margin-top: 10px;
8
+ }
vendor/freemius/assets/scss/admin/_subscription-cancellation.scss ADDED
@@ -0,0 +1,30 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ .fs-modal.fs-modal-subscription-cancellation {
2
+ .fs-price-increase-warning {
3
+ color: red;
4
+ font-weight: bold;
5
+ padding: 0 25px;
6
+ margin-bottom: 0;
7
+ }
8
+
9
+ ul.subscription-actions label {
10
+ input {
11
+ float: left;
12
+ top: 5px;
13
+ position: relative;
14
+
15
+ .rtl & {
16
+ float: right;
17
+ }
18
+ }
19
+
20
+ span {
21
+ display: block;
22
+ margin-left: 24px;
23
+
24
+ .rtl & {
25
+ margin-left: 0;
26
+ margin-right: 24px;
27
+ }
28
+ }
29
+ }
30
+ }
vendor/freemius/assets/scss/admin/common.scss CHANGED
@@ -1,7 +1,7 @@
1
  @import "../start";
2
  @import "themes";
3
 
4
- #iframe
5
  {
6
  line-height: 0;
7
  font-size: 0;
@@ -215,4 +215,6 @@ span.fs-submenu-item.fs-sub:before
215
  h2 {
216
  text-align: left;
217
  }
218
- }
 
 
1
  @import "../start";
2
  @import "themes";
3
 
4
+ #fs_frame
5
  {
6
  line-height: 0;
7
  font-size: 0;
215
  h2 {
216
  text-align: left;
217
  }
218
+ }
219
+
220
+ @import "plugin-upgrade-notice";
vendor/freemius/assets/scss/admin/dialog-boxes.scss CHANGED
@@ -1,8 +1,10 @@
1
  @import "../start";
2
  @import "modal-common";
3
  @import "deactivation-feedback";
 
4
  @import "license-activation";
5
  @import "multisite-options";
6
  @import "license-key-resend";
7
  @import "ajax-loader";
8
- @import "auto-install";
 
1
  @import "../start";
2
  @import "modal-common";
3
  @import "deactivation-feedback";
4
+ @import "subscription-cancellation";
5
  @import "license-activation";
6
  @import "multisite-options";
7
  @import "license-key-resend";
8
  @import "ajax-loader";
9
+ @import "auto-install";
10
+ @import "buttons";
vendor/freemius/includes/class-freemius.php CHANGED
@@ -33,6 +33,12 @@
33
  * @var string
34
  */
35
  private $_plugin_basename;
 
 
 
 
 
 
36
  /**
37
  * @since 1.0.0
38
  *
@@ -671,11 +677,12 @@
671
  version_compare( $sdk_version, '1.2.3', '>=' )
672
  ) {
673
  /**
674
- * Starting from version 1.2.3, paths are stored as relative paths and not absolute paths; so when upgrading to 1.2.3, make paths relative.
 
675
  *
676
  * @author Leo Fajardo (@leorw)
677
  */
678
- $this->make_paths_relative();
679
  }
680
 
681
  if ( version_compare( $sdk_prev_version, '1.1.5', '<' ) &&
@@ -699,6 +706,25 @@
699
 
700
  }
701
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
702
  }
703
 
704
  /**
@@ -824,30 +850,12 @@
824
  }
825
 
826
  /**
827
- * Makes paths relative.
828
  *
829
  * @author Leo Fajardo (@leorw)
830
  * @since 1.2.3
831
  */
832
- private function make_paths_relative() {
833
- $id_slug_type_path_map = self::$_accounts->get_option( 'id_slug_type_path_map', array() );
834
-
835
- if ( isset( $id_slug_type_path_map[ $this->_module_id ]['path'] ) ) {
836
- $id_slug_type_path_map[ $this->_module_id ]['path'] = $this->get_relative_path( $id_slug_type_path_map[ $this->_module_id ]['path'] );
837
-
838
- self::$_accounts->set_option( 'id_slug_type_path_map', $id_slug_type_path_map, true );
839
- }
840
-
841
- if ( isset( $this->_storage->plugin_main_file ) ) {
842
- $plugin_main_file = $this->_storage->plugin_main_file;
843
-
844
- if ( isset( $plugin_main_file->path ) ) {
845
- $this->_storage->plugin_main_file->path = $this->get_relative_path( $this->_storage->plugin_main_file->path );
846
- } else if ( isset( $plugin_main_file->prev_path ) ) {
847
- $this->_storage->plugin_main_file->prev_path = $this->get_relative_path( $this->_storage->plugin_main_file->prev_path );
848
- }
849
- }
850
-
851
  // Remove invalid path that is still associated with the current slug if there's any.
852
  $file_slug_map = self::$_accounts->get_option( 'file_slug_map', array() );
853
  foreach ( $file_slug_map as $plugin_basename => $slug ) {
@@ -1230,6 +1238,22 @@
1230
  <?php
1231
  }
1232
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1233
  /**
1234
  * @author Vova Feldman (@svovaf)
1235
  * @since 1.0.9
@@ -1241,6 +1265,26 @@
1241
  add_action( 'plugins_loaded', array( &$this, '_hook_action_links_and_register_account_hooks' ) );
1242
 
1243
  if ( $this->is_plugin() ) {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1244
  $plugin_dir = dirname( $this->_plugin_dir_path ) . '/';
1245
 
1246
  /**
@@ -1408,6 +1452,84 @@
1408
  }
1409
  }
1410
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1411
  /**
1412
  * Keeping the uninstall hook registered for free or premium plugin version may result to a fatal error that
1413
  * could happen when a user tries to uninstall either version while one of them is still active. Uninstalling a
@@ -1428,23 +1550,37 @@
1428
 
1429
  /**
1430
  * @since 1.2.0 Invalidate module's main file cache, otherwise, FS_Plugin_Updater will not fetch updates.
 
 
1431
  */
1432
- private function clear_module_main_file_cache() {
1433
  if ( ! isset( $this->_storage->plugin_main_file ) ||
1434
- empty( $this->_storage->plugin_main_file->path )
1435
  ) {
1436
  return;
1437
  }
1438
 
1439
- $plugin_main_file = clone $this->_storage->plugin_main_file;
 
 
 
 
 
 
 
 
 
 
 
1440
 
1441
- // Store cached path (2nd layer cache).
1442
- $plugin_main_file->prev_path = $plugin_main_file->path;
1443
 
1444
- // Clear cached path.
1445
- unset( $plugin_main_file->path );
1446
 
1447
- $this->_storage->plugin_main_file = $plugin_main_file;
 
1448
 
1449
  /**
1450
  * Clear global cached path.
@@ -1491,6 +1627,11 @@
1491
  array( &$this, '_submit_uninstall_reason_action' )
1492
  );
1493
 
 
 
 
 
 
1494
  if ( ! $this->is_addon() || $this->is_parent_plugin_installed() ) {
1495
  if ( ( $this->is_plugin() && self::is_plugins_page() ) ||
1496
  ( $this->is_theme() && self::is_themes_page() )
@@ -1615,7 +1756,7 @@
1615
 
1616
  return fs_normalize_path( trailingslashit( $is_plugin ?
1617
  WP_PLUGIN_DIR :
1618
- get_theme_root() ) );
1619
  }
1620
 
1621
  /**
@@ -1680,11 +1821,11 @@
1680
  private function get_caller_main_file_and_type() {
1681
  self::require_plugin_essentials();
1682
 
1683
- $all_plugins = get_plugins();
1684
  $all_plugins_paths = array();
1685
 
1686
  // Get active plugin's main files real full names (might be symlinks).
1687
- foreach ( $all_plugins as $relative_path => &$data ) {
1688
  if ( false === strpos( fs_normalize_path( $relative_path ), '/' ) ) {
1689
  /**
1690
  * Ignore plugins that don't have a folder (e.g. Hello Dolly) since they
@@ -1702,7 +1843,7 @@
1702
  $caller_file_candidate = false;
1703
  $caller_map = array();
1704
  $module_type = WP_FS__MODULE_TYPE_PLUGIN;
1705
- $themes_dir = fs_normalize_path( get_theme_root() );
1706
 
1707
  for ( $i = 1, $bt = debug_backtrace(), $len = count( $bt ); $i < $len; $i ++ ) {
1708
  if ( empty( $bt[ $i ]['file'] ) ) {
@@ -1722,7 +1863,10 @@
1722
  'requir' . 'e_once',
1723
  'requir' . 'e',
1724
  'includ' . 'e_once',
1725
- 'includ' . 'e'
 
 
 
1726
  ) )
1727
  ) {
1728
  // Ignore call stack hooks and files inclusion.
@@ -2058,6 +2202,51 @@
2058
  exit;
2059
  }
2060
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2061
  /**
2062
  * @author Leo Fajardo (@leorw)
2063
  * @since 2.0.2
@@ -2134,16 +2323,18 @@
2134
  * @since 1.2.2
2135
  *
2136
  * @param string|number $id_or_slug
 
2137
  *
2138
  * @return number|false
2139
  */
2140
- private static function get_module_id( $id_or_slug ) {
2141
  if ( is_numeric( $id_or_slug ) ) {
2142
  return $id_or_slug;
2143
  }
2144
 
2145
  foreach ( self::$_instances as $instance ) {
2146
- if ( $instance->is_plugin() && ( $id_or_slug === $instance->get_slug() ) ) {
 
2147
  return $instance->get_id();
2148
  }
2149
  }
@@ -2170,15 +2361,16 @@
2170
  * @author Vova Feldman (@svovaf)
2171
  * @since 1.0.1
2172
  *
2173
- * @param $plugin_file
 
2174
  *
2175
  * @return false|Freemius
2176
  */
2177
- static function get_instance_by_file( $plugin_file ) {
2178
  $slug = self::find_slug_by_basename( $plugin_file );
2179
 
2180
  return ( false !== $slug ) ?
2181
- self::instance( self::get_module_id( $slug ) ) :
2182
  false;
2183
  }
2184
 
@@ -2292,10 +2484,13 @@
2292
  function is_site_activation_mode( $and_on = true ) {
2293
  return (
2294
  ( $this->is_on() || ! $and_on ) &&
2295
- ( ! $this->is_registered() ||
2296
- ( $this->is_only_premium() && ! $this->has_features_enabled_license() ) ) &&
2297
- ( ! $this->is_enable_anonymous() ||
2298
- ( ! $this->is_anonymous() && ! $this->is_pending_activation() ) )
 
 
 
2299
  );
2300
  }
2301
 
@@ -2330,7 +2525,7 @@
2330
  return false;
2331
  }
2332
 
2333
- if ( $this->is_network_anonymous() ) {
2334
  // Super-admin skipped the connection network wide -> not activation mode.
2335
  return false;
2336
  }
@@ -2451,7 +2646,7 @@
2451
  self::require_plugin_essentials();
2452
 
2453
  $active_plugin = array();
2454
- $all_plugins = get_plugins();
2455
  $active_plugins_basenames = self::get_active_plugins_basenames( $blog_id );
2456
 
2457
  foreach ( $active_plugins_basenames as $plugin_basename ) {
@@ -2477,6 +2672,11 @@
2477
  get_option( 'active_plugins' );
2478
 
2479
  $active = array();
 
 
 
 
 
2480
  foreach ( $active_basenames as $basename ) {
2481
  $active[ $basename ] = array(
2482
  'is_active' => true,
@@ -2501,7 +2701,7 @@
2501
  private static function get_all_plugins( $blog_id = 0 ) {
2502
  self::require_plugin_essentials();
2503
 
2504
- $all_plugins = get_plugins();
2505
 
2506
  $active_plugins_basenames = self::get_active_plugins_basenames( $blog_id );
2507
 
@@ -2533,7 +2733,7 @@
2533
  private static function get_network_plugins() {
2534
  self::require_plugin_essentials();
2535
 
2536
- $all_plugins = get_plugins();
2537
 
2538
  $network_active_basenames = is_multisite() ?
2539
  get_site_option( 'active_sitewide_plugins' ) :
@@ -2630,26 +2830,28 @@
2630
  self::$_accounts = FS_Options::instance( WP_FS__ACCOUNTS_OPTION_NAME, true );
2631
 
2632
  if ( is_multisite() ) {
 
 
 
 
 
 
 
2633
  /**
2634
- * If the id_slug_type_path_map exists on the site level but doesn't exist on the
2635
  * network level storage, it means that we need to process the storage with migration.
2636
  *
2637
- * The code in this `if` scope will only be executed once and only for the first site that will execute it because once we migrate the storage data, id_slug_type_path_map will be already set in the network level storage.
2638
  *
2639
  * @author Vova Feldman (@svovaf)
2640
  * @since 2.0.0
2641
  */
2642
- if ( null === self::$_accounts->get_option( 'id_slug_type_path_map', null, true ) &&
2643
- null !== self::$_accounts->get_option( 'id_slug_type_path_map', null, false )
 
 
2644
  ) {
2645
- self::migrate_accounts_to_network();
2646
-
2647
- // Migrate API options from site level to network level.
2648
- $api_network_options = FS_Option_Manager::get_manager( WP_FS__OPTIONS_OPTION_NAME, true, true );
2649
- $api_network_options->migrate_to_network();
2650
-
2651
- // Migrate API cache to network level storage.
2652
- FS_Cache_Manager::get_manager( WP_FS__API_CACHE_OPTION_NAME )->migrate_to_network();
2653
  }
2654
  }
2655
 
@@ -2675,10 +2877,30 @@
2675
  }
2676
 
2677
  add_action( 'admin_footer', array( 'Freemius', '_enrich_ajax_url' ) );
 
 
2678
 
2679
  self::$_statics_loaded = true;
2680
  }
2681
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2682
  #----------------------------------------------------------------------------------
2683
  #region Localization
2684
  #----------------------------------------------------------------------------------
@@ -2755,6 +2977,10 @@
2755
  * @since 1.1.7.3
2756
  */
2757
  static function _toggle_debug_mode() {
 
 
 
 
2758
  $is_on = fs_request_get( 'is_on', false, 'post' );
2759
 
2760
  if ( fs_request_is_post() && in_array( $is_on, array( 0, 1 ) ) ) {
@@ -2786,8 +3012,16 @@
2786
  * @since 1.2.1.7
2787
  */
2788
  static function _get_db_option() {
 
 
2789
  $option_name = fs_request_get( 'option_name' );
2790
 
 
 
 
 
 
 
2791
  $value = get_option( $option_name );
2792
 
2793
  $result = array(
@@ -2810,7 +3044,16 @@
2810
  * @since 1.2.1.7
2811
  */
2812
  static function _set_db_option() {
2813
- $option_name = fs_request_get( 'option_name' );
 
 
 
 
 
 
 
 
 
2814
  $option_value = fs_request_get( 'option_value' );
2815
 
2816
  if ( ! empty( $option_value ) ) {
@@ -2905,6 +3148,10 @@
2905
  }
2906
 
2907
  fs_redirect( $download_url );
 
 
 
 
2908
  }
2909
  }
2910
 
@@ -4044,14 +4291,16 @@
4044
  * @author Vova Feldman (@svovaf)
4045
  */
4046
  if ( $this->is_user_in_admin() &&
4047
- ! $this->is_addon() &&
4048
- $this->has_addons() &&
4049
- 'plugin-information' === fs_request_get( 'tab', false ) &&
4050
- $this->get_id() == fs_request_get( 'parent_plugin_id', false )
 
 
4051
  ) {
4052
  require_once WP_FS__DIR_INCLUDES . '/fs-plugin-info-dialog.php';
4053
 
4054
- new FS_Plugin_Info_Dialog( $this );
4055
  }
4056
 
4057
  // Check if Freemius is on for the current plugin.
@@ -4165,7 +4414,21 @@
4165
  * @author Vova Feldman
4166
  * @since 1.2.1.6
4167
  */
4168
- if ( $this->is_premium() && $this->has_release_on_freemius() ) {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4169
  FS_Plugin_Updater::instance( $this );
4170
  }
4171
 
@@ -4208,6 +4471,26 @@
4208
  }
4209
  }
4210
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4211
  /**
4212
  * @author Leo Fajardo (@leorw)
4213
  *
@@ -4644,16 +4927,20 @@
4644
  $this->_plugin :
4645
  new FS_Plugin();
4646
 
 
 
4647
  $plugin->update( array(
4648
  'id' => $id,
4649
  'type' => $this->get_option( $plugin_info, 'type', $this->_module_type ),
4650
  'public_key' => $public_key,
4651
  'slug' => $this->_slug,
 
4652
  'parent_plugin_id' => $parent_id,
4653
  'version' => $this->get_plugin_version(),
4654
- 'title' => $this->get_plugin_name(),
4655
  'file' => $this->_plugin_basename,
4656
  'is_premium' => $this->get_bool_option( $plugin_info, 'is_premium', true ),
 
4657
  'is_live' => $this->get_bool_option( $plugin_info, 'is_live', true ),
4658
  'affiliate_moderation' => $this->get_option( $plugin_info, 'has_affiliation' ),
4659
  ) );
@@ -5034,7 +5321,7 @@
5034
  }
5035
 
5036
  $addon = $this->get_addon( $addon_id );
5037
- $premium_basename = "{$addon->slug}-premium/{$addon->slug}.php";
5038
 
5039
  if ( file_exists( fs_normalize_path( WP_PLUGIN_DIR . '/' . $premium_basename ) ) ) {
5040
  return $premium_basename;
@@ -5042,9 +5329,9 @@
5042
 
5043
  $all_plugins = $this->get_all_plugins();
5044
 
5045
- foreach ( $all_plugins as $basename => &$data ) {
5046
  if ( $addon->slug === $data['slug'] ||
5047
- $addon->slug . '-premium' === $data['slug']
5048
  ) {
5049
  return $basename;
5050
  }
@@ -5284,7 +5571,7 @@
5284
  if ( ! isset( $this->_is_anonymous ) ) {
5285
  if ( $this->is_network_anonymous() ) {
5286
  $this->_is_anonymous = true;
5287
- } else {
5288
  if ( ! isset( $this->_storage->is_anonymous ) ) {
5289
  // Not skipped.
5290
  $this->_is_anonymous = false;
@@ -5475,6 +5762,20 @@
5475
  $this->_storage->store( "{$name}_timestamp", time() );
5476
  }
5477
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
5478
  /**
5479
  * Check if cron was executed in the last $period of seconds.
5480
  *
@@ -5489,7 +5790,7 @@
5489
  private function is_cron_executed( $name, $period = WP_FS__TIME_24_HOURS_IN_SEC ) {
5490
  $this->_logger->entrance( $name );
5491
 
5492
- $last_execution = $this->set_cron_execution_timestamp( $name );
5493
 
5494
  if ( ! is_numeric( $last_execution ) ) {
5495
  return false;
@@ -5750,12 +6051,14 @@
5750
  }
5751
  }
5752
 
 
 
5753
  foreach ( $users_2_blog_ids as $user_id => $blog_ids ) {
5754
  if ( 0 < $blog_ids[0] ) {
5755
  $this->switch_to_blog( $blog_ids[0] );
5756
  }
5757
 
5758
- call_user_func_array( $callable, array( $blog_ids ) );
5759
 
5760
  foreach ( $blog_ids as $blog_id ) {
5761
  $this->do_action( "after_{$name}_cron", $blog_id );
@@ -5763,6 +6066,8 @@
5763
  }
5764
 
5765
  if ( is_multisite() ) {
 
 
5766
  $this->do_action( "after_{$name}_cron_multisite" );
5767
  }
5768
  }
@@ -5834,13 +6139,16 @@
5834
  * @author Vova Feldman (@svovaf)
5835
  * @since 2.0.0
5836
  *
5837
- * @param int[] $blog_ids
 
 
 
5838
  */
5839
- function _sync_cron_method( array $blog_ids ) {
5840
  if ( $this->is_registered() ) {
5841
  if ( $this->has_paid_plan() ) {
5842
  // Initiate background plan sync.
5843
- $this->_sync_license( true );
5844
 
5845
  if ( $this->is_paying() ) {
5846
  // Check for premium plugin updates.
@@ -5987,7 +6295,7 @@
5987
  * @param int $except_blog_id Since 2.0.0 when running in a multisite network environment, the cron execution is consolidated. This param allows excluding excluded specified blog ID from being the cron executor.
5988
  */
5989
  private function schedule_install_sync( $except_blog_id = 0 ) {
5990
- $this->schedule_cron( 'install_sync', 'install_sync', 'single', 0, false, $except_blog_id );
5991
  }
5992
 
5993
  /**
@@ -6055,9 +6363,10 @@
6055
  * @author Vova Feldman (@svovaf)
6056
  * @since 2.0.0
6057
  *
6058
- * @param int[] $blog_ids
 
6059
  */
6060
- function _sync_install_cron_method( array $blog_ids ) {
6061
  if ( $this->is_registered() ) {
6062
  if ( 1 < count( $blog_ids ) ) {
6063
  $this->sync_installs( array(), true );
@@ -6161,6 +6470,7 @@
6161
  if ( ! $this->is_addon() &&
6162
  ! ( ! $this->_is_network_active && fs_is_network_admin() ) &&
6163
  (
 
6164
  // Not registered nor anonymous.
6165
  ( ! $this->is_registered() && ! $this->is_anonymous() ) ||
6166
  // OR, network level and in network upgrade mode.
@@ -6177,14 +6487,18 @@
6177
  * @since 1.2.2
6178
  */
6179
  if ( $this->is_theme()
6180
- && $this->is_only_premium()
6181
  && ! $this->has_settings_menu()
6182
  && ! isset( $_REQUEST['fs_action'] )
6183
  && $this->can_activate_previous_theme()
6184
  ) {
6185
- $this->activate_previous_theme();
 
 
 
6186
 
6187
- return;
 
 
6188
  }
6189
 
6190
  if ( ! fs_is_network_admin() &&
@@ -6284,7 +6598,7 @@
6284
  $this->_module_type,
6285
  sprintf( '<b><a href="%s">%s</a></b>',
6286
  $this->get_activation_url(),
6287
- sprintf( $this->get_text_inline( 'Opt in to make "%s" Better!', 'optin-x-now' ), $this->get_plugin_name() )
6288
  )
6289
  ),
6290
  'connect_account',
@@ -6746,6 +7060,20 @@
6746
  }
6747
  }
6748
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
6749
  if ( ! isset( $this->_storage->is_plugin_new_install ) ) {
6750
  /**
6751
  * If no previous version of plugin's version exist, it means that it's either
@@ -7015,7 +7343,7 @@
7015
  private function remove_sdk_reference() {
7016
  global $fs_active_plugins;
7017
 
7018
- foreach ( $fs_active_plugins->plugins as $sdk_path => &$data ) {
7019
  if ( $this->_plugin_basename == $data->plugin_path ) {
7020
  unset( $fs_active_plugins->plugins[ $sdk_path ] );
7021
  break;
@@ -7197,6 +7525,23 @@
7197
  }
7198
  }
7199
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
7200
  /**
7201
  * Clears the anonymous mode and redirects to the opt-in screen.
7202
  *
@@ -7210,6 +7555,8 @@
7210
 
7211
  $this->reset_anonymous_mode( fs_is_network_admin() );
7212
 
 
 
7213
  fs_redirect( $this->get_activation_url() );
7214
  }
7215
 
@@ -7649,39 +7996,43 @@
7649
  $include_plugins = true,
7650
  $include_themes = true
7651
  ) {
7652
- /**
7653
- * @since 1.1.8 Also send plugin updates.
7654
- */
7655
- if ( $include_plugins && ! isset( $override['plugins'] ) ) {
7656
- $plugins = $this->get_plugins_data_for_api();
7657
- if ( ! empty( $plugins ) ) {
7658
- $override['plugins'] = $plugins;
 
 
7659
  }
7660
  }
7661
- /**
7662
- * @since 1.1.8 Also send themes updates.
7663
- */
7664
- if ( $include_themes && ! isset( $override['themes'] ) ) {
7665
- $themes = $this->get_themes_data_for_api();
7666
- if ( ! empty( $themes ) ) {
7667
- $override['themes'] = $themes;
 
 
 
7668
  }
7669
  }
7670
 
7671
- return array_merge( array(
7672
- 'version' => $this->get_plugin_version(),
7673
- 'is_premium' => $this->is_premium(),
7674
- 'language' => get_bloginfo( 'language' ),
7675
- 'charset' => get_bloginfo( 'charset' ),
7676
- 'platform_version' => get_bloginfo( 'version' ),
7677
- 'sdk_version' => $this->version,
7678
- 'programming_language_version' => phpversion(),
7679
- 'title' => get_bloginfo( 'name' ),
7680
- 'url' => get_site_url(),
7681
  // Special params.
7682
- 'is_active' => true,
7683
- 'is_disconnected' => $this->is_tracking_prohibited(),
7684
- 'is_uninstalled' => false,
7685
  ), $override );
7686
  }
7687
 
@@ -7726,12 +8077,10 @@
7726
  // }
7727
 
7728
  // Common properties.
7729
- $common = array_merge( array(
7730
- 'version' => $this->get_plugin_version(),
7731
- 'is_premium' => $this->is_premium(),
7732
- 'sdk_version' => $this->version,
7733
- 'programming_language_version' => phpversion(),
7734
- 'platform_version' => get_bloginfo( 'version' ),
7735
  ), $override );
7736
 
7737
 
@@ -7885,28 +8234,56 @@
7885
  $params = $this->get_install_diff_for_api( $check_properties, $this->_site, $override );
7886
  }
7887
 
7888
- if ( 0 < count( $params ) ) {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
7889
  if ( ! is_multisite() ) {
7890
  // Update last install sync timestamp.
7891
  $this->set_cron_execution_timestamp( 'install_sync' );
7892
  }
7893
 
7894
  $params['uid'] = $this->get_anonymous_id();
 
7895
 
7896
- // Send updated values to FS.
7897
- $site = $this->get_api_site_scope()->call( '/', 'put', $params );
7898
 
7899
- if ( $this->is_api_result_entity( $site ) ) {
7900
- if ( ! is_multisite() ) {
7901
- // I successfully sent install update, clear scheduled sync if exist.
7902
- $this->clear_install_sync_cron();
7903
- }
7904
- }
7905
 
7906
- return $site;
 
 
 
 
 
 
 
 
 
 
7907
  }
7908
 
7909
- return false;
7910
  }
7911
 
7912
  /**
@@ -7925,24 +8302,70 @@
7925
 
7926
  $installs_data = $this->get_installs_data_for_api( $override, ! $flush );
7927
 
 
7928
  if ( empty( $installs_data ) ) {
7929
- return false;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
7930
  }
7931
 
7932
- // Update last install sync timestamp.
7933
- $this->set_cron_execution_timestamp( 'install_sync' );
 
 
 
 
 
 
 
 
 
 
7934
 
7935
  // Send updated values to FS.
7936
  $result = $this->get_api_user_scope()->call( "/plugins/{$this->_plugin->id}/installs.json", 'put', $installs_data );
7937
 
7938
- if ( $this->is_api_result_object( $result, 'installs' ) ) {
7939
- // I successfully sent installs update, clear scheduled sync if exist.
7940
  $this->clear_install_sync_cron();
7941
  }
7942
 
7943
  return $result;
7944
  }
7945
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
7946
  /**
7947
  * Update install only if changed.
7948
  *
@@ -8147,14 +8570,59 @@
8147
  // @todo Decide if we want to delete plugin information from db.
8148
  }
8149
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
8150
  /**
8151
  * @author Vova Feldman (@svovaf)
8152
  * @since 1.1.1
 
8153
  *
8154
  * @return string
8155
  */
8156
  function premium_plugin_basename() {
8157
- return "{$this->_slug}-premium/" . basename( $this->_free_plugin_basename );
 
 
 
 
 
 
 
8158
  }
8159
 
8160
  /**
@@ -8293,13 +8761,29 @@
8293
  }
8294
 
8295
  /**
 
 
 
 
 
 
 
 
 
 
 
 
 
 
8296
  * @author Vova Feldman (@svovaf)
8297
  * @since 1.2.1.7
8298
  *
8299
  * @return string Plugin slug.
8300
  */
8301
  function get_target_folder_name() {
8302
- return $this->_slug . ( $this->can_use_premium_code() ? '-premium' : '' );
 
 
8303
  }
8304
 
8305
  /**
@@ -8370,31 +8854,63 @@
8370
  * @author Vova Feldman (@svovaf)
8371
  * @since 1.0.9
8372
  *
 
 
8373
  * @return string
8374
  */
8375
- function get_plugin_name() {
8376
  $this->_logger->entrance();
8377
 
 
 
 
 
 
8378
  if ( ! isset( $this->_plugin_name ) ) {
8379
- $plugin_data = $this->get_plugin_data();
 
 
 
 
 
 
 
 
8380
 
8381
- // Get name.
8382
- $this->_plugin_name = $plugin_data['Name'];
 
 
 
 
 
 
 
 
 
 
 
8383
 
8384
- // Check if plugin name contains "(Premium)" suffix and remove it.
8385
- $suffix = ' (premium)';
8386
- $suffix_len = strlen( $suffix );
8387
 
8388
- if ( strlen( $plugin_data['Name'] ) > $suffix_len &&
8389
- $suffix === substr( strtolower( $plugin_data['Name'] ), - $suffix_len )
8390
- ) {
8391
- $this->_plugin_name = substr( $plugin_data['Name'], 0, - $suffix_len );
8392
- }
 
 
8393
 
8394
- $this->_logger->departure( 'Name = ' . $this->_plugin_name );
 
 
 
 
 
8395
  }
8396
 
8397
- return $this->_plugin_name;
8398
  }
8399
 
8400
  /**
@@ -9100,7 +9616,16 @@
9100
  * @return bool
9101
  */
9102
  function is_premium() {
9103
- return $this->_plugin->is_premium;
 
 
 
 
 
 
 
 
 
9104
  }
9105
 
9106
  /**
@@ -10483,11 +11008,61 @@
10483
  */
10484
  function _add_license_activation_dialog_box() {
10485
  $vars = array(
10486
- 'id' => $this->_module_id,
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
10487
  );
10488
 
10489
- fs_require_template( 'forms/license-activation.php', $vars );
10490
- fs_require_template( 'forms/resend-key.php', $vars );
10491
  }
10492
 
10493
  /**
@@ -10574,7 +11149,7 @@
10574
  return;
10575
  }
10576
 
10577
- if ( ! $this->is_premium() || $this->has_active_valid_license() ) {
10578
  // This is relevant only to the free versions and premium versions without an active license.
10579
  return;
10580
  }
@@ -10674,7 +11249,7 @@
10674
  'license_key' => $fs->apply_filters( 'license_key', $license_key )
10675
  );
10676
 
10677
- $install = $api->call( '/', 'put', $params );
10678
 
10679
  if ( FS_Api::is_api_error( $install ) ) {
10680
  $error = FS_Api::is_api_error_object( $install ) ?
@@ -10767,6 +11342,10 @@
10767
  }
10768
  }
10769
 
 
 
 
 
10770
  $result = array(
10771
  'success' => ( false === $error )
10772
  );
@@ -11021,6 +11600,34 @@
11021
  static function get_current_page() {
11022
  if ( ! isset( self::$_pagenow ) ) {
11023
  global $pagenow;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
11024
 
11025
  self::$_pagenow = $pagenow;
11026
 
@@ -11052,6 +11659,16 @@
11052
  return ( 'plugins.php' === self::get_current_page() );
11053
  }
11054
 
 
 
 
 
 
 
 
 
 
 
11055
  /**
11056
  * @author Leo Fajardo (@leorw)
11057
  * @since 2.0.2
@@ -11319,6 +11936,40 @@
11319
  return $this->get_upgrade_url( WP_FS__PERIOD_ANNUALLY, true );
11320
  }
11321
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
11322
  /**
11323
  * Plugin's pricing URL.
11324
  *
@@ -11953,7 +12604,13 @@
11953
  * @author Vova Feldman (@svovaf)
11954
  */
11955
  $args = array(
11956
- 'public' => 1,
 
 
 
 
 
 
11957
  'archived' => 0,
11958
  'mature' => 0,
11959
  'spam' => 0,
@@ -12149,7 +12806,7 @@
12149
 
12150
  self::$_accounts->set_site_blog_context( $blog_id );
12151
  $this->_storage->set_site_blog_context( $blog_id );
12152
- $this->_storage->set_network_active( true, $this->is_delegated_connection( $blog_id ) );
12153
 
12154
  $this->_site = is_object( $install ) ?
12155
  $install :
@@ -13098,6 +13755,12 @@
13098
  }
13099
  }
13100
 
 
 
 
 
 
 
13101
  if ( $this->is_theme() ) {
13102
  $this->_register_account_hooks();
13103
  }
@@ -13163,6 +13826,30 @@
13163
 
13164
  }
13165
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
13166
  /**
13167
  * @author Vova Feldman (@svovaf)
13168
  * @since 1.1.7.4
@@ -13184,7 +13871,9 @@
13184
  // Return to the module's main page.
13185
  $this->get_after_activation_url( 'after_connect_url', array( 'fs_action' => $activation_action ) );
13186
 
13187
- $params = array(
 
 
13188
  'user_firstname' => $current_user->user_firstname,
13189
  'user_lastname' => $current_user->user_lastname,
13190
  'user_nickname' => $current_user->user_nicename,
@@ -13199,13 +13888,10 @@
13199
  'account',
13200
  array( 'fs_action' => 'sync_user' )
13201
  ), 'sync_user' ),
13202
- 'platform_version' => get_bloginfo( 'version' ),
13203
- 'sdk_version' => $this->version,
13204
- 'programming_language_version' => phpversion(),
13205
  'is_premium' => $this->is_premium(),
13206
  'is_active' => true,
13207
  'is_uninstalled' => false,
13208
- );
13209
 
13210
  if ( true === $network_level_or_blog_id ) {
13211
  if ( ! isset( $override_with['sites'] ) ) {
@@ -13391,7 +14077,7 @@
13391
  'timeout' => WP_FS__DEBUG_SDK ? 60 : 30,
13392
  );
13393
 
13394
- $url = WP_FS__ADDRESS . '/action/service/user/install/';
13395
  $response = self::safe_remote_post( $url, $request );
13396
 
13397
  if ( is_wp_error( $response ) ) {
@@ -14548,7 +15234,7 @@
14548
 
14549
  $hook = false;
14550
 
14551
- if ( ! $this->_menu->has_menu() ) {
14552
  // Add the opt-in page without a menu item.
14553
  $hook = FS_Admin_Menu_Manager::add_subpage(
14554
  null,
@@ -14896,15 +15582,25 @@
14896
  }
14897
  }
14898
 
14899
- if ( 0 < count( $this->_menu_items ) ) {
14900
- if ( ! $this->_menu->is_top_level() ) {
14901
- fs_enqueue_local_style( 'fs_common', '/admin/common.css' );
 
 
 
 
 
 
 
 
 
14902
 
14903
- // Append submenu items right after the plugin's submenu item.
14904
- $this->order_sub_submenu_items();
14905
- } else {
14906
- // Append submenu items.
14907
- $this->embed_submenu_items();
 
14908
  }
14909
  }
14910
  }
@@ -14930,16 +15626,6 @@
14930
 
14931
  foreach ( $this->_menu_items as $priority => $items ) {
14932
  foreach ( $items as $item ) {
14933
- if ( $item['show_submenu'] && $is_first_submenu_item ) {
14934
- if ( $this->_is_network_active && ! empty( $this->_dynamically_added_top_level_page_hook_name ) ) {
14935
- $item['menu_slug'] = '';
14936
-
14937
- $this->_menu->override_menu_item( $item['render_function'] );
14938
- }
14939
-
14940
- $is_first_submenu_item = false;
14941
- }
14942
-
14943
  $capability = ( ! empty( $item['capability'] ) ? $item['capability'] : $top_level_menu_capability );
14944
 
14945
  $menu_item = sprintf(
@@ -14950,12 +15636,13 @@
14950
  $item['menu_title']
14951
  );
14952
 
14953
- $menu_slug = $this->_menu->get_slug( $item['menu_slug'] );
 
14954
 
14955
  if ( ! isset( $item['url'] ) ) {
14956
  $hook = FS_Admin_Menu_Manager::add_subpage(
14957
  $item['show_submenu'] ?
14958
- $this->get_top_level_menu_slug() :
14959
  null,
14960
  $item['page_title'],
14961
  $menu_item,
@@ -14970,7 +15657,7 @@
14970
  } else {
14971
  FS_Admin_Menu_Manager::add_subpage(
14972
  $item['show_submenu'] ?
14973
- $this->get_top_level_menu_slug() :
14974
  null,
14975
  $item['page_title'],
14976
  $menu_item,
@@ -14979,6 +15666,24 @@
14979
  array( $this, '' )
14980
  );
14981
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
14982
  }
14983
  }
14984
  }
@@ -16221,11 +16926,12 @@
16221
  * @param bool|number $plugin_id
16222
  * @param bool $flush Since 1.1.7.3
16223
  * @param int $expiration Since 1.2.2.7
 
16224
  *
16225
  * @return object|false New plugin tag info if exist.
16226
  */
16227
- private function _fetch_newer_version( $plugin_id = false, $flush = true, $expiration = WP_FS__TIME_24_HOURS_IN_SEC ) {
16228
- $latest_tag = $this->_fetch_latest_version( $plugin_id, $flush, $expiration );
16229
 
16230
  if ( ! is_object( $latest_tag ) ) {
16231
  return false;
@@ -16250,17 +16956,18 @@
16250
  * @param bool|number $plugin_id
16251
  * @param bool $flush Since 1.1.7.3
16252
  * @param int $expiration Since 1.2.2.7
 
16253
  *
16254
  * @return bool|FS_Plugin_Tag
16255
  */
16256
- function get_update( $plugin_id = false, $flush = true, $expiration = WP_FS__TIME_24_HOURS_IN_SEC ) {
16257
  $this->_logger->entrance();
16258
 
16259
  if ( ! is_numeric( $plugin_id ) ) {
16260
  $plugin_id = $this->_plugin->id;
16261
  }
16262
 
16263
- $this->check_updates( true, $plugin_id, $flush, $expiration );
16264
  $updates = $this->get_all_updates();
16265
 
16266
  return isset( $updates[ $plugin_id ] ) && is_object( $updates[ $plugin_id ] ) ? $updates[ $plugin_id ] : false;
@@ -16289,14 +16996,62 @@
16289
  * @since 1.2.1
16290
  */
16291
  function has_active_valid_license() {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
16292
  return (
16293
- is_object( $this->_license ) &&
16294
- is_numeric( $this->_license->id ) &&
16295
- $this->_license->is_active() &&
16296
- $this->_license->is_valid()
16297
  );
16298
  }
16299
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
16300
  /**
16301
  * Check if site assigned with license with enabled features.
16302
  *
@@ -16365,8 +17120,11 @@
16365
  * the admin.
16366
  * @param bool $is_context_single_site @since 2.0.0. This is used when syncing a license for a single install from the
16367
  * network-level "Account" page.
 
 
 
16368
  */
16369
- private function _sync_license( $background = false, $is_context_single_site = false ) {
16370
  $this->_logger->entrance();
16371
 
16372
  $plugin_id = fs_request_get( 'plugin_id', $this->get_id() );
@@ -16376,7 +17134,7 @@
16376
  if ( $is_addon_sync ) {
16377
  $this->_sync_addon_license( $plugin_id, $background );
16378
  } else {
16379
- $this->_sync_plugin_license( $background, true, $is_context_single_site );
16380
  }
16381
 
16382
  $this->do_action( 'after_account_plan_sync', $this->get_plan_name() );
@@ -16466,11 +17224,15 @@
16466
  * @param bool $is_context_single_site Since 2.0.0. This is used when sending an update for a single install and
16467
  * syncing its license from the network-level "Account" page (e.g.: after
16468
  * activating a license only for the single install).
 
 
 
16469
  */
16470
  private function _sync_plugin_license(
16471
  $background = false,
16472
  $send_installs_update = true,
16473
- $is_context_single_site = false
 
16474
  ) {
16475
  $this->_logger->entrance();
16476
 
@@ -16487,6 +17249,16 @@
16487
  * @todo This line will execute install sync on a daily basis, even if running the free version (for opted-in users). The reason we want to keep it that way is for cases when the user was a paying customer, then there was a failure in subscription payment, and then after some time the payment was successful. This could be heavily optimized. For example, we can skip the $flush if the current install was never associated with a paid version.
16488
  */
16489
  if ( $is_site_level_sync ) {
 
 
 
 
 
 
 
 
 
 
16490
  $result = $this->send_install_update( array(), true );
16491
  $is_valid = $this->is_api_result_entity( $result );
16492
  } else {
@@ -16996,6 +17768,18 @@
16996
  $api = $this->get_api_site_scope();
16997
  $license = $api->call( "/licenses/{$this->_site->license_id}.json", 'delete' );
16998
 
 
 
 
 
 
 
 
 
 
 
 
 
16999
  if ( isset( $license->error ) ) {
17000
  $this->_admin_notices->add(
17001
  $this->get_text_inline( 'It looks like the license deactivation failed.', 'license-deactivation-failed-message' ) . '<br> ' .
@@ -17016,7 +17800,7 @@
17016
  }
17017
  }
17018
 
17019
- // Updated site plan to default.
17020
  $this->_sync_plans();
17021
  $this->_site->plan_id = $this->_plans[0]->id;
17022
  // Unlink license from site.
@@ -17043,13 +17827,17 @@
17043
  * @author Vova Feldman (@svovaf)
17044
  * @since 1.0.4
17045
  *
 
 
17046
  * @uses FS_Api
17047
  */
17048
  private function _downgrade_site() {
17049
  $this->_logger->entrance();
17050
 
 
 
17051
  $api = $this->get_api_site_scope();
17052
- $site = $api->call( 'downgrade.json', 'put' );
17053
 
17054
  $plan_downgraded = false;
17055
  $plan = false;
@@ -17067,29 +17855,47 @@
17067
  ( is_object( $subscription ) && ! isset( $subscription->error ) && ! $subscription->is_active() );
17068
  } else {
17069
  // handle different error cases.
17070
-
 
 
 
17071
  }
17072
 
17073
- if ( $plan_downgraded ) {
17074
- // Remove previous sticky message about upgrade (if exist).
17075
- $this->_admin_notices->remove_sticky( 'plan_upgraded' );
17076
-
17077
- $this->_admin_notices->add(
17078
- sprintf( $this->get_text_inline( 'Your plan was successfully downgraded. Your %s plan license will expire in %s.', 'plan-x-downgraded-message' ),
17079
- $plan->title,
17080
- human_time_diff( time(), strtotime( $this->_license->expiration ) )
17081
  )
17082
  );
 
17083
 
17084
- // Store site updates.
17085
- $this->_store_site();
17086
- } else {
17087
- $this->_admin_notices->add(
17088
- $this->get_text_inline( 'Seems like we are having some temporary issue with your plan downgrade. Please try again in few minutes.', 'plan-downgraded-failure-message' ),
17089
- $this->get_text_x_inline( 'Oops', 'exclamation', 'oops' ) . '...',
17090
- 'error'
17091
- );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
17092
  }
 
 
17093
  }
17094
 
17095
  /**
@@ -17196,22 +18002,19 @@
17196
  * @author Vova Feldman (@svovaf)
17197
  * @since 1.0.9
17198
  *
 
 
17199
  * @uses FS_Api
17200
  */
17201
  private function _cancel_trial() {
17202
  $this->_logger->entrance();
17203
 
17204
- // Alias.
17205
- $oops_text = $this->get_text_x_inline( 'Oops', 'exclamation', 'oops' ) . '...';
17206
-
17207
  if ( ! $this->is_trial() ) {
17208
- $this->_admin_notices->add(
17209
- $this->get_text_inline( 'It looks like you are not in trial mode anymore so there\'s nothing to cancel :)', 'trial-cancel-no-trial-message' ),
17210
- $oops_text,
17211
- 'error'
17212
  );
17213
-
17214
- return;
17215
  }
17216
 
17217
  $trial_plan = $this->get_trial_plan();
@@ -17242,31 +18045,33 @@
17242
  // @todo handle different error cases.
17243
  }
17244
 
17245
- if ( $trial_cancelled ) {
17246
- // Remove previous sticky messages about upgrade or trial (if exist).
17247
- $this->_admin_notices->remove_sticky( array(
17248
- 'trial_started',
17249
- 'trial_promotion',
17250
- 'plan_upgraded',
17251
- ) );
17252
 
17253
- // Store site updates.
17254
- $this->_store_site();
 
 
 
 
17255
 
17256
- if ( ! $this->is_addon() ||
17257
- ! $this->deactivate_premium_only_addon_without_license( true )
17258
- ) {
17259
- $this->_admin_notices->add(
17260
- sprintf( $this->get_text_inline( 'Your %s free trial was successfully cancelled.', 'trial-cancel-message' ), $trial_plan->title )
17261
- );
17262
- }
17263
- } else {
17264
  $this->_admin_notices->add(
17265
- $this->get_text_inline( 'Seems like we are having some temporary issue with your trial cancellation. Please try again in few minutes.', 'trial-cancel-failure-message' ),
17266
- $oops_text,
17267
- 'error'
17268
  );
17269
  }
 
 
17270
  }
17271
 
17272
  /**
@@ -17290,7 +18095,7 @@
17290
  * @return bool
17291
  */
17292
  private function _can_download_premium() {
17293
- return $this->has_active_valid_license() ||
17294
  ( $this->is_trial() && ! $this->get_trial_plan()->is_free() );
17295
  }
17296
 
@@ -17337,15 +18142,19 @@
17337
  * @since 1.0.4
17338
  *
17339
  * @param bool|number $addon_id
17340
- * @param bool $flush Since 1.1.7.3
17341
- * @param int $expiration Since 1.2.2.7
 
 
17342
  *
17343
  * @return object|false Plugin latest tag info.
17344
  */
17345
  function _fetch_latest_version(
17346
  $addon_id = false,
17347
  $flush = true,
17348
- $expiration = WP_FS__TIME_24_HOURS_IN_SEC
 
 
17349
  ) {
17350
  $this->_logger->entrance();
17351
 
@@ -17396,8 +18205,18 @@
17396
  $this->switch_to_blog( $switch_to_blog_id );
17397
  }
17398
 
 
 
 
 
 
 
 
 
 
 
17399
  $tag = $this->get_api_site_or_plugin_scope()->get(
17400
- $this->_get_latest_version_endpoint( $addon_id, 'json' ),
17401
  $flush,
17402
  $expiration
17403
  );
@@ -17533,17 +18352,19 @@
17533
  * @param bool|number $plugin_id
17534
  * @param bool $flush Since 1.1.7.3
17535
  * @param int $expiration Since 1.2.2.7
 
17536
  */
17537
  private function check_updates(
17538
  $background = false,
17539
  $plugin_id = false,
17540
  $flush = true,
17541
- $expiration = WP_FS__TIME_24_HOURS_IN_SEC
 
17542
  ) {
17543
  $this->_logger->entrance();
17544
 
17545
  // Check if there's a newer version for download.
17546
- $new_version = $this->_fetch_newer_version( $plugin_id, $flush, $expiration );
17547
 
17548
  $update = null;
17549
  if ( is_object( $new_version ) ) {
@@ -17899,7 +18720,9 @@
17899
  */
17900
  function get_after_activation_url( $filter, $params = array(), $network = null ) {
17901
  if ( $this->is_free_wp_org_theme() &&
17902
- fs_request_has( 'pending_activation' )
 
 
17903
  ) {
17904
  $first_time_path = '';
17905
  } else {
@@ -18031,6 +18854,8 @@
18031
  $this->_site = null;
18032
  $this->_user = null;
18033
 
 
 
18034
  fs_redirect( $this->get_activation_url() );
18035
  } else {
18036
  if ( $this->is_addon_activated( $plugin_id ) ) {
@@ -18050,15 +18875,23 @@
18050
  check_admin_referer( $action );
18051
  }
18052
 
18053
- if ( $plugin_id == $this->get_id() ) {
18054
- $this->_downgrade_site();
 
 
 
18055
 
18056
- if ( is_numeric( $blog_id ) ) {
18057
- $this->switch_to_blog( $this->_storage->network_install_blog_id );
18058
- }
18059
- } else if ( $this->is_addon_activated( $plugin_id ) ) {
18060
- $fs_addon = self::get_instance_by_id( $plugin_id );
18061
- $fs_addon->_downgrade_site();
 
 
 
 
 
18062
  }
18063
 
18064
  return;
@@ -18090,7 +18923,11 @@
18090
  $this->_site = null;
18091
  $this->_user = null;
18092
 
18093
- fs_redirect( $this->get_activation_url() );
 
 
 
 
18094
  }
18095
  } else {
18096
  if ( $this->is_addon_activated( $plugin_id ) ) {
@@ -18188,13 +19025,13 @@
18188
  #region Actions that might be called from external links (e.g. email)
18189
 
18190
  case 'cancel_trial':
18191
- if ( $plugin_id == $this->get_id() ) {
18192
- $this->_cancel_trial();
18193
- } else {
18194
- if ( $this->is_addon_activated( $plugin_id ) ) {
18195
- $fs_addon = self::get_instance_by_id( $plugin_id );
18196
- $fs_addon->_cancel_trial();
18197
- }
18198
  }
18199
 
18200
  return;
@@ -19190,11 +20027,23 @@
19190
 
19191
  if ( ! $this->is_addon() || ! $this->has_free_plan() ) {
19192
  $first_time_path = $this->_menu->get_first_time_path();
19193
- $url = $this->is_activation_mode() ?
19194
- $this->get_activation_url() :
19195
- ( empty( $first_time_path ) ?
19196
- $this->_get_admin_page_url() :
19197
- $first_time_path );
 
 
 
 
 
 
 
 
 
 
 
 
19198
  } else {
19199
  $plugin_fs = false;
19200
 
@@ -19314,6 +20163,21 @@
19314
  $this->_admin_notices->add_sticky( $message, $id, $title, $type );
19315
  }
19316
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
19317
  /**
19318
  * Helper function that returns the final steps for the upgrade completion.
19319
  *
@@ -19339,25 +20203,52 @@
19339
  $plan_title = $this->get_plan_title();
19340
  }
19341
 
19342
- // @since 1.2.1.5 The free version is auto deactivated.
19343
- $deactivation_step = version_compare( $this->version, '1.2.1.5', '<' ) ?
19344
- ( '<li>' . $this->esc_html_inline( 'Deactivate the free version', 'deactivate-free-version' ) . '.</li>' ) :
19345
- '';
 
 
 
 
 
19346
 
19347
- return sprintf(
19348
- ' %s: <ol><li>%s.</li>%s<li>%s (<a href="%s" target="_blank">%s</a>).</li></ol>',
19349
- $this->get_text_inline( 'Please follow these steps to complete the upgrade', 'follow-steps-to-complete-upgrade' ),
19350
- ( empty( $activate_license_string ) ? '' : $activate_license_string . '</li><li>' ) .
19351
- $this->get_latest_download_link( sprintf(
19352
- /* translators: %s: Plan title */
19353
- $this->get_text_inline( 'Download the latest %s version', 'download-latest-x-version' ),
19354
- $plan_title
19355
- ) ),
19356
- $deactivation_step,
19357
- $this->get_text_inline( 'Upload and activate the downloaded version', 'upload-and-activate' ),
19358
- '//bit.ly/upload-wp-' . $this->_module_type . 's',
19359
- $this->get_text_inline( 'How to upload and activate?', 'howto-upload-activate' )
19360
- );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
19361
  }
19362
 
19363
  /**
@@ -20140,13 +21031,19 @@
20140
 
20141
  // Locate the main assets folder.
20142
  if ( 1 < count( $fs_active_plugins->plugins ) ) {
20143
- $plugin_or_theme_img_dir = ( $this->is_plugin() ? WP_PLUGIN_DIR : get_theme_root() );
20144
 
20145
  foreach ( $fs_active_plugins->plugins as $sdk_path => &$data ) {
20146
  if ( $data->plugin_path == $this->get_plugin_basename() ) {
20147
  $img_dir = $plugin_or_theme_img_dir
20148
  . '/'
20149
- . str_replace( '../themes/', '', $sdk_path )
 
 
 
 
 
 
20150
  . '/assets/img';
20151
 
20152
  break;
33
  * @var string
34
  */
35
  private $_plugin_basename;
36
+ /**
37
+ * @since 2.2.1
38
+ *
39
+ * @var string
40
+ */
41
+ private $_premium_plugin_basename;
42
  /**
43
  * @since 1.0.0
44
  *
677
  version_compare( $sdk_version, '1.2.3', '>=' )
678
  ) {
679
  /**
680
+ * Starting from version 1.2.3, paths are stored as relative instead of absolute and some of them can be
681
+ * invalid.
682
  *
683
  * @author Leo Fajardo (@leorw)
684
  */
685
+ $this->remove_invalid_paths();
686
  }
687
 
688
  if ( version_compare( $sdk_prev_version, '1.1.5', '<' ) &&
706
 
707
  }
708
  }
709
+
710
+ if (
711
+ version_compare( $sdk_prev_version, '2.2.1', '<' ) &&
712
+ version_compare( $sdk_version, '2.2.1', '>=' )
713
+ ) {
714
+ /**
715
+ * Clear the file cache without storing the previous path since it could be a wrong path. For example,
716
+ * in the versions of the SDK lower than 2.2.1, it's possible for the path of an add-on to be the same
717
+ * as the parent plugin's when the add-on was auto-installed since the relevant method names were not
718
+ * skipped in the logic that determines the right path in the `get_caller_main_file_and_type` method
719
+ * (e.g. `try_activate_plugin`). Since it was an auto-installation, the caller was the parent plugin
720
+ * and so its path was used. In case the stored path is wrong, clearing the cache will resolve issues
721
+ * related to data mix-up between plugins (e.g. titles and versions of an add-on and its parent plugin).
722
+ *
723
+ * @author Leo Fajardo (@leorw)
724
+ * @since 2.2.1
725
+ */
726
+ $this->clear_module_main_file_cache( false );
727
+ }
728
  }
729
 
730
  /**
850
  }
851
 
852
  /**
853
+ * Remove invalid paths.
854
  *
855
  * @author Leo Fajardo (@leorw)
856
  * @since 1.2.3
857
  */
858
+ private function remove_invalid_paths() {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
859
  // Remove invalid path that is still associated with the current slug if there's any.
860
  $file_slug_map = self::$_accounts->get_option( 'file_slug_map', array() );
861
  foreach ( $file_slug_map as $plugin_basename => $slug ) {
1238
  <?php
1239
  }
1240
 
1241
+ /**
1242
+ * Opens the support forum subemenu item in a new browser page.
1243
+ *
1244
+ * @author Vova Feldman (@svovaf)
1245
+ * @since 2.1.4
1246
+ */
1247
+ static function _open_support_forum_in_new_page() {
1248
+ ?>
1249
+ <script type="text/javascript">
1250
+ (function ($) {
1251
+ $('.fs-submenu-item.wp-support-forum').parent().attr('target', '_blank');
1252
+ })(jQuery);
1253
+ </script>
1254
+ <?php
1255
+ }
1256
+
1257
  /**
1258
  * @author Vova Feldman (@svovaf)
1259
  * @since 1.0.9
1265
  add_action( 'plugins_loaded', array( &$this, '_hook_action_links_and_register_account_hooks' ) );
1266
 
1267
  if ( $this->is_plugin() ) {
1268
+ if ( self::is_plugin_install_page() && true !== fs_request_get_bool( 'fs_allow_updater_and_dialog' ) ) {
1269
+ /**
1270
+ * Unless the `fs_allow_updater_and_dialog` URL param exists and its value is `true`, make
1271
+ * Freemius-related updates unavailable on the "Add Plugins" admin page (/plugin-install.php)
1272
+ * so that they won't interfere with the .org plugins' functionalities on that page (e.g.
1273
+ * updating of a .org plugin).
1274
+ */
1275
+ add_filter( 'site_transient_update_plugins', array( 'Freemius', '_remove_fs_updates_from_plugin_install_page' ), 10, 2 );
1276
+ } else if ( self::is_plugins_page() || self::is_updates_page() ) {
1277
+ /**
1278
+ * On the "Plugins" and "Updates" admin pages, if there are premium or non–org-compliant
1279
+ * plugins, modify their details dialog URLs (add a Freemius-specific param) so that the SDK can
1280
+ * determine if the plugin information dialog should show information from Freemius.
1281
+ *
1282
+ * @author Leo Fajardo (@leorw)
1283
+ * @since 2.2.3
1284
+ */
1285
+ add_action( 'admin_footer', array( 'Freemius', '_prepend_fs_allow_updater_and_dialog_flag_url_param' ) );
1286
+ }
1287
+
1288
  $plugin_dir = dirname( $this->_plugin_dir_path ) . '/';
1289
 
1290
  /**
1452
  }
1453
  }
1454
 
1455
+ /**
1456
+ * Makes Freemius-related updates unavailable on the "Add Plugins" admin page (/plugin-install.php) so that
1457
+ * they won't interfere with the .org plugins' functionalities on that page (e.g. updating of a .org plugin).
1458
+ *
1459
+ * @author Leo Fajardo (@leorw)
1460
+ * @since 2.2.3
1461
+ *
1462
+ * @param object $updates
1463
+ * @param string|null $transient
1464
+ *
1465
+ * @return object
1466
+ */
1467
+ static function _remove_fs_updates_from_plugin_install_page( $updates, $transient = null ) {
1468
+ if ( is_object( $updates ) && isset( $updates->response ) ) {
1469
+ foreach ( $updates->response as $file => $plugin ) {
1470
+ if ( false !== strpos( $plugin->package, 'api.freemius' ) ) {
1471
+ unset( $updates->response[ $file ] );
1472
+ }
1473
+ }
1474
+ }
1475
+
1476
+ return $updates;
1477
+ }
1478
+
1479
+ /**
1480
+ * Prepends the `fs_allow_updater_and_dialog` param to the plugin information URLs to tell the SDK to handle
1481
+ * the information that is shown on the plugin details dialog that is shown when the relevant link is clicked.
1482
+ *
1483
+ * @author Leo Fajardo (@leorw)
1484
+ * @since 2.2.3
1485
+ *
1486
+ * @return string
1487
+ */
1488
+ static function _prepend_fs_allow_updater_and_dialog_flag_url_param() {
1489
+ $slug_basename_map = array();
1490
+ foreach ( self::$_instances as $instance ) {
1491
+ if ( ! $instance->is_plugin() ) {
1492
+ continue;
1493
+ }
1494
+
1495
+ $slug_basename_map[ $instance->get_slug() ] = $instance->premium_plugin_basename();
1496
+ }
1497
+ ?>
1498
+ <script type="text/javascript">
1499
+ (function( $ ) {
1500
+ var slugBasenameMap = <?php echo json_encode( $slug_basename_map ) ?>;
1501
+ for ( var slug in slugBasenameMap ) {
1502
+ var basename = slugBasenameMap[ slug ];
1503
+
1504
+ // Try to get the plugin rows if on the "Plugins" page.
1505
+ var $pluginRows = $( '.wp-list-table.plugins tr[data-plugin="' + basename + '"]');
1506
+
1507
+ if ( 0 === $pluginRows.length ) {
1508
+ // Try to get the plugin rows if on the "Updates" page.
1509
+ var $pluginCheckbox = $( '#update-plugins-table input[type="checkbox"][value="' + basename + '"]' );
1510
+ if ( 0 !== $pluginCheckbox.length ) {
1511
+ $pluginRows = $pluginCheckbox.parents( 'tr:first' );
1512
+ }
1513
+ }
1514
+
1515
+ if ( 0 === $pluginRows.length ) {
1516
+ // No plugin rows found.
1517
+ continue;
1518
+ }
1519
+
1520
+ // Find the "View details" links and add the `fs_allow_updater_and_dialog` param to the URL.
1521
+ $pluginRows.find( 'a[href*="plugin-install.php?tab=plugin-information"]' ).each(function() {
1522
+ var $this = $( this ),
1523
+ href = $this.attr( 'href' ).replace( '?tab=', '?fs_allow_updater_and_dialog=true&tab=');
1524
+
1525
+ $this.attr( 'href', href );
1526
+ });
1527
+ }
1528
+ })( jQuery );
1529
+ </script>
1530
+ <?php
1531
+ }
1532
+
1533
  /**
1534
  * Keeping the uninstall hook registered for free or premium plugin version may result to a fatal error that
1535
  * could happen when a user tries to uninstall either version while one of them is still active. Uninstalling a
1550
 
1551
  /**
1552
  * @since 1.2.0 Invalidate module's main file cache, otherwise, FS_Plugin_Updater will not fetch updates.
1553
+ *
1554
+ * @param bool $store_prev_path
1555
  */
1556
+ private function clear_module_main_file_cache( $store_prev_path = true ) {
1557
  if ( ! isset( $this->_storage->plugin_main_file ) ||
1558
+ empty( $this->_storage->plugin_main_file->path )
1559
  ) {
1560
  return;
1561
  }
1562
 
1563
+ if ( ! $store_prev_path ) {
1564
+ /**
1565
+ * Storing the previous path is not needed when clearing the cache after an SDK version update since
1566
+ * the main purpose of the cache clearing in that event is to correct a wrong plugin main file path
1567
+ * which causes data mix-up between plugins (e.g. titles and versions of an add-on and its parent plugin).
1568
+ *
1569
+ * @author Leo Fajardo (@leorw)
1570
+ * @since 2.2.1
1571
+ */
1572
+ unset( $this->_storage->plugin_main_file->path );
1573
+ } else {
1574
+ $plugin_main_file = clone $this->_storage->plugin_main_file;
1575
 
1576
+ // Store cached path (2nd layer cache).
1577
+ $plugin_main_file->prev_path = $plugin_main_file->path;
1578
 
1579
+ // Clear cached path.
1580
+ unset( $plugin_main_file->path );
1581
 
1582
+ $this->_storage->plugin_main_file = $plugin_main_file;
1583
+ }
1584
 
1585
  /**
1586
  * Clear global cached path.
1627
  array( &$this, '_submit_uninstall_reason_action' )
1628
  );
1629
 
1630
+ $this->add_ajax_action(
1631
+ 'cancel_subscription_or_trial',
1632
+ array( &$this, 'cancel_subscription_or_trial_ajax_action' )
1633
+ );
1634
+
1635
  if ( ! $this->is_addon() || $this->is_parent_plugin_installed() ) {
1636
  if ( ( $this->is_plugin() && self::is_plugins_page() ) ||
1637
  ( $this->is_theme() && self::is_themes_page() )
1756
 
1757
  return fs_normalize_path( trailingslashit( $is_plugin ?
1758
  WP_PLUGIN_DIR :
1759
+ get_theme_root( get_stylesheet() ) ) );
1760
  }
1761
 
1762
  /**
1821
  private function get_caller_main_file_and_type() {
1822
  self::require_plugin_essentials();
1823
 
1824
+ $all_plugins = fs_get_plugins( true );
1825
  $all_plugins_paths = array();
1826
 
1827
  // Get active plugin's main files real full names (might be symlinks).
1828
+ foreach ( $all_plugins as $relative_path => $data ) {
1829
  if ( false === strpos( fs_normalize_path( $relative_path ), '/' ) ) {
1830
  /**
1831
  * Ignore plugins that don't have a folder (e.g. Hello Dolly) since they
1843
  $caller_file_candidate = false;
1844
  $caller_map = array();
1845
  $module_type = WP_FS__MODULE_TYPE_PLUGIN;
1846
+ $themes_dir = fs_normalize_path( get_theme_root( get_stylesheet() ) );
1847
 
1848
  for ( $i = 1, $bt = debug_backtrace(), $len = count( $bt ); $i < $len; $i ++ ) {
1849
  if ( empty( $bt[ $i ]['file'] ) ) {
1863
  'requir' . 'e_once',
1864
  'requir' . 'e',
1865
  'includ' . 'e_once',
1866
+ 'includ' . 'e',
1867
+ 'install_and_activate_plugin',
1868
+ 'try_activate_plugin',
1869
+ 'activate_plugin'
1870
  ) )
1871
  ) {
1872
  // Ignore call stack hooks and files inclusion.
2202
  exit;
2203
  }
2204
 
2205
+ /**
2206
+ * @author Leo Fajardo (@leorw)
2207
+ * @since 2.1.4
2208
+ */
2209
+ function cancel_subscription_or_trial_ajax_action() {
2210
+ $this->_logger->entrance();
2211
+
2212
+ $this->check_ajax_referer( 'cancel_subscription_or_trial' );
2213
+
2214
+ $result = $this->cancel_subscription_or_trial( fs_request_get( 'plugin_id', $this->get_id() ), false );
2215
+
2216
+ if ( $this->is_api_error( $result ) ) {
2217
+ $this->shoot_ajax_failure( $result->error->message );
2218
+ }
2219
+
2220
+ $this->shoot_ajax_success();
2221
+ }
2222
+
2223
+ /**
2224
+ * @author Leo Fajardo (@leorw)
2225
+ * @since 2.1.4
2226
+ *
2227
+ * @param number $plugin_id
2228
+ *
2229
+ * @return object
2230
+ */
2231
+ private function cancel_subscription_or_trial( $plugin_id ) {
2232
+ $fs = null;
2233
+ if ( $plugin_id == $this->get_id() ) {
2234
+ $fs = $this;
2235
+ } else if ( $this->is_addon_activated( $plugin_id ) ) {
2236
+ $fs = self::get_instance_by_id( $plugin_id );
2237
+ }
2238
+
2239
+ $result = null;
2240
+
2241
+ if ( ! is_null( $fs ) ) {
2242
+ $result = $fs->is_paid_trial() ?
2243
+ $fs->_cancel_trial() :
2244
+ $fs->_downgrade_site();
2245
+ }
2246
+
2247
+ return $result;
2248
+ }
2249
+
2250
  /**
2251
  * @author Leo Fajardo (@leorw)
2252
  * @since 2.0.2
2323
  * @since 1.2.2
2324
  *
2325
  * @param string|number $id_or_slug
2326
+ * @param string $module_type
2327
  *
2328
  * @return number|false
2329
  */
2330
+ private static function get_module_id( $id_or_slug, $module_type = WP_FS__MODULE_TYPE_PLUGIN ) {
2331
  if ( is_numeric( $id_or_slug ) ) {
2332
  return $id_or_slug;
2333
  }
2334
 
2335
  foreach ( self::$_instances as $instance ) {
2336
+ // Also check the module type since there can be a plugin and a theme with the same slug.
2337
+ if ( ( $module_type === $instance->get_module_type() ) && ( $id_or_slug === $instance->get_slug() ) ) {
2338
  return $instance->get_id();
2339
  }
2340
  }
2361
  * @author Vova Feldman (@svovaf)
2362
  * @since 1.0.1
2363
  *
2364
+ * @param string $plugin_file
2365
+ * @param string $module_type
2366
  *
2367
  * @return false|Freemius
2368
  */
2369
+ static function get_instance_by_file( $plugin_file, $module_type = WP_FS__MODULE_TYPE_PLUGIN ) {
2370
  $slug = self::find_slug_by_basename( $plugin_file );
2371
 
2372
  return ( false !== $slug ) ?
2373
+ self::instance( self::get_module_id( $slug, $module_type ) ) :
2374
  false;
2375
  }
2376
 
2484
  function is_site_activation_mode( $and_on = true ) {
2485
  return (
2486
  ( $this->is_on() || ! $and_on ) &&
2487
+ ( $this->is_premium() && true === $this->_storage->require_license_activation ) ||
2488
+ (
2489
+ ( ! $this->is_registered() ||
2490
+ ( $this->is_only_premium() && ! $this->has_features_enabled_license() ) ) &&
2491
+ ( ! $this->is_enable_anonymous() ||
2492
+ ( ! $this->is_anonymous() && ! $this->is_pending_activation() ) )
2493
+ )
2494
  );
2495
  }
2496
 
2525
  return false;
2526
  }
2527
 
2528
+ if ( $this->is_network_anonymous() && true !== $this->_storage->require_license_activation ) {
2529
  // Super-admin skipped the connection network wide -> not activation mode.
2530
  return false;
2531
  }
2646
  self::require_plugin_essentials();
2647
 
2648
  $active_plugin = array();
2649
+ $all_plugins = fs_get_plugins();
2650
  $active_plugins_basenames = self::get_active_plugins_basenames( $blog_id );
2651
 
2652
  foreach ( $active_plugins_basenames as $plugin_basename ) {
2672
  get_option( 'active_plugins' );
2673
 
2674
  $active = array();
2675
+
2676
+ if ( ! is_array( $active_basenames ) ) {
2677
+ return $active;
2678
+ }
2679
+
2680
  foreach ( $active_basenames as $basename ) {
2681
  $active[ $basename ] = array(
2682
  'is_active' => true,
2701
  private static function get_all_plugins( $blog_id = 0 ) {
2702
  self::require_plugin_essentials();
2703
 
2704
+ $all_plugins = fs_get_plugins();
2705
 
2706
  $active_plugins_basenames = self::get_active_plugins_basenames( $blog_id );
2707
 
2733
  private static function get_network_plugins() {
2734
  self::require_plugin_essentials();
2735
 
2736
+ $all_plugins = fs_get_plugins();
2737
 
2738
  $network_active_basenames = is_multisite() ?
2739
  get_site_option( 'active_sitewide_plugins' ) :
2830
  self::$_accounts = FS_Options::instance( WP_FS__ACCOUNTS_OPTION_NAME, true );
2831
 
2832
  if ( is_multisite() ) {
2833
+ $has_skipped_migration = (
2834
+ // 'id_slug_type_path_map' - was never stored on older versions, therefore, not exists on the site level.
2835
+ null === self::$_accounts->get_option( 'id_slug_type_path_map', null, false ) &&
2836
+ // 'file_slug_map' stored on the site level, so it was running an SDK version before it was integrated with MS-network.
2837
+ null !== self::$_accounts->get_option( 'file_slug_map', null, false )
2838
+ );
2839
+
2840
  /**
2841
+ * If the file_slug_map exists on the site level but doesn't exist on the
2842
  * network level storage, it means that we need to process the storage with migration.
2843
  *
2844
+ * The code in this `if` scope will only be executed once and only for the first site that will execute it because once we migrate the storage data, file_slug_map will be already set in the network level storage.
2845
  *
2846
  * @author Vova Feldman (@svovaf)
2847
  * @since 2.0.0
2848
  */
2849
+ if (
2850
+ ( $has_skipped_migration && true !== self::$_accounts->get_option( 'ms_migration_complete', false, true ) ) ||
2851
+ ( null === self::$_accounts->get_option( 'file_slug_map', null, true ) &&
2852
+ null !== self::$_accounts->get_option( 'file_slug_map', null, false ) )
2853
  ) {
2854
+ self::migrate_options_to_network();
 
 
 
 
 
 
 
2855
  }
2856
  }
2857
 
2877
  }
2878
 
2879
  add_action( 'admin_footer', array( 'Freemius', '_enrich_ajax_url' ) );
2880
+ add_action( 'admin_footer', array( 'Freemius', '_open_support_forum_in_new_page' ) );
2881
+
2882
 
2883
  self::$_statics_loaded = true;
2884
  }
2885
 
2886
+ /**
2887
+ * @author Leo Fajardo (@leorw)
2888
+ *
2889
+ * @since 2.1.3
2890
+ */
2891
+ private static function migrate_options_to_network() {
2892
+ self::migrate_accounts_to_network();
2893
+
2894
+ // Migrate API options from site level to network level.
2895
+ $api_network_options = FS_Option_Manager::get_manager( WP_FS__OPTIONS_OPTION_NAME, true, true );
2896
+ $api_network_options->migrate_to_network();
2897
+
2898
+ // Migrate API cache to network level storage.
2899
+ FS_Cache_Manager::get_manager( WP_FS__API_CACHE_OPTION_NAME )->migrate_to_network();
2900
+
2901
+ self::$_accounts->set_option( 'ms_migration_complete', true, true );
2902
+ }
2903
+
2904
  #----------------------------------------------------------------------------------
2905
  #region Localization
2906
  #----------------------------------------------------------------------------------
2977
  * @since 1.1.7.3
2978
  */
2979
  static function _toggle_debug_mode() {
2980
+ if ( ! is_super_admin() ) {
2981
+ return;
2982
+ }
2983
+
2984
  $is_on = fs_request_get( 'is_on', false, 'post' );
2985
 
2986
  if ( fs_request_is_post() && in_array( $is_on, array( 0, 1 ) ) ) {
3012
  * @since 1.2.1.7
3013
  */
3014
  static function _get_db_option() {
3015
+ check_admin_referer( 'fs_get_db_option' );
3016
+
3017
  $option_name = fs_request_get( 'option_name' );
3018
 
3019
+ if ( ! is_super_admin() ||
3020
+ ! fs_starts_with( $option_name, 'fs_' )
3021
+ ) {
3022
+ self::shoot_ajax_failure();
3023
+ }
3024
+
3025
  $value = get_option( $option_name );
3026
 
3027
  $result = array(
3044
  * @since 1.2.1.7
3045
  */
3046
  static function _set_db_option() {
3047
+ check_admin_referer( 'fs_set_db_option' );
3048
+
3049
+ $option_name = fs_request_get( 'option_name' );
3050
+
3051
+ if ( ! is_super_admin() ||
3052
+ ! fs_starts_with( $option_name, 'fs_' )
3053
+ ) {
3054
+ self::shoot_ajax_failure();
3055
+ }
3056
+
3057
  $option_value = fs_request_get( 'option_value' );
3058
 
3059
  if ( ! empty( $option_value ) ) {
3148
  }
3149
 
3150
  fs_redirect( $download_url );
3151
+ } else if ( fs_request_is_action( 'migrate_options_to_network' ) ) {
3152
+ check_admin_referer( 'migrate_options_to_network' );
3153
+
3154
+ self::migrate_options_to_network();
3155
  }
3156
  }
3157
 
4291
  * @author Vova Feldman (@svovaf)
4292
  */
4293
  if ( $this->is_user_in_admin() &&
4294
+ 'plugin-information' === fs_request_get( 'tab', false ) &&
4295
+ $this->should_use_freemius_updater_and_dialog() &&
4296
+ (
4297
+ ( $this->is_addon() && $this->get_slug() == fs_request_get( 'plugin', false ) ) ||
4298
+ ( $this->has_addons() && $this->get_id() == fs_request_get( 'parent_plugin_id', false ) )
4299
+ )
4300
  ) {
4301
  require_once WP_FS__DIR_INCLUDES . '/fs-plugin-info-dialog.php';
4302
 
4303
+ new FS_Plugin_Info_Dialog( $this->is_addon() ? $this->get_parent_instance() : $this );
4304
  }
4305
 
4306
  // Check if Freemius is on for the current plugin.
4414
  * @author Vova Feldman
4415
  * @since 1.2.1.6
4416
  */
4417
+ if (
4418
+ $this->should_use_freemius_updater_and_dialog() &&
4419
+ (
4420
+ $this->is_premium() ||
4421
+ /**
4422
+ * If not premium but the premium version is installed, also instantiate the updater so that the
4423
+ * plugin information dialog of the premium version will have the information from the server.
4424
+ *
4425
+ * @author Leo Fajardo (@leorw)
4426
+ * @since 2.2.3
4427
+ */
4428
+ ( file_exists( fs_normalize_path( WP_PLUGIN_DIR . '/' . $this->premium_plugin_basename() ) ) )
4429
+ ) &&
4430
+ $this->has_release_on_freemius()
4431
+ ) {
4432
  FS_Plugin_Updater::instance( $this );
4433
  }
4434
 
4471
  }
4472
  }
4473
 
4474
+ /**
4475
+ * @author Leo Fajardo (@leorw)
4476
+ * @since 2.2.3
4477
+ *
4478
+ * @return bool
4479
+ */
4480
+ private function should_use_freemius_updater_and_dialog() {
4481
+ return (
4482
+ /**
4483
+ * Unless the `fs_allow_updater_and_dialog` URL param exists and its value is `true`, disallow updater
4484
+ * and dialog on the "Add Plugins" admin page (/plugin-install.php) so that they won't interfere with
4485
+ * the .org plugins' functionalities on that page (e.g. installation and viewing plugin details from
4486
+ * .org).
4487
+ */
4488
+ ( ! self::is_plugin_install_page() || true === fs_request_get_bool( 'fs_allow_updater_and_dialog' ) ) &&
4489
+ // Disallow updater and dialog when installing a plugin, otherwise .org "add-on" plugins will be affected.
4490
+ ( 'install-plugin' !== fs_request_get( 'action' ) )
4491
+ );
4492
+ }
4493
+
4494
  /**
4495
  * @author Leo Fajardo (@leorw)
4496
  *
4927
  $this->_plugin :
4928
  new FS_Plugin();
4929
 
4930
+ $premium_suffix = $this->get_option( $plugin_info, 'premium_suffix', '(Premium)' );
4931
+
4932
  $plugin->update( array(
4933
  'id' => $id,
4934
  'type' => $this->get_option( $plugin_info, 'type', $this->_module_type ),
4935
  'public_key' => $public_key,
4936
  'slug' => $this->_slug,
4937
+ 'premium_slug' => $this->get_option( $plugin_info, 'premium_slug', "{$this->_slug}-premium" ),
4938
  'parent_plugin_id' => $parent_id,
4939
  'version' => $this->get_plugin_version(),
4940
+ 'title' => $this->get_plugin_name( $premium_suffix ),
4941
  'file' => $this->_plugin_basename,
4942
  'is_premium' => $this->get_bool_option( $plugin_info, 'is_premium', true ),
4943
+ 'premium_suffix' => $premium_suffix,
4944
  'is_live' => $this->get_bool_option( $plugin_info, 'is_live', true ),
4945
  'affiliate_moderation' => $this->get_option( $plugin_info, 'has_affiliation' ),
4946
  ) );
5321
  }
5322
 
5323
  $addon = $this->get_addon( $addon_id );
5324
+ $premium_basename = "{$addon->premium_slug}/{$addon->slug}.php";
5325
 
5326
  if ( file_exists( fs_normalize_path( WP_PLUGIN_DIR . '/' . $premium_basename ) ) ) {
5327
  return $premium_basename;
5329
 
5330
  $all_plugins = $this->get_all_plugins();
5331
 
5332
+ foreach ( $all_plugins as $basename => $data ) {
5333
  if ( $addon->slug === $data['slug'] ||
5334
+ $addon->premium_slug === $data['slug']
5335
  ) {
5336
  return $basename;
5337
  }
5571
  if ( ! isset( $this->_is_anonymous ) ) {
5572
  if ( $this->is_network_anonymous() ) {
5573
  $this->_is_anonymous = true;
5574
+ } else if ( ! fs_is_network_admin() ) {
5575
  if ( ! isset( $this->_storage->is_anonymous ) ) {
5576
  // Not skipped.
5577
  $this->_is_anonymous = false;
5762
  $this->_storage->store( "{$name}_timestamp", time() );
5763
  }
5764
 
5765
+ /**
5766
+ * Sets the keepalive time to now.
5767
+ *
5768
+ * @author Leo Fajardo (@leorw)
5769
+ * @since 2.2.3
5770
+ *
5771
+ * @param bool|null $use_network_level_storage
5772
+ */
5773
+ private function set_keepalive_timestamp( $use_network_level_storage = null ) {
5774
+ $this->_logger->entrance();
5775
+
5776
+ $this->_storage->store( 'keepalive_timestamp', time(), $use_network_level_storage );
5777
+ }
5778
+
5779
  /**
5780
  * Check if cron was executed in the last $period of seconds.
5781
  *
5790
  private function is_cron_executed( $name, $period = WP_FS__TIME_24_HOURS_IN_SEC ) {
5791
  $this->_logger->entrance( $name );
5792
 
5793
+ $last_execution = $this->cron_last_execution( $name );
5794
 
5795
  if ( ! is_numeric( $last_execution ) ) {
5796
  return false;
6051
  }
6052
  }
6053
 
6054
+ $current_blog_id = get_current_blog_id();
6055
+
6056
  foreach ( $users_2_blog_ids as $user_id => $blog_ids ) {
6057
  if ( 0 < $blog_ids[0] ) {
6058
  $this->switch_to_blog( $blog_ids[0] );
6059
  }
6060
 
6061
+ call_user_func_array( $callable, array( $blog_ids, ( is_multisite() ? $current_blog_id : null ) ) );
6062
 
6063
  foreach ( $blog_ids as $blog_id ) {
6064
  $this->do_action( "after_{$name}_cron", $blog_id );
6066
  }
6067
 
6068
  if ( is_multisite() ) {
6069
+ $this->switch_to_blog( $current_blog_id );
6070
+
6071
  $this->do_action( "after_{$name}_cron_multisite" );
6072
  }
6073
  }
6139
  * @author Vova Feldman (@svovaf)
6140
  * @since 2.0.0
6141
  *
6142
+ * @param int[] $blog_ids
6143
+ * @param int|null $current_blog_id @since 2.2.3. This is passed from the `execute_cron` method and used by the
6144
+ * `_sync_plugin_license` method in order to switch to the previous blog when sending
6145
+ * updates for a single site in case `execute_cron` has switched to a different blog.
6146
  */
6147
+ function _sync_cron_method( array $blog_ids, $current_blog_id = null ) {
6148
  if ( $this->is_registered() ) {
6149
  if ( $this->has_paid_plan() ) {
6150
  // Initiate background plan sync.
6151
+ $this->_sync_license( true, false, $current_blog_id );
6152
 
6153
  if ( $this->is_paying() ) {
6154
  // Check for premium plugin updates.
6295
  * @param int $except_blog_id Since 2.0.0 when running in a multisite network environment, the cron execution is consolidated. This param allows excluding excluded specified blog ID from being the cron executor.
6296
  */
6297
  private function schedule_install_sync( $except_blog_id = 0 ) {
6298
+ $this->schedule_cron( 'install_sync', 'install_sync', 'single', WP_FS__SCRIPT_START_TIME, false, $except_blog_id );
6299
  }
6300
 
6301
  /**
6363
  * @author Vova Feldman (@svovaf)
6364
  * @since 2.0.0
6365
  *
6366
+ * @param int[] $blog_ids
6367
+ * @param int|null $current_blog_id
6368
  */
6369
+ function _sync_install_cron_method( array $blog_ids, $current_blog_id = null ) {
6370
  if ( $this->is_registered() ) {
6371
  if ( 1 < count( $blog_ids ) ) {
6372
  $this->sync_installs( array(), true );
6470
  if ( ! $this->is_addon() &&
6471
  ! ( ! $this->_is_network_active && fs_is_network_admin() ) &&
6472
  (
6473
+ ( true === $this->_storage->require_license_activation ) ||
6474
  // Not registered nor anonymous.
6475
  ( ! $this->is_registered() && ! $this->is_anonymous() ) ||
6476
  // OR, network level and in network upgrade mode.
6487
  * @since 1.2.2
6488
  */
6489
  if ( $this->is_theme()
 
6490
  && ! $this->has_settings_menu()
6491
  && ! isset( $_REQUEST['fs_action'] )
6492
  && $this->can_activate_previous_theme()
6493
  ) {
6494
+ if ( $this->is_only_premium() ) {
6495
+ $this->activate_previous_theme();
6496
+ return;
6497
+ }
6498
 
6499
+ if ( true === $this->_storage->require_license_activation ) {
6500
+ $this->_storage->require_license_activation = false;
6501
+ }
6502
  }
6503
 
6504
  if ( ! fs_is_network_admin() &&
6598
  $this->_module_type,
6599
  sprintf( '<b><a href="%s">%s</a></b>',
6600
  $this->get_activation_url(),
6601
+ sprintf( $this->get_text_inline( 'Opt in to make "%s" better!', 'optin-x-now' ), $this->get_plugin_name() )
6602
  )
6603
  ),
6604
  'connect_account',
7060
  }
7061
  }
7062
 
7063
+ if (
7064
+ $is_premium_version_activation &&
7065
+ (
7066
+ ( ! $this->is_registered() && $this->is_anonymous() ) ||
7067
+ (
7068
+ $this->is_registered() &&
7069
+ ! $this->is_trial() &&
7070
+ ! $this->has_features_enabled_license()
7071
+ )
7072
+ )
7073
+ ) {
7074
+ $this->_storage->require_license_activation = true;
7075
+ }
7076
+
7077
  if ( ! isset( $this->_storage->is_plugin_new_install ) ) {
7078
  /**
7079
  * If no previous version of plugin's version exist, it means that it's either
7343
  private function remove_sdk_reference() {
7344
  global $fs_active_plugins;
7345
 
7346
+ foreach ( $fs_active_plugins->plugins as $sdk_path => $data ) {
7347
  if ( $this->_plugin_basename == $data->plugin_path ) {
7348
  unset( $fs_active_plugins->plugins[ $sdk_path ] );
7349
  break;
7525
  }
7526
  }
7527
 
7528
+ /**
7529
+ * This is used to ensure that before redirecting to the opt-in page after resetting the anonymous mode or
7530
+ * deleting the account in the network level, the URL of the page to redirect to is correct.
7531
+ *
7532
+ * @author Leo Fajardo (@leorw)
7533
+ *
7534
+ * @since 2.1.3
7535
+ */
7536
+ private function maybe_set_slug_and_network_menu_exists_flag() {
7537
+ if ( ! empty( $this->_dynamically_added_top_level_page_hook_name ) ) {
7538
+ $this->_menu->set_slug_and_network_menu_exists_flag( $this->_menu->has_menu() ?
7539
+ $this->_menu->get_slug() :
7540
+ $this->_slug
7541
+ );
7542
+ }
7543
+ }
7544
+
7545
  /**
7546
  * Clears the anonymous mode and redirects to the opt-in screen.
7547
  *
7555
 
7556
  $this->reset_anonymous_mode( fs_is_network_admin() );
7557
 
7558
+ $this->maybe_set_slug_and_network_menu_exists_flag();
7559
+
7560
  fs_redirect( $this->get_activation_url() );
7561
  }
7562
 
7996
  $include_plugins = true,
7997
  $include_themes = true
7998
  ) {
7999
+ if ( ! defined( 'WP_FS__TRACK_PLUGINS' ) || false !== WP_FS__TRACK_PLUGINS ) {
8000
+ /**
8001
+ * @since 1.1.8 Also send plugin updates.
8002
+ */
8003
+ if ( $include_plugins && ! isset( $override['plugins'] ) ) {
8004
+ $plugins = $this->get_plugins_data_for_api();
8005
+ if ( ! empty( $plugins ) ) {
8006
+ $override['plugins'] = $plugins;
8007
+ }
8008
  }
8009
  }
8010
+
8011
+ if ( ! defined( 'WP_FS__TRACK_THEMES' ) || false !== WP_FS__TRACK_THEMES ) {
8012
+ /**
8013
+ * @since 1.1.8 Also send themes updates.
8014
+ */
8015
+ if ( $include_themes && ! isset( $override['themes'] ) ) {
8016
+ $themes = $this->get_themes_data_for_api();
8017
+ if ( ! empty( $themes ) ) {
8018
+ $override['themes'] = $themes;
8019
+ }
8020
  }
8021
  }
8022
 
8023
+ $versions = $this->get_versions();
8024
+
8025
+ return array_merge( $versions, array(
8026
+ 'version' => $this->get_plugin_version(),
8027
+ 'is_premium' => $this->is_premium(),
8028
+ 'language' => get_bloginfo( 'language' ),
8029
+ 'charset' => get_bloginfo( 'charset' ),
8030
+ 'title' => get_bloginfo( 'name' ),
8031
+ 'url' => get_site_url(),
 
8032
  // Special params.
8033
+ 'is_active' => true,
8034
+ 'is_disconnected' => $this->is_tracking_prohibited(),
8035
+ 'is_uninstalled' => false,
8036
  ), $override );
8037
  }
8038
 
8077
  // }
8078
 
8079
  // Common properties.
8080
+ $versions = $this->get_versions();
8081
+ $common = array_merge( $versions, array(
8082
+ 'version' => $this->get_plugin_version(),
8083
+ 'is_premium' => $this->is_premium(),
 
 
8084
  ), $override );
8085
 
8086
 
8234
  $params = $this->get_install_diff_for_api( $check_properties, $this->_site, $override );
8235
  }
8236
 
8237
+ $keepalive_only_update = false;
8238
+ if ( empty( $params ) ) {
8239
+ $keepalive_only_update = $this->should_send_keepalive_update();
8240
+
8241
+ if ( ! $keepalive_only_update ) {
8242
+ /**
8243
+ * There are no updates to send including keepalive.
8244
+ *
8245
+ * @author Leo Fajardo (@leorw)
8246
+ * @since 2.2.3
8247
+ */
8248
+ return false;
8249
+ }
8250
+ }
8251
+
8252
+ if ( ! $keepalive_only_update ) {
8253
+ /**
8254
+ * Do not update the last install sync timestamp after a keepalive-only call since there were no actual
8255
+ * updates sent.
8256
+ *
8257
+ * @author Leo Fajardo (@leorw)
8258
+ * @since 2.2.3
8259
+ */
8260
  if ( ! is_multisite() ) {
8261
  // Update last install sync timestamp.
8262
  $this->set_cron_execution_timestamp( 'install_sync' );
8263
  }
8264
 
8265
  $params['uid'] = $this->get_anonymous_id();
8266
+ }
8267
 
8268
+ $this->set_keepalive_timestamp();
 
8269
 
8270
+ // Send updated values to FS.
8271
+ $site = $this->get_api_site_scope()->call( '/', 'put', $params );
 
 
 
 
8272
 
8273
+ if ( ! $keepalive_only_update && $this->is_api_result_entity( $site ) ) {
8274
+ /**
8275
+ * Do not clear scheduled sync after a keepalive-only call since there were no actual updates sent.
8276
+ *
8277
+ * @author Leo Fajardo (@leorw)
8278
+ * @since 2.2.3
8279
+ */
8280
+ if ( ! is_multisite() ) {
8281
+ // I successfully sent install update, clear scheduled sync if exist.
8282
+ $this->clear_install_sync_cron();
8283
+ }
8284
  }
8285
 
8286
+ return $site;
8287
  }
8288
 
8289
  /**
8302
 
8303
  $installs_data = $this->get_installs_data_for_api( $override, ! $flush );
8304
 
8305
+ $keepalive_only_update = false;
8306
  if ( empty( $installs_data ) ) {
8307
+ /**
8308
+ * Pass `true` to use the network level storage since the update is for many installs.
8309
+ *
8310
+ * @author Leo Fajardo (@leorw)
8311
+ * @since 2.2.3
8312
+ */
8313
+ $keepalive_only_update = $this->should_send_keepalive_update( true );
8314
+
8315
+ if ( ! $keepalive_only_update ) {
8316
+ /**
8317
+ * There are no updates to send including keepalive.
8318
+ *
8319
+ * @author Leo Fajardo (@leorw)
8320
+ * @since 2.2.3
8321
+ */
8322
+ return false;
8323
+ }
8324
  }
8325
 
8326
+ if ( ! $keepalive_only_update ) {
8327
+ // Update last install sync timestamp if there were actual updates sent (i.e., not a keepalive-only call).
8328
+ $this->set_cron_execution_timestamp( 'install_sync' );
8329
+ }
8330
+
8331
+ /**
8332
+ * Pass `true` to use the network level storage since the update is for many installs.
8333
+ *
8334
+ * @author Leo Fajardo (@leorw)
8335
+ * @since 2.2.3
8336
+ */
8337
+ $this->set_keepalive_timestamp( true );
8338
 
8339
  // Send updated values to FS.
8340
  $result = $this->get_api_user_scope()->call( "/plugins/{$this->_plugin->id}/installs.json", 'put', $installs_data );
8341
 
8342
+ if ( ! $keepalive_only_update && $this->is_api_result_object( $result, 'installs' ) ) {
8343
+ // I successfully sent installs update (there was an actual update sent and it's not just a keepalive-only call), clear scheduled sync if exist.
8344
  $this->clear_install_sync_cron();
8345
  }
8346
 
8347
  return $result;
8348
  }
8349
 
8350
+ /**
8351
+ * @author Leo Fajardo (@leorw)
8352
+ *
8353
+ * @param bool|null $use_network_level_storage
8354
+ *
8355
+ * @return bool
8356
+ */
8357
+ private function should_send_keepalive_update( $use_network_level_storage = null ) {
8358
+ $keepalive_timestamp = $this->_storage->get( 'keepalive_timestamp', 0, $use_network_level_storage );
8359
+
8360
+ if ( $keepalive_timestamp < ( time() - WP_FS__TIME_WEEK_IN_SEC ) ) {
8361
+ // If updated more than 7 days ago, trigger a keepalive and update the time it was triggered.
8362
+ return true;
8363
+ } else {
8364
+ // If updated 7 days ago or less, "flip a coin", if the value is 7 trigger a keepalive and update the last time it was triggered.
8365
+ return ( 7 == rand( 1, 7 ) );
8366
+ }
8367
+ }
8368
+
8369
  /**
8370
  * Update install only if changed.
8371
  *
8570
  // @todo Decide if we want to delete plugin information from db.
8571
  }
8572
 
8573
+ /**
8574
+ * Set the basename of the current product and hook _activate_plugin_event_hook() to the activation action.
8575
+ *
8576
+ * @author Vova Feldman (@svovaf)
8577
+ * @since 2.2.1
8578
+ *
8579
+ * @param string $is_premium
8580
+ * @param string $caller
8581
+ *
8582
+ * @return string
8583
+ */
8584
+ function set_basename( $is_premium, $caller ) {
8585
+ $basename = plugin_basename( $caller );
8586
+
8587
+ $current_basename = $is_premium ?
8588
+ $this->_premium_plugin_basename :
8589
+ $this->_free_plugin_basename;
8590
+
8591
+ if ( $current_basename == $basename ) {
8592
+ // Basename value set correctly.
8593
+ return;
8594
+ }
8595
+
8596
+ if ( $is_premium ) {
8597
+ $this->_premium_plugin_basename = $basename;
8598
+ } else {
8599
+ $this->_free_plugin_basename = $basename;
8600
+ }
8601
+
8602
+ $plugin_dir = dirname( $this->_plugin_dir_path ) . '/';
8603
+
8604
+ register_activation_hook(
8605
+ $plugin_dir . $basename,
8606
+ array( &$this, '_activate_plugin_event_hook' )
8607
+ );
8608
+ }
8609
+
8610
  /**
8611
  * @author Vova Feldman (@svovaf)
8612
  * @since 1.1.1
8613
+ * @since 2.2.1 If the context product is in its premium version, use the current module's basename, even if it was renamed.
8614
  *
8615
  * @return string
8616
  */
8617
  function premium_plugin_basename() {
8618
+ if ( ! isset( $this->_premium_plugin_basename ) ) {
8619
+ $this->_premium_plugin_basename = $this->is_premium() ?
8620
+ // The product is premium, so use the current basename.
8621
+ $this->_plugin_basename :
8622
+ $this->get_premium_slug() . '/' . basename( $this->_free_plugin_basename );
8623
+ }
8624
+
8625
+ return $this->_premium_plugin_basename;
8626
  }
8627
 
8628
  /**
8761
  }
8762
 
8763
  /**
8764
+ * @author Leo Fajardo (@leorw)
8765
+ * @since 2.2.1
8766
+ *
8767
+ * @return string
8768
+ */
8769
+ function get_premium_slug() {
8770
+ return is_object( $this->_plugin ) ?
8771
+ $this->_plugin->premium_slug :
8772
+ "{$this->_slug}-premium";
8773
+ }
8774
+
8775
+ /**
8776
+ * Retrieve the desired folder name for the product.
8777
+ *
8778
  * @author Vova Feldman (@svovaf)
8779
  * @since 1.2.1.7
8780
  *
8781
  * @return string Plugin slug.
8782
  */
8783
  function get_target_folder_name() {
8784
+ return $this->can_use_premium_code() ?
8785
+ $this->_plugin->premium_slug :
8786
+ $this->_slug;
8787
  }
8788
 
8789
  /**
8854
  * @author Vova Feldman (@svovaf)
8855
  * @since 1.0.9
8856
  *
8857
+ * @param string|bool $premium_suffix
8858
+ *
8859
  * @return string
8860
  */
8861
+ function get_plugin_name( $premium_suffix = false ) {
8862
  $this->_logger->entrance();
8863
 
8864
+ /**
8865
+ * This `if-else` can be squeezed into a single `if` but I intentionally split it for code readability.
8866
+ *
8867
+ * @author Vova Feldman
8868
+ */
8869
  if ( ! isset( $this->_plugin_name ) ) {
8870
+ // Name is not yet set.
8871
+ $this->set_name( $premium_suffix );
8872
+ } else if (
8873
+ ! empty( $premium_suffix ) &&
8874
+ ( ! is_object( $this->_plugin ) || $this->_plugin->premium_suffix !== $premium_suffix )
8875
+ ) {
8876
+ // Name is already set, but there's a change in the premium suffix.
8877
+ $this->set_name( $premium_suffix );
8878
+ }
8879
 
8880
+ return $this->_plugin_name;
8881
+ }
8882
+
8883
+ /**
8884
+ * Calculates and stores the product's name. This helper function was created specifically for get_plugin_name() just to make the code clearer.
8885
+ *
8886
+ * @author Vova Feldman (@svovaf)
8887
+ * @since 2.2.1
8888
+ *
8889
+ * @param string $premium_suffix
8890
+ */
8891
+ private function set_name( $premium_suffix = '' ) {
8892
+ $plugin_data = $this->get_plugin_data();
8893
 
8894
+ // Get name.
8895
+ $this->_plugin_name = $plugin_data['Name'];
 
8896
 
8897
+ if ( is_string( $premium_suffix ) ) {
8898
+ $premium_suffix = trim( $premium_suffix );
8899
+
8900
+ if ( ! empty( $premium_suffix ) ) {
8901
+ // Check if plugin name contains " (premium)" or a custom suffix and remove it.
8902
+ $suffix = ( ' ' . strtolower( $premium_suffix ) );
8903
+ $suffix_len = strlen( $suffix );
8904
 
8905
+ if ( strlen( $plugin_data['Name'] ) > $suffix_len &&
8906
+ $suffix === substr( strtolower( $plugin_data['Name'] ), - $suffix_len )
8907
+ ) {
8908
+ $this->_plugin_name = substr( $plugin_data['Name'], 0, - $suffix_len );
8909
+ }
8910
+ }
8911
  }
8912
 
8913
+ $this->_logger->departure( 'Name = ' . $this->_plugin_name );
8914
  }
8915
 
8916
  /**
9616
  * @return bool
9617
  */
9618
  function is_premium() {
9619
+ /**
9620
+ * `$this->_plugin` will be `false` when `is_activation_mode` calls this method directly from the
9621
+ * `_register_hooks` method.
9622
+ *
9623
+ * @author Leo Fajardo (@leorw)
9624
+ * @since 2.2.3
9625
+ */
9626
+ return is_object( $this->_plugin ) ?
9627
+ $this->_plugin->is_premium :
9628
+ false;
9629
  }
9630
 
9631
  /**
11008
  */
11009
  function _add_license_activation_dialog_box() {
11010
  $vars = array(
11011
+ 'id' => $this->_module_id,
11012
+ );
11013
+
11014
+ fs_require_template( 'forms/license-activation.php', $vars );
11015
+ fs_require_template( 'forms/resend-key.php', $vars );
11016
+ }
11017
+
11018
+ /**
11019
+ * Displays a subscription cancellation dialog box when the user clicks on the "Deactivate License"
11020
+ * link on the "Account" page or deactivates a plugin and there's an active subscription that is
11021
+ * either associated with a non-lifetime single-site license or non-lifetime multisite license that
11022
+ * is only activated on a single production site.
11023
+ *
11024
+ * @author Leo Fajardo (@leorw)
11025
+ * @since 2.2.1
11026
+ *
11027
+ * @param bool $is_license_deactivation
11028
+ */
11029
+ function _maybe_add_subscription_cancellation_dialog_box( $is_license_deactivation = false ) {
11030
+ if ( fs_is_network_admin() ) {
11031
+ // Subscription cancellation dialog box is currently not supported for multisite networks.
11032
+ return;
11033
+ }
11034
+
11035
+ $license = $this->_get_license();
11036
+
11037
+ /**
11038
+ * If the installation is associated with a non-lifetime license, which is either a single-site or only activated on a single production site (or zero), and connected to an active subscription, suggest the customer to cancel the subscription upon deactivation.
11039
+ *
11040
+ * @author Leo Fajardo (@leorw) (Comment added by Vova Feldman @svovaf)
11041
+ * @since 2.2.1
11042
+ */
11043
+ if ( ! is_object( $license ) ||
11044
+ $license->is_lifetime() ||
11045
+ ( ! $license->is_single_site() && $license->activated > 1 )
11046
+ ) {
11047
+ return;
11048
+ }
11049
+
11050
+ /**
11051
+ * @var FS_Subscription $subscription
11052
+ */
11053
+ $subscription = $this->_get_subscription( $license->id );
11054
+ if ( ! is_object( $subscription ) || ! $subscription->is_active() ) {
11055
+ return;
11056
+ }
11057
+
11058
+ $vars = array(
11059
+ 'id' => $this->_module_id,
11060
+ 'license' => $license,
11061
+ 'has_trial' => $this->is_paid_trial(),
11062
+ 'is_license_deactivation' => $is_license_deactivation,
11063
  );
11064
 
11065
+ fs_require_template( 'forms/subscription-cancellation.php', $vars );
 
11066
  }
11067
 
11068
  /**
11149
  return;
11150
  }
11151
 
11152
+ if ( ! $this->is_premium() || $this->has_any_active_valid_license() ) {
11153
  // This is relevant only to the free versions and premium versions without an active license.
11154
  return;
11155
  }
11249
  'license_key' => $fs->apply_filters( 'license_key', $license_key )
11250
  );
11251
 
11252
+ $install = $api->call( $fs->add_show_pending( '/' ), 'put', $params );
11253
 
11254
  if ( FS_Api::is_api_error( $install ) ) {
11255
  $error = FS_Api::is_api_error_object( $install ) ?
11342
  }
11343
  }
11344
 
11345
+ if ( false === $error && true === $this->_storage->require_license_activation ) {
11346
+ $this->_storage->require_license_activation = false;
11347
+ }
11348
+
11349
  $result = array(
11350
  'success' => ( false === $error )
11351
  );
11600
  static function get_current_page() {
11601
  if ( ! isset( self::$_pagenow ) ) {
11602
  global $pagenow;
11603
+ if ( empty( $pagenow ) && is_admin() && is_multisite() ) {
11604
+ /**
11605
+ * It appears that `$pagenow` is not yet initialized in some network admin pages when this method
11606
+ * is called, so initialize it here using some pieces of code from `wp-includes/vars.php`.
11607
+ *
11608
+ * @author Leo Fajardo (@leorw)
11609
+ * @since 2.2.3
11610
+ */
11611
+ if ( is_network_admin() ) {
11612
+ preg_match( '#/wp-admin/network/?(.*?)$#i', $_SERVER['PHP_SELF'], $self_matches );
11613
+ } else if ( is_user_admin() ) {
11614
+ preg_match( '#/wp-admin/user/?(.*?)$#i', $_SERVER['PHP_SELF'], $self_matches );
11615
+ } else {
11616
+ preg_match( '#/wp-admin/?(.*?)$#i', $_SERVER['PHP_SELF'], $self_matches );
11617
+ }
11618
+
11619
+ $pagenow = $self_matches[1];
11620
+ $pagenow = trim( $pagenow, '/' );
11621
+ $pagenow = preg_replace( '#\?.*?$#', '', $pagenow );
11622
+ if ( '' === $pagenow || 'index' === $pagenow || 'index.php' === $pagenow ) {
11623
+ $pagenow = 'index.php';
11624
+ } else {
11625
+ preg_match( '#(.*?)(/|$)#', $pagenow, $self_matches );
11626
+ $pagenow = strtolower( $self_matches[1] );
11627
+ if ( '.php' !== substr($pagenow, -4, 4) )
11628
+ $pagenow .= '.php'; // for Options +Multiviews: /wp-admin/themes/index.php (themes.php is queried)
11629
+ }
11630
+ }
11631
 
11632
  self::$_pagenow = $pagenow;
11633
 
11659
  return ( 'plugins.php' === self::get_current_page() );
11660
  }
11661
 
11662
+ /**
11663
+ * @author Leo Fajardo (@leorw)
11664
+ * @since 2.2.3
11665
+ *
11666
+ * @return bool
11667
+ */
11668
+ static function is_plugin_install_page() {
11669
+ return ( 'plugin-install.php' === self::get_current_page() );
11670
+ }
11671
+
11672
  /**
11673
  * @author Leo Fajardo (@leorw)
11674
  * @since 2.0.2
11936
  return $this->get_upgrade_url( WP_FS__PERIOD_ANNUALLY, true );
11937
  }
11938
 
11939
+ /**
11940
+ * @author Leo Fajardo (@leorw)
11941
+ * @since 2.1.4
11942
+ *
11943
+ * @param string $new_version
11944
+ *
11945
+ * @return string
11946
+ */
11947
+ function version_upgrade_checkout_link( $new_version ) {
11948
+ if ( ! is_object( $this->_license ) ) {
11949
+ $url = $this->pricing_url();
11950
+
11951
+ $purchase_license_text = $this->get_text_inline( 'Buy a license now', 'buy-license-now' );
11952
+ } else {
11953
+ $subscription = $this->_get_subscription( $this->_license->id );
11954
+
11955
+ $url = $this->checkout_url(
11956
+ is_object( $subscription ) ?
11957
+ ( 1 == $subscription->billing_cycle ? WP_FS__PERIOD_MONTHLY : WP_FS__PERIOD_ANNUALLY ) :
11958
+ WP_FS__PERIOD_LIFETIME,
11959
+ false,
11960
+ array( 'licenses' => $this->_license->quota )
11961
+ );
11962
+
11963
+ $purchase_license_text = $this->get_text_inline( 'Renew your license now', 'renew-license-now' );
11964
+ }
11965
+
11966
+ return sprintf(
11967
+ $this->get_text_inline( '%s to access version %s security & feature updates, and support.', 'x-for-updates-and-support' ),
11968
+ sprintf( '<a href="%s">%s</a>', $url, $purchase_license_text ),
11969
+ $new_version
11970
+ );
11971
+ }
11972
+
11973
  /**
11974
  * Plugin's pricing URL.
11975
  *
12604
  * @author Vova Feldman (@svovaf)
12605
  */
12606
  $args = array(
12607
+ /**
12608
+ * Commented out in order to handle the migration of site options whether the site is public or not.
12609
+ *
12610
+ * @author Leo Fajardo (@leorw)
12611
+ * @since 2.2.1
12612
+ */
12613
+ // 'public' => 1,
12614
  'archived' => 0,
12615
  'mature' => 0,
12616
  'spam' => 0,
12806
 
12807
  self::$_accounts->set_site_blog_context( $blog_id );
12808
  $this->_storage->set_site_blog_context( $blog_id );
12809
+ $this->_storage->set_network_active( $this->_is_network_active, $this->is_delegated_connection( $blog_id ) );
12810
 
12811
  $this->_site = is_object( $install ) ?
12812
  $install :
13755
  }
13756
  }
13757
 
13758
+ if ( true === $this->_storage->require_license_activation &&
13759
+ ! fs_request_get_bool( 'require_license', true )
13760
+ ) {
13761
+ $this->_storage->require_license_activation = false;
13762
+ }
13763
+
13764
  if ( $this->is_theme() ) {
13765
  $this->_register_account_hooks();
13766
  }
13826
 
13827
  }
13828
 
13829
+ /**
13830
+ * Get a sanitized array with the WordPress version, SDK version, and PHP version.
13831
+ * Each version is trimmed after the 16th char.
13832
+ *
13833
+ * @author Vova Feldman (@svovaf)
13834
+ * @since 2.2.1
13835
+ *
13836
+ * @return array
13837
+ */
13838
+ private function get_versions() {
13839
+ $versions = array();
13840
+ $versions['platform_version'] = get_bloginfo( 'version' );
13841
+ $versions['sdk_version'] = $this->version;
13842
+ $versions['programming_language_version'] = phpversion();
13843
+
13844
+ foreach ( $versions as $k => $version ) {
13845
+ if ( is_string( $versions[ $k ] ) && ! empty( $versions[ $k ] ) ) {
13846
+ $versions[ $k ] = substr( $versions[ $k ], 0, 16 );
13847
+ }
13848
+ }
13849
+
13850
+ return $versions;
13851
+ }
13852
+
13853
  /**
13854
  * @author Vova Feldman (@svovaf)
13855
  * @since 1.1.7.4
13871
  // Return to the module's main page.
13872
  $this->get_after_activation_url( 'after_connect_url', array( 'fs_action' => $activation_action ) );
13873
 
13874
+ $versions = $this->get_versions();
13875
+
13876
+ $params = array_merge( $versions, array(
13877
  'user_firstname' => $current_user->user_firstname,
13878
  'user_lastname' => $current_user->user_lastname,
13879
  'user_nickname' => $current_user->user_nicename,
13888
  'account',
13889
  array( 'fs_action' => 'sync_user' )
13890
  ), 'sync_user' ),
 
 
 
13891
  'is_premium' => $this->is_premium(),
13892
  'is_active' => true,
13893
  'is_uninstalled' => false,
13894
+ ) );
13895
 
13896
  if ( true === $network_level_or_blog_id ) {
13897
  if ( ! isset( $override_with['sites'] ) ) {
14077
  'timeout' => WP_FS__DEBUG_SDK ? 60 : 30,
14078
  );
14079
 
14080
+ $url = $this->add_show_pending( WP_FS__ADDRESS . '/action/service/user/install/' );
14081
  $response = self::safe_remote_post( $url, $request );
14082
 
14083
  if ( is_wp_error( $response ) ) {
15234
 
15235
  $hook = false;
15236
 
15237
+ if ( ! $this->has_settings_menu() ) {
15238
  // Add the opt-in page without a menu item.
15239
  $hook = FS_Admin_Menu_Manager::add_subpage(
15240
  null,
15582
  }
15583
  }
15584
 
15585
+ if ( ! $is_activation_mode || ( true !== $this->_storage->require_license_activation ) ) {
15586
+ /**
15587
+ * Add the other menu items if there are any when not in activation mode or license activation is not
15588
+ * required (license activation is required for registered or anonymous users after activating the
15589
+ * premium version when the site is not in trial mode or there's no active valid license).
15590
+ *
15591
+ * @author Leo Fajardo (@leorw)
15592
+ * @since 2.2.1
15593
+ */
15594
+ if ( 0 < count( $this->_menu_items ) ) {
15595
+ if ( ! $this->_menu->is_top_level() ) {
15596
+ fs_enqueue_local_style( 'fs_common', '/admin/common.css' );
15597
 
15598
+ // Append submenu items right after the plugin's submenu item.
15599
+ $this->order_sub_submenu_items();
15600
+ } else {
15601
+ // Append submenu items.
15602
+ $this->embed_submenu_items();
15603
+ }
15604
  }
15605
  }
15606
  }
15626
 
15627
  foreach ( $this->_menu_items as $priority => $items ) {
15628
  foreach ( $items as $item ) {
 
 
 
 
 
 
 
 
 
 
15629
  $capability = ( ! empty( $item['capability'] ) ? $item['capability'] : $top_level_menu_capability );
15630
 
15631
  $menu_item = sprintf(
15636
  $item['menu_title']
15637
  );
15638
 
15639
+ $top_level_menu_slug = $this->get_top_level_menu_slug();
15640
+ $menu_slug = $this->_menu->get_slug( $item['menu_slug'] );
15641
 
15642
  if ( ! isset( $item['url'] ) ) {
15643
  $hook = FS_Admin_Menu_Manager::add_subpage(
15644
  $item['show_submenu'] ?
15645
+ $top_level_menu_slug :
15646
  null,
15647
  $item['page_title'],
15648
  $menu_item,
15657
  } else {
15658
  FS_Admin_Menu_Manager::add_subpage(
15659
  $item['show_submenu'] ?
15660
+ $top_level_menu_slug :
15661
  null,
15662
  $item['page_title'],
15663
  $menu_item,
15666
  array( $this, '' )
15667
  );
15668
  }
15669
+
15670
+ if ( $item['show_submenu'] && $is_first_submenu_item ) {
15671
+ if ( $this->_is_network_active && ! empty( $this->_dynamically_added_top_level_page_hook_name ) ) {
15672
+ /**
15673
+ * If the top-level menu has been dynamically created, remove the first submenu item that
15674
+ * WordPress automatically creates when there's no submenu item whose slug matches the
15675
+ * parent's. In the following example, the `Awesome Plugin` submenu item will be removed.
15676
+ *
15677
+ * Awesome Plugin
15678
+ * - Awesome Plugin <-- we want to remove this since there's no real setting page for the top-level
15679
+ *
15680
+ * @author Leo Fajardo (@leorw)
15681
+ */
15682
+ remove_submenu_page( $top_level_menu_slug, $top_level_menu_slug );
15683
+ }
15684
+
15685
+ $is_first_submenu_item = false;
15686
+ }
15687
  }
15688
  }
15689
  }
16926
  * @param bool|number $plugin_id
16927
  * @param bool $flush Since 1.1.7.3
16928
  * @param int $expiration Since 1.2.2.7
16929
+ * @param bool|string $newer_than Since 2.2.1
16930
  *
16931
  * @return object|false New plugin tag info if exist.
16932
  */
16933
+ private function _fetch_newer_version( $plugin_id = false, $flush = true, $expiration = WP_FS__TIME_24_HOURS_IN_SEC, $newer_than = false ) {
16934
+ $latest_tag = $this->_fetch_latest_version( $plugin_id, $flush, $expiration, $newer_than );
16935
 
16936
  if ( ! is_object( $latest_tag ) ) {
16937
  return false;
16956
  * @param bool|number $plugin_id
16957
  * @param bool $flush Since 1.1.7.3
16958
  * @param int $expiration Since 1.2.2.7
16959
+ * @param bool|string $newer_than Since 2.2.1
16960
  *
16961
  * @return bool|FS_Plugin_Tag
16962
  */
16963
+ function get_update( $plugin_id = false, $flush = true, $expiration = WP_FS__TIME_24_HOURS_IN_SEC, $newer_than = false ) {
16964
  $this->_logger->entrance();
16965
 
16966
  if ( ! is_numeric( $plugin_id ) ) {
16967
  $plugin_id = $this->_plugin->id;
16968
  }
16969
 
16970
+ $this->check_updates( true, $plugin_id, $flush, $expiration, $newer_than );
16971
  $updates = $this->get_all_updates();
16972
 
16973
  return isset( $updates[ $plugin_id ] ) && is_object( $updates[ $plugin_id ] ) ? $updates[ $plugin_id ] : false;
16996
  * @since 1.2.1
16997
  */
16998
  function has_active_valid_license() {
16999
+ return self::is_active_valid_license( $this->_license );
17000
+ }
17001
+
17002
+ /**
17003
+ * Check if a given license is active & valid (not expired).
17004
+ *
17005
+ * @author Vova Feldman (@svovaf)
17006
+ * @since 2.1.3
17007
+ *
17008
+ * @param FS_Plugin_License $license
17009
+ *
17010
+ * @return bool
17011
+ */
17012
+ private static function is_active_valid_license( $license ) {
17013
  return (
17014
+ is_object( $license ) &&
17015
+ FS_Plugin_License::is_valid_id( $license->id ) &&
17016
+ $license->is_active() &&
17017
+ $license->is_valid()
17018
  );
17019
  }
17020
 
17021
+ /**
17022
+ * Checks if there's any site that is associated with an active & valid license.
17023
+ * This logic is used to determine if the admin can download the premium code base from a network level admin.
17024
+ *
17025
+ * @author Vova Feldman (@svovaf)
17026
+ * @since 2.1.3
17027
+ *
17028
+ * @return bool
17029
+ */
17030
+ function has_any_active_valid_license() {
17031
+ if ( ! fs_is_network_admin() ) {
17032
+ return $this->has_active_valid_license();
17033
+ }
17034
+
17035
+ $installs = $this->get_blog_install_map();
17036
+ $all_plugin_licenses = self::get_all_licenses( $this->_module_id );
17037
+
17038
+ foreach ( $installs as $blog_id => $install ) {
17039
+ if ( ! FS_Plugin_License::is_valid_id( $install->license_id ) ) {
17040
+ continue;
17041
+ }
17042
+
17043
+ foreach ( $all_plugin_licenses as $license ) {
17044
+ if ( $license->id == $install->license_id ) {
17045
+ if ( self::is_active_valid_license( $license ) ) {
17046
+ return true;
17047
+ }
17048
+ }
17049
+ }
17050
+ }
17051
+
17052
+ return false;
17053
+ }
17054
+
17055
  /**
17056
  * Check if site assigned with license with enabled features.
17057
  *
17120
  * the admin.
17121
  * @param bool $is_context_single_site @since 2.0.0. This is used when syncing a license for a single install from the
17122
  * network-level "Account" page.
17123
+ * @param int|null $current_blog_id @since 2.2.3. This is passed from the `execute_cron` method and used by the
17124
+ * `_sync_plugin_license` method in order to switch to the previous blog when sending
17125
+ * updates for a single site in case `execute_cron` has switched to a different blog.
17126
  */
17127
+ private function _sync_license( $background = false, $is_context_single_site = false, $current_blog_id = null ) {
17128
  $this->_logger->entrance();
17129
 
17130
  $plugin_id = fs_request_get( 'plugin_id', $this->get_id() );
17134
  if ( $is_addon_sync ) {
17135
  $this->_sync_addon_license( $plugin_id, $background );
17136
  } else {
17137
+ $this->_sync_plugin_license( $background, true, $is_context_single_site, $current_blog_id );
17138
  }
17139
 
17140
  $this->do_action( 'after_account_plan_sync', $this->get_plan_name() );
17224
  * @param bool $is_context_single_site Since 2.0.0. This is used when sending an update for a single install and
17225
  * syncing its license from the network-level "Account" page (e.g.: after
17226
  * activating a license only for the single install).
17227
+ * @param int|null $current_blog_id Since 2.2.3. This is passed from the `execute_cron` method so that it
17228
+ * can be used here to switch to the previous blog in case `execute_cron`
17229
+ * has switched to a different blog.
17230
  */
17231
  private function _sync_plugin_license(
17232
  $background = false,
17233
  $send_installs_update = true,
17234
+ $is_context_single_site = false,
17235
+ $current_blog_id = null
17236
  ) {
17237
  $this->_logger->entrance();
17238
 
17249
  * @todo This line will execute install sync on a daily basis, even if running the free version (for opted-in users). The reason we want to keep it that way is for cases when the user was a paying customer, then there was a failure in subscription payment, and then after some time the payment was successful. This could be heavily optimized. For example, we can skip the $flush if the current install was never associated with a paid version.
17250
  */
17251
  if ( $is_site_level_sync ) {
17252
+ /**
17253
+ * Switch to the previous blog since `execute_cron` may have switched to a different blog.
17254
+ *
17255
+ * @author Leo Fajardo (@leorw)
17256
+ * @since 2.2.3
17257
+ */
17258
+ if ( is_numeric( $current_blog_id ) ) {
17259
+ $this->switch_to_blog( $current_blog_id );
17260
+ }
17261
+
17262
  $result = $this->send_install_update( array(), true );
17263
  $is_valid = $this->is_api_result_entity( $result );
17264
  } else {
17768
  $api = $this->get_api_site_scope();
17769
  $license = $api->call( "/licenses/{$this->_site->license_id}.json", 'delete' );
17770
 
17771
+ $this->handle_license_deactivation_result( $license, $hmm_text, $show_notice );
17772
+ }
17773
+
17774
+ /**
17775
+ * @author Leo Fajardo (@leorw)
17776
+ * @since 2.2.1
17777
+ *
17778
+ * @param FS_Plugin_License $license
17779
+ * @param bool|string $hmm_text
17780
+ * @param bool $show_notice
17781
+ */
17782
+ private function handle_license_deactivation_result( $license, $hmm_text = false, $show_notice = true ) {
17783
  if ( isset( $license->error ) ) {
17784
  $this->_admin_notices->add(
17785
  $this->get_text_inline( 'It looks like the license deactivation failed.', 'license-deactivation-failed-message' ) . '<br> ' .
17800
  }
17801
  }
17802
 
17803
+ // Update site plan to default.
17804
  $this->_sync_plans();
17805
  $this->_site->plan_id = $this->_plans[0]->id;
17806
  // Unlink license from site.
17827
  * @author Vova Feldman (@svovaf)
17828
  * @since 1.0.4
17829
  *
17830
+ * @return object
17831
+ *
17832
  * @uses FS_Api
17833
  */
17834
  private function _downgrade_site() {
17835
  $this->_logger->entrance();
17836
 
17837
+ $deactivate_license = fs_request_get_bool( 'deactivate_license' );
17838
+
17839
  $api = $this->get_api_site_scope();
17840
+ $site = $api->call( 'downgrade.json', 'put', array( 'deactivate_license' => $deactivate_license ) );
17841
 
17842
  $plan_downgraded = false;
17843
  $plan = false;
17855
  ( is_object( $subscription ) && ! isset( $subscription->error ) && ! $subscription->is_active() );
17856
  } else {
17857
  // handle different error cases.
17858
+ $this->handle_license_deactivation_result(
17859
+ $site,
17860
+ $this->get_text_x_inline( 'Hmm', 'something somebody says when they are thinking about what you have just said.', 'hmm' ) . '...'
17861
+ );
17862
  }
17863
 
17864
+ if ( ! $plan_downgraded ) {
17865
+ return (object) array(
17866
+ 'error' => (object) array(
17867
+ 'message' => $this->get_text_inline( 'Seems like we are having some temporary issue with your subscription cancellation. Please try again in few minutes.', 'subscription-cancellation-failure-message' )
 
 
 
 
17868
  )
17869
  );
17870
+ }
17871
 
17872
+ // Remove previous sticky message about upgrade (if exist).
17873
+ $this->_admin_notices->remove_sticky( 'plan_upgraded' );
17874
+
17875
+ $this->_admin_notices->add(
17876
+ sprintf( $this->get_text_inline( 'Your subscription was successfully cancelled. Your %s plan license will expire in %s.', 'plan-x-downgraded-message' ),
17877
+ $plan->title,
17878
+ human_time_diff( time(), strtotime( $this->_license->expiration ) )
17879
+ )
17880
+ );
17881
+
17882
+ // Store site updates.
17883
+ $this->_store_site();
17884
+
17885
+ if ( $deactivate_license &&
17886
+ ! FS_Plugin_License::is_valid_id( $site->license_id )
17887
+ ) {
17888
+ if ( $this->_site->is_localhost() ) {
17889
+ $this->_license->activated_local = max( 0, $this->_license->activated_local - 1 );
17890
+ } else {
17891
+ $this->_license->activated = max( 0, $this->_license->activated - 1 );
17892
+ }
17893
+
17894
+ // Handle successful license deactivation result.
17895
+ $this->handle_license_deactivation_result( $this->_license );
17896
  }
17897
+
17898
+ return $site;
17899
  }
17900
 
17901
  /**
18002
  * @author Vova Feldman (@svovaf)
18003
  * @since 1.0.9
18004
  *
18005
+ * @return object
18006
+ *
18007
  * @uses FS_Api
18008
  */
18009
  private function _cancel_trial() {
18010
  $this->_logger->entrance();
18011
 
 
 
 
18012
  if ( ! $this->is_trial() ) {
18013
+ return (object) array(
18014
+ 'error' => (object) array(
18015
+ 'message' => $this->get_text_inline( 'It looks like you are not in trial mode anymore so there\'s nothing to cancel :)', 'trial-cancel-no-trial-message' )
18016
+ )
18017
  );
 
 
18018
  }
18019
 
18020
  $trial_plan = $this->get_trial_plan();
18045
  // @todo handle different error cases.
18046
  }
18047
 
18048
+ if ( ! $trial_cancelled ) {
18049
+ return (object) array(
18050
+ 'error' => (object) array(
18051
+ 'message' => $this->get_text_inline( 'Seems like we are having some temporary issue with your trial cancellation. Please try again in few minutes.', 'trial-cancel-failure-message' )
18052
+ )
18053
+ );
18054
+ }
18055
 
18056
+ // Remove previous sticky messages about upgrade or trial (if exist).
18057
+ $this->_admin_notices->remove_sticky( array(
18058
+ 'trial_started',
18059
+ 'trial_promotion',
18060
+ 'plan_upgraded',
18061
+ ) );
18062
 
18063
+ // Store site updates.
18064
+ $this->_store_site();
18065
+
18066
+ if ( ! $this->is_addon() ||
18067
+ ! $this->deactivate_premium_only_addon_without_license( true )
18068
+ ) {
 
 
18069
  $this->_admin_notices->add(
18070
+ sprintf( $this->get_text_inline( 'Your %s free trial was successfully cancelled.', 'trial-cancel-message' ), $trial_plan->title )
 
 
18071
  );
18072
  }
18073
+
18074
+ return $site;
18075
  }
18076
 
18077
  /**
18095
  * @return bool
18096
  */
18097
  private function _can_download_premium() {
18098
+ return $this->has_any_active_valid_license() ||
18099
  ( $this->is_trial() && ! $this->get_trial_plan()->is_free() );
18100
  }
18101
 
18142
  * @since 1.0.4
18143
  *
18144
  * @param bool|number $addon_id
18145
+ * @param bool $flush Since 1.1.7.3
18146
+ * @param int $expiration Since 1.2.2.7
18147
+ * @param bool|string $newer_than Since 2.2.1
18148
+ * @param bool|string $fetch_readme Since 2.2.1
18149
  *
18150
  * @return object|false Plugin latest tag info.
18151
  */
18152
  function _fetch_latest_version(
18153
  $addon_id = false,
18154
  $flush = true,
18155
+ $expiration = WP_FS__TIME_24_HOURS_IN_SEC,
18156
+ $newer_than = false,
18157
+ $fetch_readme = true
18158
  ) {
18159
  $this->_logger->entrance();
18160
 
18205
  $this->switch_to_blog( $switch_to_blog_id );
18206
  }
18207
 
18208
+ $latest_version_endpoint = $this->_get_latest_version_endpoint( $addon_id, 'json' );
18209
+
18210
+ if ( ! empty( $newer_than ) ) {
18211
+ $latest_version_endpoint = add_query_arg( 'newer_than', $newer_than, $latest_version_endpoint );
18212
+ }
18213
+
18214
+ if ( true === $fetch_readme ) {
18215
+ $latest_version_endpoint = add_query_arg( 'readme', 'true', $latest_version_endpoint );
18216
+ }
18217
+
18218
  $tag = $this->get_api_site_or_plugin_scope()->get(
18219
+ $latest_version_endpoint,
18220
  $flush,
18221
  $expiration
18222
  );
18352
  * @param bool|number $plugin_id
18353
  * @param bool $flush Since 1.1.7.3
18354
  * @param int $expiration Since 1.2.2.7
18355
+ * @param bool|string $newer_than Since 2.2.1
18356
  */
18357
  private function check_updates(
18358
  $background = false,
18359
  $plugin_id = false,
18360
  $flush = true,
18361
+ $expiration = WP_FS__TIME_24_HOURS_IN_SEC,
18362
+ $newer_than = false
18363
  ) {
18364
  $this->_logger->entrance();
18365
 
18366
  // Check if there's a newer version for download.
18367
+ $new_version = $this->_fetch_newer_version( $plugin_id, $flush, $expiration, $newer_than );
18368
 
18369
  $update = null;
18370
  if ( is_object( $new_version ) ) {
18720
  */
18721
  function get_after_activation_url( $filter, $params = array(), $network = null ) {
18722
  if ( $this->is_free_wp_org_theme() &&
18723
+ ( fs_request_has( 'pending_activation' ) ||
18724
+ // For cases when the first time path is set, even though it's a WP.org theme.
18725
+ fs_request_get_bool( $this->get_unique_affix() . '_show_optin' ) )
18726
  ) {
18727
  $first_time_path = '';
18728
  } else {
18854
  $this->_site = null;
18855
  $this->_user = null;
18856
 
18857
+ $this->maybe_set_slug_and_network_menu_exists_flag();
18858
+
18859
  fs_redirect( $this->get_activation_url() );
18860
  } else {
18861
  if ( $this->is_addon_activated( $plugin_id ) ) {
18875
  check_admin_referer( $action );
18876
  }
18877
 
18878
+ $switch_to_network_install_blog_after_cancellation = (
18879
+ is_numeric( $blog_id ) &&
18880
+ $plugin_id == $this->get_id() &&
18881
+ ! $this->is_trial()
18882
+ );
18883
 
18884
+ $result = $this->cancel_subscription_or_trial( $plugin_id );
18885
+ if ( $this->is_api_error( $result ) ) {
18886
+ $this->_admin_notices->add(
18887
+ $result->error->message,
18888
+ $this->get_text_x_inline( 'Oops', 'exclamation', 'oops' ) . '...',
18889
+ 'error'
18890
+ );
18891
+ }
18892
+
18893
+ if ( $switch_to_network_install_blog_after_cancellation ) {
18894
+ $this->switch_to_blog( $this->_storage->network_install_blog_id );
18895
  }
18896
 
18897
  return;
18923
  $this->_site = null;
18924
  $this->_user = null;
18925
 
18926
+ if ( ! $is_network_action ) {
18927
+ fs_redirect( $this->get_activation_url() );
18928
+ } else if ( is_numeric( $blog_id ) ) {
18929
+ $this->switch_to_blog( $this->_storage->network_install_blog_id );
18930
+ }
18931
  }
18932
  } else {
18933
  if ( $this->is_addon_activated( $plugin_id ) ) {
19025
  #region Actions that might be called from external links (e.g. email)
19026
 
19027
  case 'cancel_trial':
19028
+ $result = $this->cancel_subscription_or_trial( $plugin_id );
19029
+ if ( $this->is_api_error( $result ) ) {
19030
+ $this->_admin_notices->add(
19031
+ $result->error->message,
19032
+ $this->get_text_x_inline( 'Oops', 'exclamation', 'oops' ) . '...',
19033
+ 'error'
19034
+ );
19035
  }
19036
 
19037
  return;
20027
 
20028
  if ( ! $this->is_addon() || ! $this->has_free_plan() ) {
20029
  $first_time_path = $this->_menu->get_first_time_path();
20030
+
20031
+ if ( $this->is_activation_mode() ) {
20032
+ $url = $this->get_activation_url();
20033
+ } else if ( ! empty( $first_time_path ) ) {
20034
+ $url = $first_time_path;
20035
+ } else {
20036
+ $page = '';
20037
+ if ( ! empty( $this->_dynamically_added_top_level_page_hook_name ) ) {
20038
+ if ( $this->is_network_registered() ) {
20039
+ $page = 'account';
20040
+ } else if ( $this->is_network_anonymous() ) {
20041
+ $this->maybe_set_slug_and_network_menu_exists_flag();
20042
+ }
20043
+ }
20044
+
20045
+ $url = $this->_get_admin_page_url( $page );
20046
+ }
20047
  } else {
20048
  $plugin_fs = false;
20049
 
20163
  $this->_admin_notices->add_sticky( $message, $id, $title, $type );
20164
  }
20165
 
20166
+ /**
20167
+ * Check if the paid version of the module is installed.
20168
+ *
20169
+ * @author Vova Feldman (@svovaf)
20170
+ * @since 2.2.0
20171
+ *
20172
+ * @return bool
20173
+ */
20174
+ private function is_premium_version_installed() {
20175
+ $premium_plugin_basename = $this->premium_plugin_basename();
20176
+ $premium_plugin = get_plugins( '/' . dirname( $premium_plugin_basename ) );
20177
+
20178
+ return ! empty( $premium_plugin );
20179
+ }
20180
+
20181
  /**
20182
  * Helper function that returns the final steps for the upgrade completion.
20183
  *
20203
  $plan_title = $this->get_plan_title();
20204
  }
20205
 
20206
+ if ( $this->is_premium_version_installed() ) {
20207
+ /**
20208
+ * If the premium version is already installed, instead of showing the installation instructions,
20209
+ * tell the current user to activate it.
20210
+ *
20211
+ * @author Leo Fajardo (@leorw)
20212
+ * @since 2.2.1
20213
+ */
20214
+ $premium_plugin_basename = $this->premium_plugin_basename();
20215
 
20216
+ return sprintf(
20217
+ /* translators: %1s: Product title; %2s: Plan title */
20218
+ $this->get_text_inline( ' The paid version of %1s is already installed. Please activate it to start benefiting the %2s features. %3s', 'activate-premium-version' ),
20219
+ sprintf( '<em>%s</em>', esc_html( $this->get_plugin_title() ) ),
20220
+ $plan_title,
20221
+ sprintf(
20222
+ '<a style="margin-left: 10px;" href="%s"><button class="button button-primary">%s</button></a>',
20223
+ wp_nonce_url( 'plugins.php?action=activate&amp;plugin=' . $premium_plugin_basename, 'activate-plugin_' . $premium_plugin_basename ),
20224
+ esc_html( sprintf(
20225
+ /* translators: %s: Plan title */
20226
+ $this->get_text_inline( 'Activate %s features', 'activate-x-features' ),
20227
+ $plan_title
20228
+ ) )
20229
+ )
20230
+ );
20231
+ } else {
20232
+ // @since 1.2.1.5 The free version is auto deactivated.
20233
+ $deactivation_step = version_compare( $this->version, '1.2.1.5', '<' ) ?
20234
+ ( '<li>' . $this->esc_html_inline( 'Deactivate the free version', 'deactivate-free-version' ) . '.</li>' ) :
20235
+ '';
20236
+
20237
+ return sprintf(
20238
+ ' %s: <ol><li>%s.</li>%s<li>%s (<a href="%s" target="_blank">%s</a>).</li></ol>',
20239
+ $this->get_text_inline( 'Please follow these steps to complete the upgrade', 'follow-steps-to-complete-upgrade' ),
20240
+ ( empty( $activate_license_string ) ? '' : $activate_license_string . '</li><li>' ) .
20241
+ $this->get_latest_download_link( sprintf(
20242
+ /* translators: %s: Plan title */
20243
+ $this->get_text_inline( 'Download the latest %s version', 'download-latest-x-version' ),
20244
+ $plan_title
20245
+ ) ),
20246
+ $deactivation_step,
20247
+ $this->get_text_inline( 'Upload and activate the downloaded version', 'upload-and-activate' ),
20248
+ '//bit.ly/upload-wp-' . $this->_module_type . 's',
20249
+ $this->get_text_inline( 'How to upload and activate?', 'howto-upload-activate' )
20250
+ );
20251
+ }
20252
  }
20253
 
20254
  /**
21031
 
21032
  // Locate the main assets folder.
21033
  if ( 1 < count( $fs_active_plugins->plugins ) ) {
21034
+ $plugin_or_theme_img_dir = ( $this->is_plugin() ? WP_PLUGIN_DIR : get_theme_root( get_stylesheet() ) );
21035
 
21036
  foreach ( $fs_active_plugins->plugins as $sdk_path => &$data ) {
21037
  if ( $data->plugin_path == $this->get_plugin_basename() ) {
21038
  $img_dir = $plugin_or_theme_img_dir
21039
  . '/'
21040
+ /**
21041
+ * The basename will be `themes` or the basename of a custom themes directory.
21042
+ *
21043
+ * @author Leo Fajardo (@leorw)
21044
+ * @since 2.2.3
21045
+ */
21046
+ . str_replace( '../' . basename( $plugin_or_theme_img_dir ) . '/', '', $sdk_path )
21047
  . '/assets/img';
21048
 
21049
  break;
vendor/freemius/includes/class-fs-api.php CHANGED
@@ -238,7 +238,7 @@
238
  if ( ! is_object( $result ) || isset( $result->error ) ) {
239
  // Api returned an error.
240
  if ( is_object( $cached_result ) &&
241
- ! isset( $cached_result )
242
  ) {
243
  // If there was an error during a newer data fetch,
244
  // fallback to older data version.
@@ -248,9 +248,19 @@
248
  $this->_logger->warn( 'Fallback to cached API result: ' . var_export( $cached_result, true ) );
249
  }
250
  } else {
251
- // If no older data version, return result without
252
- // caching the error.
253
- return $result;
 
 
 
 
 
 
 
 
 
 
254
  }
255
  }
256
 
238
  if ( ! is_object( $result ) || isset( $result->error ) ) {
239
  // Api returned an error.
240
  if ( is_object( $cached_result ) &&
241
+ ! isset( $cached_result->error )
242
  ) {
243
  // If there was an error during a newer data fetch,
244
  // fallback to older data version.
248
  $this->_logger->warn( 'Fallback to cached API result: ' . var_export( $cached_result, true ) );
249
  }
250
  } else {
251
+ if ( is_object( $result ) && 404 == $result->error->http ) {
252
+ /**
253
+ * If the response code is 404, cache the result for half of the `$expiration`.
254
+ *
255
+ * @author Leo Fajardo (@leorw)
256
+ * @since 2.2.3.1
257
+ */
258
+ $expiration /= 2;
259
+ } else {
260
+ // If no older data version and the response code is not 404, return result without
261
+ // caching the error.
262
+ return $result;
263
+ }
264
  }
265
  }
266
 
vendor/freemius/includes/class-fs-plugin-updater.php CHANGED
@@ -35,6 +35,8 @@
35
  */
36
  private $_translation_updates;
37
 
 
 
38
  #--------------------------------------------------------------------------------
39
  #region Singleton
40
  #--------------------------------------------------------------------------------
@@ -82,25 +84,25 @@
82
 
83
  $this->add_transient_filters();
84
 
85
- if ( ! $this->_fs->has_active_valid_license() ) {
86
- /**
87
- * If user has the premium plugin's code but do NOT have an active license,
88
- * encourage him to upgrade by showing that there's a new release, but instead
89
- * of showing an update link, show upgrade link to the pricing page.
90
- *
91
- * @since 1.1.6
92
- *
93
- */
94
- // WP 2.9+
95
- add_action( "after_plugin_row_{$this->_fs->get_plugin_basename()}", array(
96
- &$this,
97
- 'catch_plugin_update_row'
98
- ), 9 );
99
- add_action( "after_plugin_row_{$this->_fs->get_plugin_basename()}", array(
100
- &$this,
101
- 'edit_and_echo_plugin_update_row'
102
- ), 11, 2 );
103
- }
104
 
105
  if ( ! WP_FS__IS_PRODUCTION_MODE ) {
106
  add_filter( 'http_request_host_is_external', array(
@@ -110,16 +112,88 @@
110
  }
111
 
112
  if ( $this->_fs->is_premium() ) {
113
- if ( $this->is_correct_folder_name() ) {
114
  add_filter( 'upgrader_post_install', array( &$this, '_maybe_update_folder_name' ), 10, 3 );
115
  }
116
 
117
- if ( ! $this->_fs->has_active_valid_license() ) {
 
 
 
118
  add_filter( 'wp_prepare_themes_for_js', array( &$this, 'change_theme_update_info_html' ), 10, 1 );
119
  }
120
  }
121
  }
122
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
123
  /**
124
  * @author Vova Feldman (@svovaf)
125
  * @since 2.0.0
@@ -183,15 +257,57 @@
183
 
184
  $r = $current->response[ $file ];
185
 
186
- $plugin_update_row = preg_replace(
187
- '/(\<div.+>)(.+)(\<a.+\<a.+)\<\/div\>/is',
188
- '$1 $2 ' . sprintf(
189
- $this->_fs->get_text_inline( '%sRenew your license now%s to access version %s security & feature updates, and support.', 'renew-license-now' ),
190
- '<a href="' . $this->_fs->pricing_url() . '">', '</a>',
191
- $r->new_version ) .
192
- '$4',
193
- $plugin_update_row
194
- );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
195
 
196
  echo $plugin_update_row;
197
  }
@@ -220,10 +336,7 @@
220
 
221
  $prepared_themes[ $theme_basename ]['update'] = preg_replace(
222
  '/(\<p.+>)(.+)(\<a.+\<a.+)\.(.+\<\/p\>)/is',
223
- '$1 $2 ' . sprintf(
224
- $this->_fs->get_text_inline( '%sRenew your license now%s to access version %s security & feature updates, and support.', 'renew-license-now' ),
225
- '<a href="' . $this->_fs->pricing_url() . '">', '</a>',
226
- $themes_update->response[ $theme_basename ]['new_version'] ) .
227
  '$4',
228
  $prepared_themes[ $theme_basename ]['update']
229
  );
@@ -303,7 +416,8 @@
303
  $new_version = $this->_fs->get_update(
304
  false,
305
  fs_request_get_bool( 'force-check' ),
306
- WP_FS__TIME_24_HOURS_IN_SEC / 24
 
307
  );
308
 
309
  $this->_update_details = false;
@@ -401,6 +515,18 @@
401
  );
402
  }
403
 
 
 
 
 
 
 
 
 
 
 
 
 
404
  $update->{$this->_fs->get_module_type()} = $this->_fs->get_plugin_basename();
405
 
406
  return $update;
@@ -573,7 +699,7 @@
573
 
574
  $plugin_basename = $this->_fs->get_plugin_basename();
575
  if ( 'themes' === $module_type ) {
576
- $plugin_basename = str_replace( '-premium', '', $plugin_basename );
577
  }
578
 
579
  global $wp_version;
@@ -585,7 +711,7 @@
585
  array(
586
  "{$module_type}" => array(
587
  $plugin_basename => array(
588
- 'Name' => trim( str_replace( '(Premium)', '', $plugin_data['Name'] ) ),
589
  'Author' => $plugin_data['Author'],
590
  )
591
  )
@@ -748,11 +874,13 @@ if ( !isset($info->error) ) {
748
  }*/
749
  }
750
 
 
 
751
  // Get plugin's newest update.
752
- $new_version = $this->get_latest_download_details( $is_addon ? $addon->id : false );
753
 
754
  if ( ! is_object( $new_version ) || empty( $new_version->version ) ) {
755
- $data->version = $this->_fs->get_plugin_version();
756
  } else {
757
  if ( $is_addon ) {
758
  $data->name = $addon->title . ' ' . $this->_fs->get_text_inline( 'Add-On', 'addon' );
@@ -769,6 +897,52 @@ if ( !isset($info->error) ) {
769
 
770
  $data->version = $new_version->version;
771
  $data->download_link = $new_version->url;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
772
  }
773
 
774
  return $data;
@@ -779,11 +953,13 @@ if ( !isset($info->error) ) {
779
  * @since 1.2.1.7
780
  *
781
  * @param number|bool $addon_id
 
 
782
  *
783
  * @return object
784
  */
785
- private function get_latest_download_details( $addon_id = false ) {
786
- return $this->_fs->_fetch_latest_version( $addon_id );
787
  }
788
 
789
  /**
@@ -793,16 +969,10 @@ if ( !isset($info->error) ) {
793
  * @author Vova Feldman (@svovaf)
794
  * @since 1.2.1.6
795
  *
796
- * @param string $basename Current plugin's basename.
797
- *
798
  * @return bool
799
  */
800
- private function is_correct_folder_name( $basename = '' ) {
801
- if ( empty( $basename ) ) {
802
- $basename = $this->_fs->get_plugin_basename();
803
- }
804
-
805
- return ( $this->_fs->get_target_folder_name() != trim( dirname( $basename ), '/\\' ) );
806
  }
807
 
808
  /**
@@ -838,7 +1008,7 @@ if ( !isset($info->error) ) {
838
  $filename = basename( $basename );
839
 
840
  $new_basename = plugin_basename(
841
- trailingslashit( $this->_fs->get_slug() . ( $this->_fs->is_premium() ? '-premium' : '' ) ) .
842
  $filename
843
  );
844
 
@@ -906,14 +1076,16 @@ if ( !isset($info->error) ) {
906
  );
907
  }
908
 
909
- $slug = $addon->slug;
910
- $title = $addon->title . ' ' . $this->_fs->get_text_inline( 'Add-On', 'addon' );
 
911
 
912
  $is_addon = true;
913
  } else {
914
- $slug = $this->_fs->get_slug();
915
- $title = $this->_fs->get_plugin_title() .
916
- ( $this->_fs->is_addon() ? ' ' . $this->_fs->get_text_inline( 'Add-On', 'addon' ) : '' );
 
917
  }
918
 
919
  if ( $this->is_premium_plugin_active( $plugin_id ) ) {
@@ -926,8 +1098,8 @@ if ( !isset($info->error) ) {
926
  );
927
  }
928
 
929
- $latest_version = $this->get_latest_download_details( $plugin_id );
930
- $target_folder = "{$slug}-premium";
931
 
932
  // Prep variables for Plugin_Installer_Skin class.
933
  $extra = array();
@@ -966,11 +1138,11 @@ if ( !isset($info->error) ) {
966
  $upgrader = new Plugin_Upgrader( $skin );
967
 
968
  // Perform the action and install the plugin from the $source urldecode().
969
- add_filter( 'upgrader_source_selection', array( &$this, '_maybe_adjust_source_dir' ), 1, 3 );
970
 
971
  $install_result = $upgrader->install( $source );
972
 
973
- remove_filter( 'upgrader_source_selection', array( &$this, '_maybe_adjust_source_dir' ), 1 );
974
 
975
  if ( is_wp_error( $install_result ) ) {
976
  return array(
@@ -1060,6 +1232,29 @@ if ( !isset($info->error) ) {
1060
  return is_plugin_active( $this->_fs->premium_plugin_basename() );
1061
  }
1062
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1063
  /**
1064
  * Adjust the plugin directory name if necessary.
1065
  * Assumes plugin has a folder (not a single file plugin).
@@ -1071,6 +1266,7 @@ if ( !isset($info->error) ) {
1071
  *
1072
  * @author Vova Feldman
1073
  * @since 1.2.1.7
 
1074
  *
1075
  * @param string $source Path to upgrade/zip-file-name.tmp/subdirectory/.
1076
  * @param string $remote_source Path to upgrade/zip-file-name.tmp.
@@ -1078,13 +1274,64 @@ if ( !isset($info->error) ) {
1078
  *
1079
  * @return string|WP_Error
1080
  */
1081
- function _maybe_adjust_source_dir( $source, $remote_source, $upgrader ) {
1082
  if ( ! is_object( $GLOBALS['wp_filesystem'] ) ) {
1083
  return $source;
1084
  }
1085
 
 
 
 
1086
  // Figure out what the slug is supposed to be.
1087
- $desired_slug = $upgrader->skin->options['extra']['slug'];
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1088
 
1089
  $subdir_name = untrailingslashit( str_replace( trailingslashit( $remote_source ), '', $source ) );
1090
 
@@ -1094,19 +1341,20 @@ if ( !isset($info->error) ) {
1094
 
1095
  if ( true === $GLOBALS['wp_filesystem']->move( $from_path, $to_path ) ) {
1096
  return trailingslashit( $to_path );
1097
- } else {
1098
- return new WP_Error(
1099
- 'rename_failed',
1100
- $this->_fs->get_text_inline( 'The remote plugin package does not contain a folder with the desired slug and renaming did not work.', 'module-package-rename-failure' ),
1101
- array(
1102
- 'found' => $subdir_name,
1103
- 'expected' => $desired_slug
1104
- ) );
1105
  }
 
 
 
 
 
 
 
 
 
1106
  }
1107
 
1108
  return $source;
1109
  }
1110
 
1111
  #endregion
1112
- }
35
  */
36
  private $_translation_updates;
37
 
38
+ private static $_upgrade_basename = null;
39
+
40
  #--------------------------------------------------------------------------------
41
  #region Singleton
42
  #--------------------------------------------------------------------------------
84
 
85
  $this->add_transient_filters();
86
 
87
+ /**
88
+ * If user has the premium plugin's code but do NOT have an active license,
89
+ * encourage him to upgrade by showing that there's a new release, but instead
90
+ * of showing an update link, show upgrade link to the pricing page.
91
+ *
92
+ * @since 1.1.6
93
+ *
94
+ */
95
+ // WP 2.9+
96
+ add_action( "after_plugin_row_{$this->_fs->get_plugin_basename()}", array(
97
+ &$this,
98
+ 'catch_plugin_update_row'
99
+ ), 9 );
100
+ add_action( "after_plugin_row_{$this->_fs->get_plugin_basename()}", array(
101
+ &$this,
102
+ 'edit_and_echo_plugin_update_row'
103
+ ), 11, 2 );
104
+
105
+ add_action( 'admin_head', array( &$this, 'catch_plugin_information_dialog_contents' ) );
106
 
107
  if ( ! WP_FS__IS_PRODUCTION_MODE ) {
108
  add_filter( 'http_request_host_is_external', array(
112
  }
113
 
114
  if ( $this->_fs->is_premium() ) {
115
+ if ( ! $this->is_correct_folder_name() ) {
116
  add_filter( 'upgrader_post_install', array( &$this, '_maybe_update_folder_name' ), 10, 3 );
117
  }
118
 
119
+ add_filter( 'upgrader_pre_install', array( 'FS_Plugin_Updater', '_store_basename_for_source_adjustment' ), 1, 2 );
120
+ add_filter( 'upgrader_source_selection', array( 'FS_Plugin_Updater', '_maybe_adjust_source_dir' ), 1, 3 );
121
+
122
+ if ( ! $this->_fs->has_any_active_valid_license() ) {
123
  add_filter( 'wp_prepare_themes_for_js', array( &$this, 'change_theme_update_info_html' ), 10, 1 );
124
  }
125
  }
126
  }
127
 
128
+ /**
129
+ * @author Leo Fajardo (@leorw)
130
+ * @since 2.1.4
131
+ */
132
+ function catch_plugin_information_dialog_contents() {
133
+ if (
134
+ 'plugin-information' !== fs_request_get( 'tab', false ) ||
135
+ $this->_fs->get_slug() !== fs_request_get( 'plugin', false )
136
+ ) {
137
+ return;
138
+ }
139
+
140
+ add_action( 'admin_footer', array( &$this, 'edit_and_echo_plugin_information_dialog_contents' ), 0, 1 );
141
+
142
+ ob_start();
143
+ }
144
+
145
+ /**
146
+ * @author Leo Fajardo (@leorw)
147
+ * @since 2.1.4
148
+ *
149
+ * @param string $hook_suffix
150
+ */
151
+ function edit_and_echo_plugin_information_dialog_contents( $hook_suffix ) {
152
+ if (
153
+ 'plugin-information' !== fs_request_get( 'tab', false ) ||
154
+ $this->_fs->get_slug() !== fs_request_get( 'plugin', false )
155
+ ) {
156
+ return;
157
+ }
158
+
159
+ $license = $this->_fs->_get_license();
160
+
161
+ $subscription = ( is_object( $license ) && ! $license->is_lifetime() ) ?
162
+ $this->_fs->_get_subscription( $license->id ) :
163
+ null;
164
+
165
+ $contents = ob_get_clean();
166
+
167
+ /**
168
+ * Replace the plugin information dialog's "Install Update Now" button's text and URL. If there's a license,
169
+ * the text will be "Renew license" and will link to the checkout page with the license's billing cycle
170
+ * and quota. If there's no license, the text will be "Buy license" and will link to the pricing page.
171
+ */
172
+ $contents = preg_replace(
173
+ '/(.+\<a.+)(id="plugin_update_from_iframe")(.+href=")([^\s]+)(".+\>)(.+)(\<\/a.+)/is',
174
+ is_object( $license ) ?
175
+ sprintf(
176
+ '$1$3%s$5%s$7',
177
+ $this->_fs->checkout_url(
178
+ is_object( $subscription ) ?
179
+ ( 1 == $subscription->billing_cycle ? WP_FS__PERIOD_MONTHLY : WP_FS__PERIOD_ANNUALLY ) :
180
+ WP_FS__PERIOD_LIFETIME,
181
+ false,
182
+ array( 'licenses' => $license->quota )
183
+ ),
184
+ fs_text_inline( 'Renew license', 'renew-license', $this->_fs->get_slug() )
185
+ ) :
186
+ sprintf(
187
+ '$1$3%s$5%s$7',
188
+ $this->_fs->pricing_url(),
189
+ fs_text_inline( 'Buy license', 'buy-license', $this->_fs->get_slug() )
190
+ ),
191
+ $contents
192
+ );
193
+
194
+ echo $contents;
195
+ }
196
+
197
  /**
198
  * @author Vova Feldman (@svovaf)
199
  * @since 2.0.0
257
 
258
  $r = $current->response[ $file ];
259
 
260
+ if ( ! $this->_fs->has_any_active_valid_license() ) {
261
+ /**
262
+ * Turn the "new version" text into a link that opens the plugin information dialog when clicked and
263
+ * make the "View version x details" text link to the checkout page instead of opening the plugin
264
+ * information dialog when clicked.
265
+ *
266
+ * Sample input:
267
+ * There is a new version of Awesome Plugin available. <a href="...>View version x.y.z details</a> or <a href="...>update now</a>.
268
+ * Output:
269
+ * There is a <a href="...>new version</a> of Awesome Plugin available. <a href="...>Buy a license now</a> to access version x.y.z security & feature updates, and support.
270
+ *
271
+ * @author Leo Fajardo (@leorw)
272
+ */
273
+ $plugin_update_row = preg_replace(
274
+ '/(\<div.+>)(.+)(\<a.+href="([^\s]+)"([^\<]+)\>.+\<a.+)(\<\/div\>)/is',
275
+ (
276
+ '$1' .
277
+ sprintf(
278
+ fs_text_inline( 'There is a %s of %s available.', 'new-version-available', $this->_fs->get_slug() ),
279
+ sprintf(
280
+ '<a href="$4"%s>%s</a>',
281
+ '$5',
282
+ fs_text_inline( 'new version', 'new-version', $this->_fs->get_slug() )
283
+ ),
284
+ $this->_fs->get_plugin_title()
285
+ ) .
286
+ ' ' .
287
+ $this->_fs->version_upgrade_checkout_link( $r->new_version ) .
288
+ '$6'
289
+ ),
290
+ $plugin_update_row
291
+ );
292
+ }
293
+
294
+ if (
295
+ $this->_fs->is_plugin() &&
296
+ isset( $r->upgrade_notice ) &&
297
+ strlen( trim( $r->upgrade_notice ) ) > 0
298
+ ) {
299
+ $slug = $this->_fs->get_slug();
300
+
301
+ $upgrade_notice_html = sprintf(
302
+ '<p class="notice fs-upgrade-notice fs-slug-%1s fs-type-%2s" data-slug="%1s" data-type="%2s"><strong>%3s</strong> %4s</p>',
303
+ $slug,
304
+ $this->_fs->get_module_type(),
305
+ fs_text_inline( 'Important Upgrade Notice:', 'upgrade_notice', $slug ),
306
+ esc_html( $r->upgrade_notice )
307
+ );
308
+
309
+ $plugin_update_row = str_replace( '</div>', '</div>' . $upgrade_notice_html, $plugin_update_row );
310
+ }
311
 
312
  echo $plugin_update_row;
313
  }
336
 
337
  $prepared_themes[ $theme_basename ]['update'] = preg_replace(
338
  '/(\<p.+>)(.+)(\<a.+\<a.+)\.(.+\<\/p\>)/is',
339
+ '$1 $2 ' . $this->_fs->version_upgrade_checkout_link( $themes_update->response[ $theme_basename ]['new_version'] ) .
 
 
 
340
  '$4',
341
  $prepared_themes[ $theme_basename ]['update']
342
  );
416
  $new_version = $this->_fs->get_update(
417
  false,
418
  fs_request_get_bool( 'force-check' ),
419
+ WP_FS__TIME_24_HOURS_IN_SEC / 24,
420
+ $this->_fs->get_plugin_version()
421
  );
422
 
423
  $this->_update_details = false;
515
  );
516
  }
517
 
518
+ if ( $this->_fs->is_premium() ) {
519
+ $latest_tag = $this->_fs->_fetch_latest_version( $this->_fs->get_id(), false );
520
+
521
+ if (
522
+ isset( $latest_tag->readme ) &&
523
+ isset( $latest_tag->readme->upgrade_notice ) &&
524
+ ! empty( $latest_tag->readme->upgrade_notice )
525
+ ) {
526
+ $update->upgrade_notice = $latest_tag->readme->upgrade_notice;
527
+ }
528
+ }
529
+
530
  $update->{$this->_fs->get_module_type()} = $this->_fs->get_plugin_basename();
531
 
532
  return $update;
699
 
700
  $plugin_basename = $this->_fs->get_plugin_basename();
701
  if ( 'themes' === $module_type ) {
702
+ $plugin_basename = $slug;
703
  }
704
 
705
  global $wp_version;
711
  array(
712
  "{$module_type}" => array(
713
  $plugin_basename => array(
714
+ 'Name' => trim( str_replace( $this->_fs->get_plugin()->premium_suffix, '', $plugin_data['Name'] ) ),
715
  'Author' => $plugin_data['Author'],
716
  )
717
  )
874
  }*/
875
  }
876
 
877
+ $plugin_version = $this->_fs->get_plugin_version();
878
+
879
  // Get plugin's newest update.
880
+ $new_version = $this->get_latest_download_details( $is_addon ? $addon->id : false, $plugin_version );
881
 
882
  if ( ! is_object( $new_version ) || empty( $new_version->version ) ) {
883
+ $data->version = $plugin_version;
884
  } else {
885
  if ( $is_addon ) {
886
  $data->name = $addon->title . ' ' . $this->_fs->get_text_inline( 'Add-On', 'addon' );
897
 
898
  $data->version = $new_version->version;
899
  $data->download_link = $new_version->url;
900
+
901
+ if ( isset( $new_version->readme ) && is_object( $new_version->readme ) ) {
902
+ $new_version_readme_data = $new_version->readme;
903
+ if ( isset( $new_version_readme_data->sections ) ) {
904
+ $new_version_readme_data->sections = (array) $new_version_readme_data->sections;
905
+ } else {
906
+ $new_version_readme_data->sections = array();
907
+ }
908
+
909
+ if ( isset( $data->sections ) ) {
910
+ if ( isset( $data->sections['screenshots'] ) ) {
911
+ $new_version_readme_data->sections['screenshots'] = $data->sections['screenshots'];
912
+ }
913
+
914
+ if ( isset( $data->sections['reviews'] ) ) {
915
+ $new_version_readme_data->sections['reviews'] = $data->sections['reviews'];
916
+ }
917
+ }
918
+
919
+ if ( isset( $new_version_readme_data->banners ) ) {
920
+ $new_version_readme_data->banners = (array) $new_version_readme_data->banners;
921
+ } else if ( isset( $data->banners ) ) {
922
+ $new_version_readme_data->banners = $data->banners;
923
+ }
924
+
925
+ $wp_org_sections = array(
926
+ 'author',
927
+ 'author_profile',
928
+ 'rating',
929
+ 'ratings',
930
+ 'num_ratings',
931
+ 'support_threads',
932
+ 'support_threads_resolved',
933
+ 'active_installs',
934
+ 'added',
935
+ 'homepage'
936
+ );
937
+
938
+ foreach ( $wp_org_sections as $wp_org_section ) {
939
+ if ( isset( $data->{$wp_org_section} ) ) {
940
+ $new_version_readme_data->{$wp_org_section} = $data->{$wp_org_section};
941
+ }
942
+ }
943
+
944
+ $data = $new_version_readme_data;
945
+ }
946
  }
947
 
948
  return $data;
953
  * @since 1.2.1.7
954
  *
955
  * @param number|bool $addon_id
956
+ * @param bool|string $newer_than Since 2.2.1
957
+ * @param bool|string $fetch_readme Since 2.2.1
958
  *
959
  * @return object
960
  */
961
+ private function get_latest_download_details( $addon_id = false, $newer_than = false, $fetch_readme = true ) {
962
+ return $this->_fs->_fetch_latest_version( $addon_id, true, WP_FS__TIME_24_HOURS_IN_SEC, $newer_than, $fetch_readme );
963
  }
964
 
965
  /**
969
  * @author Vova Feldman (@svovaf)
970
  * @since 1.2.1.6
971
  *
 
 
972
  * @return bool
973
  */
974
+ private function is_correct_folder_name() {
975
+ return ( $this->_fs->get_target_folder_name() == trim( dirname( $this->_fs->get_plugin_basename() ), '/\\' ) );
 
 
 
 
976
  }
977
 
978
  /**
1008
  $filename = basename( $basename );
1009
 
1010
  $new_basename = plugin_basename(
1011
+ trailingslashit( $this->_fs->is_premium() ? $this->_fs->get_premium_slug() : $this->_fs->get_slug() ) .
1012
  $filename
1013
  );
1014
 
1076
  );
1077
  }
1078
 
1079
+ $slug = $addon->slug;
1080
+ $premium_slug = $addon->premium_slug;
1081
+ $title = $addon->title . ' ' . $this->_fs->get_text_inline( 'Add-On', 'addon' );
1082
 
1083
  $is_addon = true;
1084
  } else {
1085
+ $slug = $this->_fs->get_slug();
1086
+ $premium_slug = $this->_fs->get_premium_slug();
1087
+ $title = $this->_fs->get_plugin_title() .
1088
+ ( $this->_fs->is_addon() ? ' ' . $this->_fs->get_text_inline( 'Add-On', 'addon' ) : '' );
1089
  }
1090
 
1091
  if ( $this->is_premium_plugin_active( $plugin_id ) ) {
1098
  );
1099
  }
1100
 
1101
+ $latest_version = $this->get_latest_download_details( $plugin_id, false, false );
1102
+ $target_folder = $premium_slug;
1103
 
1104
  // Prep variables for Plugin_Installer_Skin class.
1105
  $extra = array();
1138
  $upgrader = new Plugin_Upgrader( $skin );
1139
 
1140
  // Perform the action and install the plugin from the $source urldecode().
1141
+ add_filter( 'upgrader_source_selection', array( 'FS_Plugin_Updater', '_maybe_adjust_source_dir' ), 1, 3 );
1142
 
1143
  $install_result = $upgrader->install( $source );
1144
 
1145
+ remove_filter( 'upgrader_source_selection', array( 'FS_Plugin_Updater', '_maybe_adjust_source_dir' ), 1 );
1146
 
1147
  if ( is_wp_error( $install_result ) ) {
1148
  return array(
1232
  return is_plugin_active( $this->_fs->premium_plugin_basename() );
1233
  }
1234
 
1235
+ /**
1236
+ * Store the basename since it's not always available in the `_maybe_adjust_source_dir` method below.
1237
+ *
1238
+ * @author Leo Fajardo (@leorw)
1239
+ * @since 2.2.1
1240
+ *
1241
+ * @param bool|WP_Error $response Response.
1242
+ * @param array $hook_extra Extra arguments passed to hooked filters.
1243
+ *
1244
+ * @return bool|WP_Error
1245
+ */
1246
+ static function _store_basename_for_source_adjustment( $response, $hook_extra ) {
1247
+ if ( isset( $hook_extra['plugin'] ) ) {
1248
+ self::$_upgrade_basename = $hook_extra['plugin'];
1249
+ } else if ( isset( $hook_extra['theme'] ) ) {
1250
+ self::$_upgrade_basename = $hook_extra['theme'];
1251
+ } else {
1252
+ self::$_upgrade_basename = null;
1253
+ }
1254
+
1255
+ return $response;
1256
+ }
1257
+
1258
  /**
1259
  * Adjust the plugin directory name if necessary.
1260
  * Assumes plugin has a folder (not a single file plugin).
1266
  *
1267
  * @author Vova Feldman
1268
  * @since 1.2.1.7
1269
+ * @since 2.2.1 The method was converted to static since when the admin update bulk products via the Updates section, the logic applies the `upgrader_source_selection` filter for every product that is being updated.
1270
  *
1271
  * @param string $source Path to upgrade/zip-file-name.tmp/subdirectory/.
1272
  * @param string $remote_source Path to upgrade/zip-file-name.tmp.
1274
  *
1275
  * @return string|WP_Error
1276
  */
1277
+ static function _maybe_adjust_source_dir( $source, $remote_source, $upgrader ) {
1278
  if ( ! is_object( $GLOBALS['wp_filesystem'] ) ) {
1279
  return $source;
1280
  }
1281
 
1282
+ $basename = self::$_upgrade_basename;
1283
+ $is_theme = false;
1284
+
1285
  // Figure out what the slug is supposed to be.
1286
+ if ( isset( $upgrader->skin->options['extra'] ) ) {
1287
+ // Set by the auto-install logic.
1288
+ $desired_slug = $upgrader->skin->options['extra']['slug'];
1289
+ } else if ( ! empty( $basename ) ) {
1290
+ /**
1291
+ * If it doesn't end with ".php", it's a theme.
1292
+ *
1293
+ * @author Leo Fajardo (@leorw)
1294
+ * @since 2.2.1
1295
+ */
1296
+ $is_theme = ( ! fs_ends_with( $basename, '.php' ) );
1297
+
1298
+ $desired_slug = ( ! $is_theme ) ?
1299
+ dirname( $basename ) :
1300
+ // Theme slug
1301
+ $basename;
1302
+ } else {
1303
+ // Can't figure out the desired slug, stop the execution.
1304
+ return $source;
1305
+ }
1306
+
1307
+ if ( is_multisite() ) {
1308
+ /**
1309
+ * If we are running in a multisite environment and the product is not network activated,
1310
+ * the instance will not exist anyway. Therefore, try to update the source if necessary
1311
+ * regardless if the Freemius instance of the product exists or not.
1312
+ *
1313
+ * @author Vova Feldman
1314
+ */
1315
+ } else if ( ! empty( $basename ) ) {
1316
+ $fs = Freemius::get_instance_by_file(
1317
+ $basename,
1318
+ $is_theme ?
1319
+ WP_FS__MODULE_TYPE_THEME :
1320
+ WP_FS__MODULE_TYPE_PLUGIN
1321
+ );
1322
+
1323
+ if ( ! is_object( $fs ) ) {
1324
+ /**
1325
+ * If the Freemius instance does not exist on a non-multisite network environment, it means that:
1326
+ * 1. The product is not powered by Freemius; OR
1327
+ * 2. The product is not activated, therefore, we don't mind if after the update the folder name will change.
1328
+ *
1329
+ * @author Leo Fajardo (@leorw)
1330
+ * @since 2.2.1
1331
+ */
1332
+ return $source;
1333
+ }
1334
+ }
1335
 
1336
  $subdir_name = untrailingslashit( str_replace( trailingslashit( $remote_source ), '', $source ) );
1337
 
1341
 
1342
  if ( true === $GLOBALS['wp_filesystem']->move( $from_path, $to_path ) ) {
1343
  return trailingslashit( $to_path );
 
 
 
 
 
 
 
 
1344
  }
1345
+
1346
+ return new WP_Error(
1347
+ 'rename_failed',
1348
+ fs_text_inline( 'The remote plugin package does not contain a folder with the desired slug and renaming did not work.', 'module-package-rename-failure' ),
1349
+ array(
1350
+ 'found' => $subdir_name,
1351
+ 'expected' => $desired_slug
1352
+ )
1353
+ );
1354
  }
1355
 
1356
  return $source;
1357
  }
1358
 
1359
  #endregion
1360
+ }
vendor/freemius/includes/class-fs-storage.php CHANGED
@@ -132,9 +132,8 @@
132
  * @param int $blog_id
133
  */
134
  function set_site_blog_context( $blog_id ) {
 
135
  $this->_blog_id = $blog_id;
136
-
137
- $this->_storage = $this->get_site_storage( $this->_blog_id );
138
  }
139
 
140
  /**
@@ -374,6 +373,7 @@
374
  // When network activated, then network level.
375
  'install_timestamp' => 1,
376
  'prev_is_premium' => 1,
 
377
 
378
  // If not network activated OR delegated, then site level.
379
  'activation_timestamp' => 2,
132
  * @param int $blog_id
133
  */
134
  function set_site_blog_context( $blog_id ) {
135
+ $this->_storage = $this->get_site_storage( $blog_id );
136
  $this->_blog_id = $blog_id;
 
 
137
  }
138
 
139
  /**
373
  // When network activated, then network level.
374
  'install_timestamp' => 1,
375
  'prev_is_premium' => 1,
376
+ 'require_license_activation' => 1,
377
 
378
  // If not network activated OR delegated, then site level.
379
  'activation_timestamp' => 2,
vendor/freemius/includes/entities/class-fs-plugin.php CHANGED
@@ -24,6 +24,13 @@
24
  * @var string
25
  */
26
  public $slug;
 
 
 
 
 
 
 
27
  /**
28
  * @since 1.2.2
29
  *
@@ -67,6 +74,13 @@
67
  * @var bool
68
  */
69
  public $is_premium;
 
 
 
 
 
 
 
70
  /**
71
  * @since 1.0.9
72
  *
@@ -87,6 +101,14 @@
87
  $this->is_premium = false;
88
  $this->is_live = true;
89
 
 
 
 
 
 
 
 
 
90
  if ( isset( $plugin->info ) && is_object( $plugin->info ) ) {
91
  $this->info = new FS_Plugin_Info( $plugin->info );
92
  }
24
  * @var string
25
  */
26
  public $slug;
27
+ /**
28
+ * @author Leo Fajardo (@leorw)
29
+ * @since 2.2.1
30
+ *
31
+ * @var string
32
+ */
33
+ public $premium_slug;
34
  /**
35
  * @since 1.2.2
36
  *
74
  * @var bool
75
  */
76
  public $is_premium;
77
+ /**
78
+ * @author Leo Fajardo (@leorw)
79
+ * @since 2.2.1
80
+ *
81
+ * @var string
82
+ */
83
+ public $premium_suffix;
84
  /**
85
  * @since 1.0.9
86
  *
101
  $this->is_premium = false;
102
  $this->is_live = true;
103
 
104
+ if ( empty( $this->premium_slug ) && ! empty( $plugin->slug ) ) {
105
+ $this->premium_slug = "{$this->slug}-premium";
106
+ }
107
+
108
+ if ( empty( $this->premium_suffix ) ) {
109
+ $this->premium_suffix = '(Premium)';
110
+ }
111
+
112
  if ( isset( $plugin->info ) && is_object( $plugin->info ) ) {
113
  $this->info = new FS_Plugin_Info( $plugin->info );
114
  }
vendor/freemius/includes/entities/class-fs-site.php CHANGED
@@ -150,6 +150,7 @@
150
  fs_starts_with( $subdomain, 'local.' ) ||
151
  fs_starts_with( $subdomain, 'dev.' ) ||
152
  fs_starts_with( $subdomain, 'test.' ) ||
 
153
  fs_starts_with( $subdomain, 'staging.' ) ||
154
 
155
  // Ends with.
@@ -163,6 +164,8 @@
163
  fs_ends_with( $subdomain, '.myftpupload.com' ) ||
164
  // ngrok tunneling.
165
  fs_ends_with( $subdomain, '.ngrok.io' ) ||
 
 
166
  // SiteGround staging.
167
  fs_starts_with( $subdomain, 'staging' ) ||
168
  // WPEngine staging.
@@ -171,7 +174,9 @@
171
  ( fs_ends_with($subdomain, 'pantheonsite.io') &&
172
  (fs_starts_with($subdomain, 'test-') || fs_starts_with($subdomain, 'dev-'))) ||
173
  // Cloudways
174
- fs_ends_with( $subdomain, '.cloudwaysapps.com' )
 
 
175
  );
176
  }
177
 
150
  fs_starts_with( $subdomain, 'local.' ) ||
151
  fs_starts_with( $subdomain, 'dev.' ) ||
152
  fs_starts_with( $subdomain, 'test.' ) ||
153
+ fs_starts_with( $subdomain, 'stage.' ) ||
154
  fs_starts_with( $subdomain, 'staging.' ) ||
155
 
156
  // Ends with.
164
  fs_ends_with( $subdomain, '.myftpupload.com' ) ||
165
  // ngrok tunneling.
166
  fs_ends_with( $subdomain, '.ngrok.io' ) ||
167
+ // wpsandbox.
168
+ fs_ends_with( $subdomain, '.wpsandbox.pro' ) ||
169
  // SiteGround staging.
170
  fs_starts_with( $subdomain, 'staging' ) ||
171
  // WPEngine staging.
174
  ( fs_ends_with($subdomain, 'pantheonsite.io') &&
175
  (fs_starts_with($subdomain, 'test-') || fs_starts_with($subdomain, 'dev-'))) ||
176
  // Cloudways
177
+ fs_ends_with( $subdomain, '.cloudwaysapps.com' ) ||
178
+ // Kinsta
179
+ (fs_ends_with($subdomain, '.kinsta.com') && fs_starts_with($subdomain, 'staging-'))
180
  );
181
  }
182
 
vendor/freemius/includes/fs-core-functions.php CHANGED
@@ -86,9 +86,25 @@
86
  function fs_asset_url( $asset_abs_path ) {
87
  $wp_content_dir = fs_normalize_path( WP_CONTENT_DIR );
88
  $asset_abs_path = fs_normalize_path( $asset_abs_path );
89
- $asset_rel_path = str_replace( $wp_content_dir, '', $asset_abs_path );
90
 
91
- $asset_url = content_url( fs_normalize_path( $asset_rel_path ) );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
92
 
93
  return $asset_url;
94
  }
@@ -709,6 +725,97 @@
709
  return $key;
710
  }
711
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
712
  /**
713
  * Get a translatable text override if exists, or `false`.
714
  *
@@ -746,7 +853,9 @@
746
 
747
  return false;
748
  }
 
749
 
 
750
  /**
751
  * Get a translatable text and its text domain.
752
  *
@@ -776,9 +885,9 @@
776
 
777
  return array( $text, $text_domain );
778
  }
 
779
 
780
- #region Private
781
-
782
  /**
783
  * Retrieve an inline translated text by key.
784
  *
@@ -801,33 +910,9 @@
801
 
802
  return $fn( $text, $text_domain );
803
  }
 
804
 
805
- /**
806
- * Retrieve an inline translated text by key with a context.
807
- *
808
- * @author Vova Feldman (@svovaf)
809
- * @since 1.2.3
810
- *
811
- * @param string $text Translatable string.
812
- * @param string $context Context information for the translators.
813
- * @param string $key String key for overrides.
814
- * @param string $slug Module slug for overrides.
815
- *
816
- * @return string
817
- *
818
- * @global $fs_text_overrides
819
- */
820
- function _fs_text_x_inline( $text, $context, $key = '', $slug = 'freemius' ) {
821
- list( $text, $text_domain ) = fs_text_and_domain( $text, $key, $slug );
822
-
823
- // Avoid misleading Theme Check warning.
824
- $fn = 'translate_with_gettext_context';
825
-
826
- return $fn( $text, $context, $text_domain );
827
- }
828
-
829
- #endregion
830
-
831
  /**
832
  * Retrieve an inline translated text by key.
833
  *
@@ -845,67 +930,6 @@
845
  function fs_text_inline( $text, $key = '', $slug = 'freemius' ) {
846
  return _fs_text_inline( $text, $key, $slug );
847
  }
848
-
849
- /**
850
- * Retrieve an inline translated text by key with a context.
851
- *
852
- * @author Vova Feldman (@svovaf)
853
- * @since 1.2.3
854
- *
855
- * @param string $text Translatable string.
856
- * @param string $context Context information for the translators.
857
- * @param string $key String key for overrides.
858
- * @param string $slug Module slug for overrides.
859
- *
860
- * @return string
861
- *
862
- * @global $fs_text_overrides
863
- */
864
- function fs_text_x_inline( $text, $context, $key = '', $slug = 'freemius' ) {
865
- return _fs_text_x_inline( $text, $context, $key, $slug );
866
- }
867
-
868
- /**
869
- * Output a translated text by key.
870
- *
871
- * @author Vova Feldman (@svovaf)
872
- * @since 1.2.1.7
873
- *
874
- * @param string $key
875
- * @param string $slug
876
- */
877
- function fs_echo( $key, $slug = 'freemius' ) {
878
- echo fs_text( $key, $slug );
879
- }
880
-
881
- /**
882
- * Output an inline translated text.
883
- *
884
- * @author Vova Feldman (@svovaf)
885
- * @since 1.2.3
886
- *
887
- * @param string $text Translatable string.
888
- * @param string $key String key for overrides.
889
- * @param string $slug Module slug for overrides.
890
- */
891
- function fs_echo_inline( $text, $key = '', $slug = 'freemius' ) {
892
- echo _fs_text_inline( $text, $key, $slug );
893
- }
894
-
895
- /**
896
- * Output an inline translated text with a context.
897
- *
898
- * @author Vova Feldman (@svovaf)
899
- * @since 1.2.3
900
- *
901
- * @param string $text Translatable string.
902
- * @param string $context Context information for the translators.
903
- * @param string $key String key for overrides.
904
- * @param string $slug Module slug for overrides.
905
- */
906
- function fs_echo_x_inline( $text, $context, $key = '', $slug = 'freemius' ) {
907
- echo _fs_text_x_inline( $text, $context, $key, $slug );
908
- }
909
  }
910
 
911
  if ( ! function_exists( 'fs_esc_attr' ) ) {
86
  function fs_asset_url( $asset_abs_path ) {
87
  $wp_content_dir = fs_normalize_path( WP_CONTENT_DIR );
88
  $asset_abs_path = fs_normalize_path( $asset_abs_path );
 
89
 
90
+ if ( 0 === strpos( $asset_abs_path, $wp_content_dir ) ) {
91
+ // Handle both theme and plugin assets located in the standard directories.
92
+ $asset_rel_path = str_replace( $wp_content_dir, '', $asset_abs_path );
93
+ $asset_url = content_url( fs_normalize_path( $asset_rel_path ) );
94
+ } else {
95
+ $wp_plugins_dir = fs_normalize_path( WP_PLUGIN_DIR );
96
+ if ( 0 === strpos( $asset_abs_path, $wp_plugins_dir ) ) {
97
+ // Try to handle plugin assets that may be located in a non-standard plugins directory.
98
+ $asset_rel_path = str_replace( $wp_plugins_dir, '', $asset_abs_path );
99
+ $asset_url = plugins_url( fs_normalize_path( $asset_rel_path ) );
100
+ } else {
101
+ // Try to handle theme assets that may be located in a non-standard themes directory.
102
+ $active_theme_stylesheet = get_stylesheet();
103
+ $wp_themes_dir = fs_normalize_path( trailingslashit( get_theme_root( $active_theme_stylesheet ) ) );
104
+ $asset_rel_path = str_replace( $wp_themes_dir, '', fs_normalize_path( $asset_abs_path ) );
105
+ $asset_url = trailingslashit( get_theme_root_uri( $active_theme_stylesheet ) ) . fs_normalize_path( $asset_rel_path );
106
+ }
107
+ }
108
 
109
  return $asset_url;
110
  }
725
  return $key;
726
  }
727
 
728
+ #region Private
729
+
730
+ /**
731
+ * Retrieve an inline translated text by key with a context.
732
+ *
733
+ * @author Vova Feldman (@svovaf)
734
+ * @since 1.2.3
735
+ *
736
+ * @param string $text Translatable string.
737
+ * @param string $context Context information for the translators.
738
+ * @param string $key String key for overrides.
739
+ * @param string $slug Module slug for overrides.
740
+ *
741
+ * @return string
742
+ *
743
+ * @global $fs_text_overrides
744
+ */
745
+ function _fs_text_x_inline( $text, $context, $key = '', $slug = 'freemius' ) {
746
+ list( $text, $text_domain ) = fs_text_and_domain( $text, $key, $slug );
747
+
748
+ // Avoid misleading Theme Check warning.
749
+ $fn = 'translate_with_gettext_context';
750
+
751
+ return $fn( $text, $context, $text_domain );
752
+ }
753
+
754
+ #endregion
755
+
756
+ /**
757
+ * Retrieve an inline translated text by key with a context.
758
+ *
759
+ * @author Vova Feldman (@svovaf)
760
+ * @since 1.2.3
761
+ *
762
+ * @param string $text Translatable string.
763
+ * @param string $context Context information for the translators.
764
+ * @param string $key String key for overrides.
765
+ * @param string $slug Module slug for overrides.
766
+ *
767
+ * @return string
768
+ *
769
+ * @global $fs_text_overrides
770
+ */
771
+ function fs_text_x_inline( $text, $context, $key = '', $slug = 'freemius' ) {
772
+ return _fs_text_x_inline( $text, $context, $key, $slug );
773
+ }
774
+
775
+ /**
776
+ * Output a translated text by key.
777
+ *
778
+ * @author Vova Feldman (@svovaf)
779
+ * @since 1.2.1.7
780
+ *
781
+ * @param string $key
782
+ * @param string $slug
783
+ */
784
+ function fs_echo( $key, $slug = 'freemius' ) {
785
+ echo fs_text( $key, $slug );
786
+ }
787
+
788
+ /**
789
+ * Output an inline translated text.
790
+ *
791
+ * @author Vova Feldman (@svovaf)
792
+ * @since 1.2.3
793
+ *
794
+ * @param string $text Translatable string.
795
+ * @param string $key String key for overrides.
796
+ * @param string $slug Module slug for overrides.
797
+ */
798
+ function fs_echo_inline( $text, $key = '', $slug = 'freemius' ) {
799
+ echo _fs_text_inline( $text, $key, $slug );
800
+ }
801
+
802
+ /**
803
+ * Output an inline translated text with a context.
804
+ *
805
+ * @author Vova Feldman (@svovaf)
806
+ * @since 1.2.3
807
+ *
808
+ * @param string $text Translatable string.
809
+ * @param string $context Context information for the translators.
810
+ * @param string $key String key for overrides.
811
+ * @param string $slug Module slug for overrides.
812
+ */
813
+ function fs_echo_x_inline( $text, $context, $key = '', $slug = 'freemius' ) {
814
+ echo _fs_text_x_inline( $text, $context, $key, $slug );
815
+ }
816
+ }
817
+
818
+ if ( ! function_exists( 'fs_text_override' ) ) {
819
  /**
820
  * Get a translatable text override if exists, or `false`.
821
  *
853
 
854
  return false;
855
  }
856
+ }
857
 
858
+ if ( ! function_exists( 'fs_text_and_domain' ) ) {
859
  /**
860
  * Get a translatable text and its text domain.
861
  *
885
 
886
  return array( $text, $text_domain );
887
  }
888
+ }
889
 
890
+ if ( ! function_exists( '_fs_text_inline' ) ) {
 
891
  /**
892
  * Retrieve an inline translated text by key.
893
  *
910
 
911
  return $fn( $text, $text_domain );
912
  }
913
+ }
914
 
915
+ if ( ! function_exists( 'fs_text_inline' ) ) {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
916
  /**
917
  * Retrieve an inline translated text by key.
918
  *
930
  function fs_text_inline( $text, $key = '', $slug = 'freemius' ) {
931
  return _fs_text_inline( $text, $key, $slug );
932
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
933
  }
934
 
935
  if ( ! function_exists( 'fs_esc_attr' ) ) {
vendor/freemius/includes/fs-essential-functions.php CHANGED
@@ -36,6 +36,8 @@
36
  }
37
  }
38
 
 
 
39
  #region Core Redirect (copied from BuddyPress) -----------------------------------------
40
 
41
  if ( ! function_exists( 'fs_redirect' ) ) {
@@ -273,11 +275,11 @@
273
  require_once ABSPATH . 'wp-admin/includes/plugin.php';
274
  }
275
 
276
- $all_plugins = get_plugins();
277
  $all_plugins_paths = array();
278
 
279
  // Get active plugin's main files real full names (might be symlinks).
280
- foreach ( $all_plugins as $relative_path => &$data ) {
281
  $all_plugins_paths[] = fs_normalize_path( realpath( WP_PLUGIN_DIR . '/' . $relative_path ) );
282
  }
283
 
36
  }
37
  }
38
 
39
+ require_once dirname( __FILE__ ) . '/supplements/fs-essential-functions-2.2.1.php';
40
+
41
  #region Core Redirect (copied from BuddyPress) -----------------------------------------
42
 
43
  if ( ! function_exists( 'fs_redirect' ) ) {
275
  require_once ABSPATH . 'wp-admin/includes/plugin.php';
276
  }
277
 
278
+ $all_plugins = fs_get_plugins( true );
279
  $all_plugins_paths = array();
280
 
281
  // Get active plugin's main files real full names (might be symlinks).
282
+ foreach ( $all_plugins as $relative_path => $data ) {
283
  $all_plugins_paths[] = fs_normalize_path( realpath( WP_PLUGIN_DIR . '/' . $relative_path ) );
284
  }
285
 
vendor/freemius/includes/fs-plugin-info-dialog.php CHANGED
@@ -64,7 +64,7 @@
64
  function _get_addon_info_filter( $data, $action = '', $args = null ) {
65
  $this->_logger->entrance();
66
 
67
- $parent_plugin_id = fs_request_get( 'parent_plugin_id', false );
68
 
69
  if ( $this->_fs->get_id() != $parent_plugin_id ||
70
  ( 'plugin_information' !== $action ) ||
@@ -142,6 +142,8 @@
142
  }
143
  }
144
 
 
 
145
  if ( ! $has_paid_plan && $selected_addon->is_wp_org_compliant ) {
146
  $repo_data = FS_Plugin_Updater::_fetch_plugin_info_from_repository(
147
  'plugin_information', (object) array(
@@ -170,8 +172,28 @@
170
  } else {
171
  $data->wp_org_missing = false;
172
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
173
  // Fetch latest version from Freemius.
174
- $latest = $this->_fs->_fetch_latest_version( $selected_addon->id );
 
 
 
 
 
175
 
176
  if ( $has_paid_plan ) {
177
  $data->checkout_link = $this->_fs->checkout_url();
@@ -203,7 +225,7 @@
203
 
204
  if ( is_object( $latest ) ) {
205
  $data->version = $latest->version;
206
- $data->last_updated = ! is_null( $latest->updated ) ? $latest->updated : $latest->created;
207
  $data->requires = $latest->requires_platform_version;
208
  $data->tested = $latest->tested_up_to_version;
209
  } else {
@@ -214,11 +236,19 @@
214
  }
215
  }
216
 
217
- $data->name = $selected_addon->title;
218
- $view_vars = array( 'plugin' => $selected_addon );
219
- $data->sections = array(
220
- 'description' => fs_get_template( '/plugin-info/description.php', $view_vars ),
221
- );
 
 
 
 
 
 
 
 
222
 
223
  if ( $has_pricing ) {
224
  // Add plans to data.
64
  function _get_addon_info_filter( $data, $action = '', $args = null ) {
65
  $this->_logger->entrance();
66
 
67
+ $parent_plugin_id = fs_request_get( 'parent_plugin_id', $this->_fs->get_id() );
68
 
69
  if ( $this->_fs->get_id() != $parent_plugin_id ||
70
  ( 'plugin_information' !== $action ) ||
142
  }
143
  }
144
 
145
+ $latest = null;
146
+
147
  if ( ! $has_paid_plan && $selected_addon->is_wp_org_compliant ) {
148
  $repo_data = FS_Plugin_Updater::_fetch_plugin_info_from_repository(
149
  'plugin_information', (object) array(
172
  } else {
173
  $data->wp_org_missing = false;
174
 
175
+ $current_addon_version = false;
176
+ if ( $this->_fs->is_addon_activated( $selected_addon->id ) ) {
177
+ $current_addon_version = $this->_fs->get_addon_instance( $selected_addon->id )->get_plugin_version();
178
+ } else if ( $this->_fs->is_addon_installed( $selected_addon->id ) ) {
179
+ $addon_plugin_data = get_plugin_data(
180
+ ( WP_PLUGIN_DIR . '/' . $this->_fs->get_addon_basename( $selected_addon->id ) ),
181
+ false,
182
+ false
183
+ );
184
+
185
+ if ( ! empty( $addon_plugin_data ) ) {
186
+ $current_addon_version = $addon_plugin_data['Version'];
187
+ }
188
+ }
189
+
190
  // Fetch latest version from Freemius.
191
+ $latest = $this->_fs->_fetch_latest_version(
192
+ $selected_addon->id,
193
+ true,
194
+ WP_FS__TIME_24_HOURS_IN_SEC,
195
+ $current_addon_version
196
+ );
197
 
198
  if ( $has_paid_plan ) {
199
  $data->checkout_link = $this->_fs->checkout_url();
225
 
226
  if ( is_object( $latest ) ) {
227
  $data->version = $latest->version;
228
+ $data->last_updated = $latest->created;
229
  $data->requires = $latest->requires_platform_version;
230
  $data->tested = $latest->tested_up_to_version;
231
  } else {
236
  }
237
  }
238
 
239
+ $data->name = $selected_addon->title;
240
+ $view_vars = array( 'plugin' => $selected_addon );
241
+
242
+ if ( is_object( $latest ) && isset( $latest->readme ) && is_object( $latest->readme ) ) {
243
+ $latest_version_readme_data = $latest->readme;
244
+ if ( isset( $latest_version_readme_data->sections ) ) {
245
+ $data->sections = (array) $latest_version_readme_data->sections;
246
+ } else {
247
+ $data->sections = array();
248
+ }
249
+ }
250
+
251
+ $data->sections['description'] = fs_get_template( '/plugin-info/description.php', $view_vars );
252
 
253
  if ( $has_pricing ) {
254
  // Add plans to data.
vendor/freemius/includes/i18n.php CHANGED
@@ -94,7 +94,7 @@
94
  'activate-x-now' => _fs_x( 'Complete "%s" Activation Now',
95
  '%s - plugin name. As complete "Jetpack" activation now' ),
96
  'few-plugin-tweaks' => _fs_text( 'We made a few tweaks to the %s, %s' ),
97
- 'optin-x-now' => _fs_text( 'Opt in to make "%s" Better!' ),
98
  'error' => _fs_text( 'Error' ),
99
  'failed-finding-main-path' => _fs_text( 'Freemius SDK couldn\'t find the plugin\'s main file. Please contact sdk@freemius.com with the current error.' ),
100
  'learn-more' => _fs_text( 'Learn more' ),
@@ -215,7 +215,7 @@
215
  'delete-account-confirm' => _fs_text( 'Deletion is not temporary. Only delete if you no longer want to use this %s anymore. Are you sure you would like to continue with the deletion?' ),
216
  'downgrade-x-confirm' => _fs_text( 'Downgrading your plan will immediately stop all future recurring payments and your %s plan license will expire in %s.' ),
217
  'cancel-trial-confirm' => _fs_text( 'Cancelling the trial will immediately block access to all premium features. Are you sure?' ),
218
- 'after-downgrade-non-blocking' => _fs_text( 'You can still enjoy all %s features but you will not have access to %s updates and support.' ),
219
  'after-downgrade-blocking' => _fs_text( 'Once your license expires you can still use the Free version but you will NOT have access to the %s features.' ),
220
  'proceed-confirmation' => _fs_text( 'Are you sure you want to proceed?' ),
221
  #endregion Account
@@ -600,4 +600,4 @@
600
  'not-compatible-warning' => _fs_text( 'This plugin has not been marked as compatible with your version of WordPress.' ),
601
  'newer-installed' => _fs_text( 'Newer Version (%s) Installed' ),
602
  'latest-installed' => _fs_text( 'Latest Version Installed' ),
603
- );
94
  'activate-x-now' => _fs_x( 'Complete "%s" Activation Now',
95
  '%s - plugin name. As complete "Jetpack" activation now' ),
96
  'few-plugin-tweaks' => _fs_text( 'We made a few tweaks to the %s, %s' ),
97
+ 'optin-x-now' => _fs_text( 'Opt in to make "%s" better!' ),
98
  'error' => _fs_text( 'Error' ),
99
  'failed-finding-main-path' => _fs_text( 'Freemius SDK couldn\'t find the plugin\'s main file. Please contact sdk@freemius.com with the current error.' ),
100
  'learn-more' => _fs_text( 'Learn more' ),
215
  'delete-account-confirm' => _fs_text( 'Deletion is not temporary. Only delete if you no longer want to use this %s anymore. Are you sure you would like to continue with the deletion?' ),
216
  'downgrade-x-confirm' => _fs_text( 'Downgrading your plan will immediately stop all future recurring payments and your %s plan license will expire in %s.' ),
217
  'cancel-trial-confirm' => _fs_text( 'Cancelling the trial will immediately block access to all premium features. Are you sure?' ),
218
+ 'after-downgrade-non-blocking' => _fs_text( 'You can still enjoy all %s features but you will not have access to %s security & feature updates, nor support.' ),
219
  'after-downgrade-blocking' => _fs_text( 'Once your license expires you can still use the Free version but you will NOT have access to the %s features.' ),
220
  'proceed-confirmation' => _fs_text( 'Are you sure you want to proceed?' ),
221
  #endregion Account
600
  'not-compatible-warning' => _fs_text( 'This plugin has not been marked as compatible with your version of WordPress.' ),
601
  'newer-installed' => _fs_text( 'Newer Version (%s) Installed' ),
602
  'latest-installed' => _fs_text( 'Latest Version Installed' ),
603
+ );
vendor/freemius/includes/managers/class-fs-admin-menu-manager.php CHANGED
@@ -181,11 +181,6 @@
181
 
182
  // @deprecated
183
  $this->_type = $this->get_option( $menu, 'type', 'page' );
184
-
185
- $this->_first_time_path = $this->get_option( $menu, 'first-path', false );
186
- if ( ! empty( $this->_first_time_path ) && is_string( $this->_first_time_path ) ) {
187
- $this->_first_time_path = admin_url( $this->_first_time_path, 'admin' );
188
- }
189
  }
190
 
191
  $this->_is_override_exact = $this->get_bool_option( $menu, 'override_exact' );
@@ -208,6 +203,11 @@
208
  // 'page'
209
  // ) );
210
  }
 
 
 
 
 
211
  }
212
  }
213
 
@@ -280,6 +280,18 @@
280
  return $this->_network_menu_exists;
281
  }
282
 
 
 
 
 
 
 
 
 
 
 
 
 
283
  /**
284
  * @author Vova Feldman (@svovaf)
285
  * @since 1.1.3
181
 
182
  // @deprecated
183
  $this->_type = $this->get_option( $menu, 'type', 'page' );
 
 
 
 
 
184
  }
185
 
186
  $this->_is_override_exact = $this->get_bool_option( $menu, 'override_exact' );
203
  // 'page'
204
  // ) );
205
  }
206
+
207
+ $this->_first_time_path = $this->get_option( $menu, 'first-path', false );
208
+ if ( ! empty( $this->_first_time_path ) && is_string( $this->_first_time_path ) ) {
209
+ $this->_first_time_path = admin_url( $this->_first_time_path, 'admin' );
210
+ }
211
  }
212
  }
213
 
280
  return $this->_network_menu_exists;
281
  }
282
 
283
+ /**
284
+ * @author Leo Fajardo (@leorw)
285
+ *
286
+ * @param string $menu_slug
287
+ *
288
+ * @since 2.1.3
289
+ */
290
+ function set_slug_and_network_menu_exists_flag($menu_slug ) {
291
+ $this->_menu_slug = $menu_slug;
292
+ $this->_network_menu_exists = false;
293
+ }
294
+
295
  /**
296
  * @author Vova Feldman (@svovaf)
297
  * @since 1.1.3
vendor/freemius/includes/managers/class-fs-admin-notice-manager.php CHANGED
@@ -219,6 +219,9 @@
219
  return;
220
  }
221
 
 
 
 
222
  foreach ( $this->_notices as $id => $msg ) {
223
  if ( isset( $msg['wp_user_id'] ) && is_numeric( $msg['wp_user_id'] ) ) {
224
  if ( get_current_user_id() != $msg['wp_user_id'] ) {
@@ -226,6 +229,49 @@
226
  }
227
  }
228
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
229
  fs_require_template( 'admin-notice.php', $msg );
230
 
231
  if ( $msg['sticky'] ) {
@@ -244,6 +290,34 @@
244
  fs_enqueue_local_style( 'fs_common', '/admin/common.css' );
245
  }
246
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
247
  /**
248
  * Add admin message to admin messages queue, and hook to admin_notices / all_admin_notices if not yet hooked.
249
  *
219
  return;
220
  }
221
 
222
+
223
+ $show_admin_notices = ( ! $this->is_gutenberg_page() );
224
+
225
  foreach ( $this->_notices as $id => $msg ) {
226
  if ( isset( $msg['wp_user_id'] ) && is_numeric( $msg['wp_user_id'] ) ) {
227
  if ( get_current_user_id() != $msg['wp_user_id'] ) {
229
  }
230
  }
231
 
232
+ /**
233
+ * Added a filter to control the visibility of admin notices.
234
+ *
235
+ * Usage example:
236
+ *
237
+ * /**
238
+ * * @param bool $show
239
+ * * @param array $msg {
240
+ * * @var string $message The actual message.
241
+ * * @var string $title An optional message title.
242
+ * * @var string $type The type of the message ('success', 'update', 'warning', 'promotion').
243
+ * * @var string $id The unique identifier of the message.
244
+ * * @var string $manager_id The unique identifier of the notices manager. For plugins it would be the plugin's slug, for themes - `<slug>-theme`.
245
+ * * @var string $plugin The product's title.
246
+ * * @var string $wp_user_id An optional WP user ID that this admin notice is for.
247
+ * * }
248
+ * *
249
+ * * @return bool
250
+ * *\/
251
+ * function my_custom_show_admin_notice( $show, $msg ) {
252
+ * if ('trial_promotion' != $msg['id']) {
253
+ * return false;
254
+ * }
255
+ *
256
+ * return $show;
257
+ * }
258
+ *
259
+ * my_fs()->add_filter( 'show_admin_notice', 'my_custom_show_admin_notice', 10, 2 );
260
+ *
261
+ * @author Vova Feldman
262
+ * @since 2.2.0
263
+ */
264
+ $show_notice = call_user_func_array( 'fs_apply_filter', array(
265
+ $this->_module_unique_affix,
266
+ 'show_admin_notice',
267
+ $show_admin_notices,
268
+ $msg
269
+ ) );
270
+
271
+ if ( true !== $show_notice ) {
272
+ continue;
273
+ }
274
+
275
  fs_require_template( 'admin-notice.php', $msg );
276
 
277
  if ( $msg['sticky'] ) {
290
  fs_enqueue_local_style( 'fs_common', '/admin/common.css' );
291
  }
292
 
293
+ /**
294
+ * Check if the current page is the Gutenberg block editor.
295
+ *
296
+ * @author Vova Feldman (@svovaf)
297
+ * @since 2.2.3
298
+ *
299
+ * @return bool
300
+ */
301
+ function is_gutenberg_page() {
302
+ if ( function_exists( 'is_gutenberg_page' ) &&
303
+ is_gutenberg_page()
304
+ ) {
305
+ // The Gutenberg plugin is on.
306
+ return true;
307
+ }
308
+
309
+ $current_screen = get_current_screen();
310
+
311
+ if ( method_exists( $current_screen, 'is_block_editor' ) &&
312
+ $current_screen->is_block_editor()
313
+ ) {
314
+ // Gutenberg page on 5+.
315
+ return true;
316
+ }
317
+
318
+ return false;
319
+ }
320
+
321
  /**
322
  * Add admin message to admin messages queue, and hook to admin_notices / all_admin_notices if not yet hooked.
323
  *
vendor/freemius/includes/supplements/fs-essential-functions-1.1.7.1.php CHANGED
@@ -26,16 +26,12 @@
26
  * If the user changes the main plugin's file name, the file_exists()
27
  * will catch it.
28
  */
29
- if ( ! function_exists( 'get_plugins' ) ) {
30
- require_once ABSPATH . 'wp-admin/includes/plugin.php';
31
- }
32
-
33
- $all_plugins = get_plugins();
34
 
35
  $file_real_path = fs_normalize_path( realpath( $file ) );
36
 
37
  // Get active plugin's main files real full names (might be symlinks).
38
- foreach ( $all_plugins as $relative_path => &$data ) {
39
  if ( 0 === strpos( $file_real_path, fs_normalize_path( dirname( realpath( WP_PLUGIN_DIR . '/' . $relative_path ) ) ) ) ) {
40
  if ( '.' !== dirname( trailingslashit( $relative_path ) ) ) {
41
  return $relative_path;
26
  * If the user changes the main plugin's file name, the file_exists()
27
  * will catch it.
28
  */
29
+ $all_plugins = fs_get_plugins( true );
 
 
 
 
30
 
31
  $file_real_path = fs_normalize_path( realpath( $file ) );
32
 
33
  // Get active plugin's main files real full names (might be symlinks).
34
+ foreach ( $all_plugins as $relative_path => $data ) {
35
  if ( 0 === strpos( $file_real_path, fs_normalize_path( dirname( realpath( WP_PLUGIN_DIR . '/' . $relative_path ) ) ) ) ) {
36
  if ( '.' !== dirname( trailingslashit( $relative_path ) ) ) {
37
  return $relative_path;
vendor/freemius/includes/supplements/fs-essential-functions-2.2.1.php ADDED
@@ -0,0 +1,45 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /**
3
+ * @package Freemius
4
+ * @copyright Copyright (c) 2015, Freemius, Inc.
5
+ * @license https://www.gnu.org/licenses/gpl-3.0.html GNU General Public License Version 3
6
+ * @since 2.2.1
7
+ */
8
+
9
+ if ( ! defined( 'ABSPATH' ) ) {
10
+ exit;
11
+ }
12
+
13
+ if ( ! function_exists( 'fs_get_plugins' ) ) {
14
+ /**
15
+ * @author Leo Fajardo (@leorw)
16
+ * @since 2.2.1
17
+ *
18
+ * @param bool $delete_cache
19
+ *
20
+ * @return array
21
+ */
22
+ function fs_get_plugins( $delete_cache = false ) {
23
+ $cached_plugins = wp_cache_get( 'plugins', 'plugins' );
24
+ if ( ! is_array( $cached_plugins ) ) {
25
+ $cached_plugins = array();
26
+ }
27
+
28
+ $plugin_folder = '';
29
+ if ( isset( $cached_plugins[ $plugin_folder ] ) ) {
30
+ $plugins = $cached_plugins[ $plugin_folder ];
31
+ } else {
32
+ if ( ! function_exists( 'get_plugins' ) ) {
33
+ require_once ABSPATH . 'wp-admin/includes/plugin.php';
34
+ }
35
+
36
+ $plugins = get_plugins();
37
+
38
+ if ( $delete_cache && is_plugin_active( 'woocommerce/woocommerce.php' ) ) {
39
+ wp_cache_delete( 'plugins', 'plugins' );
40
+ }
41
+ }
42
+
43
+ return $plugins;
44
+ }
45
+ }
vendor/freemius/languages/freemius.pot CHANGED
@@ -1,4 +1,4 @@
1
- # Copyright (C) 2018 freemius
2
  # This file is distributed under the same license as the freemius package.
3
  msgid ""
4
  msgstr ""
@@ -16,1226 +16,1301 @@ msgstr ""
16
  "X-Poedit-SourceCharset: UTF-8\n"
17
  "Plural-Forms: nplurals=2; plural=(n != 1);\n"
18
 
19
- #: includes/class-freemius.php:1551
20
  msgid "Freemius SDK couldn't find the plugin's main file. Please contact sdk@freemius.com with the current error."
21
  msgstr ""
22
 
23
- #: includes/class-freemius.php:1553
24
  msgid "Error"
25
  msgstr ""
26
 
27
- #: includes/class-freemius.php:1871
28
  msgid "I found a better %s"
29
  msgstr ""
30
 
31
- #: includes/class-freemius.php:1873
32
  msgid "What's the %s's name?"
33
  msgstr ""
34
 
35
- #: includes/class-freemius.php:1879
36
  msgid "It's a temporary %s. I'm just debugging an issue."
37
  msgstr ""
38
 
39
- #: includes/class-freemius.php:1881
40
  msgid "Deactivation"
41
  msgstr ""
42
 
43
- #: includes/class-freemius.php:1882
44
  msgid "Theme Switch"
45
  msgstr ""
46
 
47
- #: includes/class-freemius.php:1891, templates/forms/resend-key.php:24
48
  msgid "Other"
49
  msgstr ""
50
 
51
- #: includes/class-freemius.php:1899
52
  msgid "I no longer need the %s"
53
  msgstr ""
54
 
55
- #: includes/class-freemius.php:1906
56
  msgid "I only needed the %s for a short period"
57
  msgstr ""
58
 
59
- #: includes/class-freemius.php:1912
60
  msgid "The %s broke my site"
61
  msgstr ""
62
 
63
- #: includes/class-freemius.php:1919
64
  msgid "The %s suddenly stopped working"
65
  msgstr ""
66
 
67
- #: includes/class-freemius.php:1929
68
  msgid "I can't pay for it anymore"
69
  msgstr ""
70
 
71
- #: includes/class-freemius.php:1931
72
  msgid "What price would you feel comfortable paying?"
73
  msgstr ""
74
 
75
- #: includes/class-freemius.php:1937
76
  msgid "I don't like to share my information with you"
77
  msgstr ""
78
 
79
- #: includes/class-freemius.php:1958
80
  msgid "The %s didn't work"
81
  msgstr ""
82
 
83
- #: includes/class-freemius.php:1968
84
  msgid "I couldn't understand how to make it work"
85
  msgstr ""
86
 
87
- #: includes/class-freemius.php:1976
88
  msgid "The %s is great, but I need specific feature that you don't support"
89
  msgstr ""
90
 
91
- #: includes/class-freemius.php:1978
92
  msgid "What feature?"
93
  msgstr ""
94
 
95
- #: includes/class-freemius.php:1982
96
  msgid "The %s is not working"
97
  msgstr ""
98
 
99
- #: includes/class-freemius.php:1984
100
  msgid "Kindly share what didn't work so we can fix it for future users..."
101
  msgstr ""
102
 
103
- #: includes/class-freemius.php:1988
104
  msgid "It's not what I was looking for"
105
  msgstr ""
106
 
107
- #: includes/class-freemius.php:1990
108
  msgid "What you've been looking for?"
109
  msgstr ""
110
 
111
- #: includes/class-freemius.php:1994
112
  msgid "The %s didn't work as expected"
113
  msgstr ""
114
 
115
- #: includes/class-freemius.php:1996
116
  msgid "What did you expect?"
117
  msgstr ""
118
 
119
- #: includes/class-freemius.php:2729, templates/debug.php:20
120
  msgid "Freemius Debug"
121
  msgstr ""
122
 
123
- #: includes/class-freemius.php:3453
124
  msgid "I don't know what is cURL or how to install it, help me!"
125
  msgstr ""
126
 
127
- #: includes/class-freemius.php:3455
128
  msgid "We'll make sure to contact your hosting company and resolve the issue. You will get a follow-up email to %s once we have an update."
129
  msgstr ""
130
 
131
- #: includes/class-freemius.php:3462
132
  msgid "Great, please install cURL and enable it in your php.ini file. In addition, search for the 'disable_functions' directive in your php.ini file and remove any disabled methods starting with 'curl_'. To make sure it was successfully activated, use 'phpinfo()'. Once activated, deactivate the %s and reactivate it back again."
133
  msgstr ""
134
 
135
- #: includes/class-freemius.php:3567
136
  msgid "Yes - do your thing"
137
  msgstr ""
138
 
139
- #: includes/class-freemius.php:3572
140
  msgid "No - just deactivate"
141
  msgstr ""
142
 
143
- #: includes/class-freemius.php:3617, includes/class-freemius.php:4117, includes/class-freemius.php:5178, includes/class-freemius.php:10992, includes/class-freemius.php:14256, includes/class-freemius.php:14308, includes/class-freemius.php:14370, includes/class-freemius.php:16500, includes/class-freemius.php:16510, includes/class-freemius.php:17066, includes/class-freemius.php:17084, includes/class-freemius.php:17182, includes/class-freemius.php:17925, templates/add-ons.php:43
144
  msgctxt "exclamation"
145
  msgid "Oops"
146
  msgstr ""
147
 
148
- #: includes/class-freemius.php:3686
149
  msgid "Thank for giving us the chance to fix it! A message was just sent to our technical staff. We will get back to you as soon as we have an update to %s. Appreciate your patience."
150
  msgstr ""
151
 
152
- #: includes/class-freemius.php:4114
153
  msgctxt "addonX cannot run without pluginY"
154
  msgid "%s cannot run without %s."
155
  msgstr ""
156
 
157
- #: includes/class-freemius.php:4115
158
  msgctxt "addonX cannot run..."
159
  msgid "%s cannot run without the plugin."
160
  msgstr ""
161
 
162
- #: includes/class-freemius.php:4227, includes/class-freemius.php:4252, includes/class-freemius.php:17155
163
  msgid "Unexpected API error. Please contact the %s's author with the following error."
164
  msgstr ""
165
 
166
- #: includes/class-freemius.php:4866
167
  msgid "Premium %s version was successfully activated."
168
  msgstr ""
169
 
170
- #: includes/class-freemius.php:4878, includes/class-freemius.php:6711
171
  msgctxt "Used to express elation, enthusiasm, or triumph (especially in electronic communication)."
172
  msgid "W00t"
173
  msgstr ""
174
 
175
- #: includes/class-freemius.php:4893
176
  msgid "You have a %s license."
177
  msgstr ""
178
 
179
- #: includes/class-freemius.php:4897, includes/class-freemius.php:13677, includes/class-freemius.php:13688, includes/class-freemius.php:16428, includes/class-freemius.php:16728, includes/class-freemius.php:16793, includes/class-freemius.php:16943
180
  msgctxt "interjection expressing joy or exuberance"
181
  msgid "Yee-haw"
182
  msgstr ""
183
 
184
- #: includes/class-freemius.php:5161
185
  msgid "%s free trial was successfully cancelled. Since the add-on is premium only it was automatically deactivated. If you like to use it in the future, you'll have to purchase a license."
186
  msgstr ""
187
 
188
- #: includes/class-freemius.php:5165
189
  msgid "%s is a premium only add-on. You have to purchase a license first before activating the plugin."
190
  msgstr ""
191
 
192
- #: includes/class-freemius.php:5174, templates/add-ons.php:99, templates/account/partials/addon.php:283
193
  msgid "More information about %s"
194
  msgstr ""
195
 
196
- #: includes/class-freemius.php:5175
197
  msgid "Purchase License"
198
  msgstr ""
199
 
200
- #: includes/class-freemius.php:6086, templates/connect.php:161
201
  msgid "You should receive an activation email for %s to your mailbox at %s. Please make sure you click the activation button in that email to %s."
202
  msgstr ""
203
 
204
- #: includes/class-freemius.php:6090
205
  msgid "start the trial"
206
  msgstr ""
207
 
208
- #: includes/class-freemius.php:6091, templates/connect.php:165
209
  msgid "complete the install"
210
  msgstr ""
211
 
212
- #: includes/class-freemius.php:6198
213
  msgid "You are just one step away - %s"
214
  msgstr ""
215
 
216
- #: includes/class-freemius.php:6201
217
  msgctxt "%s - plugin name. As complete \"PluginX\" activation now"
218
  msgid "Complete \"%s\" Activation Now"
219
  msgstr ""
220
 
221
- #: includes/class-freemius.php:6278
222
  msgid "We made a few tweaks to the %s, %s"
223
  msgstr ""
224
 
225
- #: includes/class-freemius.php:6282
226
- msgid "Opt in to make \"%s\" Better!"
227
  msgstr ""
228
 
229
- #: includes/class-freemius.php:6710
230
  msgid "The upgrade of %s was successfully completed."
231
  msgstr ""
232
 
233
- #: includes/class-freemius.php:8435, includes/class-fs-plugin-updater.php:581, includes/class-fs-plugin-updater.php:733, includes/class-fs-plugin-updater.php:739, templates/auto-installation.php:32
234
  msgid "Add-On"
235
  msgstr ""
236
 
237
- #: includes/class-freemius.php:8437, templates/debug.php:349, templates/debug.php:510
238
  msgid "Plugin"
239
  msgstr ""
240
 
241
- #: includes/class-freemius.php:8438, templates/debug.php:349, templates/debug.php:510, templates/forms/deactivation/form.php:64
242
  msgid "Theme"
243
  msgstr ""
244
 
245
- #: includes/class-freemius.php:10859
246
  msgid "Invalid site details collection."
247
  msgstr ""
248
 
249
- #: includes/class-freemius.php:10979
250
  msgid "We couldn't find your email address in the system, are you sure it's the right address?"
251
  msgstr ""
252
 
253
- #: includes/class-freemius.php:10981
254
  msgid "We can't see any active licenses associated with that email address, are you sure it's the right address?"
255
  msgstr ""
256
 
257
- #: includes/class-freemius.php:11217
258
  msgid "Account is pending activation."
259
  msgstr ""
260
 
261
- #: includes/class-freemius.php:13659
 
 
 
 
 
 
 
 
 
 
 
 
262
  msgid "%s activation was successfully completed."
263
  msgstr ""
264
 
265
- #: includes/class-freemius.php:13673
266
  msgid "Your account was successfully activated with the %s plan."
267
  msgstr ""
268
 
269
- #: includes/class-freemius.php:13684, includes/class-freemius.php:16789
270
  msgid "Your trial has been successfully started."
271
  msgstr ""
272
 
273
- #: includes/class-freemius.php:14254, includes/class-freemius.php:14306, includes/class-freemius.php:14368
274
  msgid "Couldn't activate %s."
275
  msgstr ""
276
 
277
- #: includes/class-freemius.php:14255, includes/class-freemius.php:14307, includes/class-freemius.php:14369
278
  msgid "Please contact us with the following message:"
279
  msgstr ""
280
 
281
- #: includes/class-freemius.php:14718, includes/class-freemius.php:18988
282
  msgid "Upgrade"
283
  msgstr ""
284
 
285
- #: includes/class-freemius.php:14724
286
  msgid "Start Trial"
287
  msgstr ""
288
 
289
- #: includes/class-freemius.php:14726
290
  msgid "Pricing"
291
  msgstr ""
292
 
293
- #: includes/class-freemius.php:14786, includes/class-freemius.php:14788
294
  msgid "Affiliation"
295
  msgstr ""
296
 
297
- #: includes/class-freemius.php:14808, includes/class-freemius.php:14810, templates/account.php:146, templates/debug.php:314
298
  msgid "Account"
299
  msgstr ""
300
 
301
- #: includes/class-freemius.php:14821, includes/class-freemius.php:14823, includes/customizer/class-fs-customizer-support-section.php:60
302
  msgid "Contact Us"
303
  msgstr ""
304
 
305
- #: includes/class-freemius.php:14833, includes/class-freemius.php:14835, includes/class-freemius.php:18998, templates/account.php:96, templates/account/partials/addon.php:37
306
  msgid "Add-Ons"
307
  msgstr ""
308
 
309
- #: includes/class-freemius.php:14867, templates/pricing.php:97
 
 
 
 
 
 
 
 
 
 
310
  msgctxt "noun"
311
  msgid "Pricing"
312
  msgstr ""
313
 
314
- #: includes/class-freemius.php:15061, includes/customizer/class-fs-customizer-support-section.php:67
315
  msgid "Support Forum"
316
  msgstr ""
317
 
318
- #: includes/class-freemius.php:15846
319
  msgid "Your email has been successfully verified - you are AWESOME!"
320
  msgstr ""
321
 
322
- #: includes/class-freemius.php:15847
323
  msgctxt "a positive response"
324
  msgid "Right on"
325
  msgstr ""
326
 
327
- #: includes/class-freemius.php:16419
328
  msgid "Your %s Add-on plan was successfully upgraded."
329
  msgstr ""
330
 
331
- #: includes/class-freemius.php:16421
332
  msgid "%s Add-on was successfully purchased."
333
  msgstr ""
334
 
335
- #: includes/class-freemius.php:16424
336
  msgid "Download the latest version"
337
  msgstr ""
338
 
339
- #: includes/class-freemius.php:16496
340
  msgctxt "%1s - plugin title, %2s - API domain"
341
  msgid "Your server is blocking the access to Freemius' API, which is crucial for %1s synchronization. Please contact your host to whitelist %2s"
342
  msgstr ""
343
 
344
- #: includes/class-freemius.php:16499, includes/class-freemius.php:16914, includes/class-freemius.php:16979
345
  msgid "Error received from the server:"
346
  msgstr ""
347
 
348
- #: includes/class-freemius.php:16509
349
  msgid "It seems like one of the authentication parameters is wrong. Update your Public Key, Secret Key & User ID, and try again."
350
  msgstr ""
351
 
352
- #: includes/class-freemius.php:16691, includes/class-freemius.php:16919, includes/class-freemius.php:16962
353
  msgctxt "something somebody says when they are thinking about what you have just said."
354
  msgid "Hmm"
355
  msgstr ""
356
 
357
- #: includes/class-freemius.php:16704
358
  msgid "It looks like you are still on the %s plan. If you did upgrade or change your plan, it's probably an issue on our side - sorry."
359
  msgstr ""
360
 
361
- #: includes/class-freemius.php:16705, templates/account.php:98, templates/add-ons.php:130, templates/account/partials/addon.php:39
362
  msgctxt "trial period"
363
  msgid "Trial"
364
  msgstr ""
365
 
366
- #: includes/class-freemius.php:16710
367
  msgid "I have upgraded my account but when I try to Sync the License, the plan remains %s."
368
  msgstr ""
369
 
370
- #: includes/class-freemius.php:16714, includes/class-freemius.php:16771
371
  msgid "Please contact us here"
372
  msgstr ""
373
 
374
- #: includes/class-freemius.php:16724
375
  msgid "Your plan was successfully upgraded."
376
  msgstr ""
377
 
378
- #: includes/class-freemius.php:16741
379
  msgid "Your plan was successfully changed to %s."
380
  msgstr ""
381
 
382
- #: includes/class-freemius.php:16757
383
  msgid "Your license has expired. You can still continue using the free %s forever."
384
  msgstr ""
385
 
386
- #: includes/class-freemius.php:16759
387
  msgid "Your license has expired. %1$sUpgrade now%2$s to continue using the %3$s without interruptions."
388
  msgstr ""
389
 
390
- #: includes/class-freemius.php:16767
391
  msgid "Your license has been cancelled. If you think it's a mistake, please contact support."
392
  msgstr ""
393
 
394
- #: includes/class-freemius.php:16780
395
  msgid "Your license has expired. You can still continue using all the %s features, but you'll need to renew your license to continue getting updates and support."
396
  msgstr ""
397
 
398
- #: includes/class-freemius.php:16803
399
  msgid "Your free trial has expired. You can still continue using all our free features."
400
  msgstr ""
401
 
402
- #: includes/class-freemius.php:16805
403
  msgid "Your free trial has expired. %1$sUpgrade now%2$s to continue using the %3$s without interruptions."
404
  msgstr ""
405
 
406
- #: includes/class-freemius.php:16910
407
  msgid "It looks like the license could not be activated."
408
  msgstr ""
409
 
410
- #: includes/class-freemius.php:16940
411
  msgid "Your license was successfully activated."
412
  msgstr ""
413
 
414
- #: includes/class-freemius.php:16966
415
  msgid "It looks like your site currently doesn't have an active license."
416
  msgstr ""
417
 
418
- #: includes/class-freemius.php:16978
419
  msgid "It looks like the license deactivation failed."
420
  msgstr ""
421
 
422
- #: includes/class-freemius.php:17006
423
  msgid "Your license was successfully deactivated, you are back to the %s plan."
424
  msgstr ""
425
 
426
- #: includes/class-freemius.php:17007
427
  msgid "O.K"
428
  msgstr ""
429
 
430
- #: includes/class-freemius.php:17055
431
- msgid "Your plan was successfully downgraded. Your %s plan license will expire in %s."
432
  msgstr ""
433
 
434
- #: includes/class-freemius.php:17065
435
- msgid "Seems like we are having some temporary issue with your plan downgrade. Please try again in few minutes."
436
  msgstr ""
437
 
438
- #: includes/class-freemius.php:17089
439
  msgid "You are already running the %s in a trial mode."
440
  msgstr ""
441
 
442
- #: includes/class-freemius.php:17100
443
  msgid "You already utilized a trial before."
444
  msgstr ""
445
 
446
- #: includes/class-freemius.php:17114
447
  msgid "Plan %s do not exist, therefore, can't start a trial."
448
  msgstr ""
449
 
450
- #: includes/class-freemius.php:17125
451
  msgid "Plan %s does not support a trial period."
452
  msgstr ""
453
 
454
- #: includes/class-freemius.php:17136
455
  msgid "None of the %s's plans supports a trial period."
456
  msgstr ""
457
 
458
- #: includes/class-freemius.php:17186
459
  msgid "It looks like you are not in trial mode anymore so there's nothing to cancel :)"
460
  msgstr ""
461
 
462
- #: includes/class-freemius.php:17237
463
- msgid "Your %s free trial was successfully cancelled."
464
  msgstr ""
465
 
466
- #: includes/class-freemius.php:17242
467
- msgid "Seems like we are having some temporary issue with your trial cancellation. Please try again in few minutes."
468
  msgstr ""
469
 
470
- #: includes/class-freemius.php:17533
471
  msgid "Version %s was released."
472
  msgstr ""
473
 
474
- #: includes/class-freemius.php:17533
475
  msgid "Please download %s."
476
  msgstr ""
477
 
478
- #: includes/class-freemius.php:17540
479
  msgid "the latest %s version here"
480
  msgstr ""
481
 
482
- #: includes/class-freemius.php:17545
483
  msgid "New"
484
  msgstr ""
485
 
486
- #: includes/class-freemius.php:17550
487
  msgid "Seems like you got the latest release."
488
  msgstr ""
489
 
490
- #: includes/class-freemius.php:17551
491
  msgid "You are all good!"
492
  msgstr ""
493
 
494
- #: includes/class-freemius.php:17817
495
  msgid "Verification mail was just sent to %s. If you can't find it after 5 min, please check your spam box."
496
  msgstr ""
497
 
498
- #: includes/class-freemius.php:17952
499
  msgid "Site successfully opted in."
500
  msgstr ""
501
 
502
- #: includes/class-freemius.php:17953, includes/class-freemius.php:18730
503
  msgid "Awesome"
504
  msgstr ""
505
 
506
- #: includes/class-freemius.php:17969, templates/forms/optout.php:32
507
  msgid "We appreciate your help in making the %s better by letting us track some usage data."
508
  msgstr ""
509
 
510
- #: includes/class-freemius.php:17970
511
  msgid "Thank you!"
512
  msgstr ""
513
 
514
- #: includes/class-freemius.php:17977
515
  msgid "We will no longer be sending any usage data of %s on %s to %s."
516
  msgstr ""
517
 
518
- #: includes/class-freemius.php:18092
519
  msgid "Please check your mailbox, you should receive an email via %s to confirm the ownership change. From security reasons, you must confirm the change within the next 15 min. If you cannot find the email, please check your spam folder."
520
  msgstr ""
521
 
522
- #: includes/class-freemius.php:18098
523
  msgid "Thanks for confirming the ownership change. An email was just sent to %s for final approval."
524
  msgstr ""
525
 
526
- #: includes/class-freemius.php:18103
527
  msgid "%s is the new owner of the account."
528
  msgstr ""
529
 
530
- #: includes/class-freemius.php:18105
531
  msgctxt "as congratulations"
532
  msgid "Congrats"
533
  msgstr ""
534
 
535
- #: includes/class-freemius.php:18125
536
  msgid "Sorry, we could not complete the email update. Another user with the same email is already registered."
537
  msgstr ""
538
 
539
- #: includes/class-freemius.php:18126
540
  msgid "If you would like to give up the ownership of the %s's account to %s click the Change Ownership button."
541
  msgstr ""
542
 
543
- #: includes/class-freemius.php:18133
544
  msgid "Change Ownership"
545
  msgstr ""
546
 
547
- #: includes/class-freemius.php:18141
548
  msgid "Your email was successfully updated. You should receive an email with confirmation instructions in few moments."
549
  msgstr ""
550
 
551
- #: includes/class-freemius.php:18153
552
  msgid "Please provide your full name."
553
  msgstr ""
554
 
555
- #: includes/class-freemius.php:18158
556
  msgid "Your name was successfully updated."
557
  msgstr ""
558
 
559
- #: includes/class-freemius.php:18219
560
  msgid "You have successfully updated your %s."
561
  msgstr ""
562
 
563
- #: includes/class-freemius.php:18359
564
  msgid "Just letting you know that the add-ons information of %s is being pulled from an external server."
565
  msgstr ""
566
 
567
- #: includes/class-freemius.php:18360
568
  msgctxt "advance notice of something that will need attention."
569
  msgid "Heads up"
570
  msgstr ""
571
 
572
- #: includes/class-freemius.php:18770
573
  msgctxt "exclamation"
574
  msgid "Hey"
575
  msgstr ""
576
 
577
- #: includes/class-freemius.php:18770
578
  msgid "How do you like %s so far? Test all our %s premium features with a %d-day free trial."
579
  msgstr ""
580
 
581
- #: includes/class-freemius.php:18778
582
  msgid "No commitment for %s days - cancel anytime!"
583
  msgstr ""
584
 
585
- #: includes/class-freemius.php:18779
586
  msgid "No credit card required"
587
  msgstr ""
588
 
589
- #: includes/class-freemius.php:18786, templates/forms/trial-start.php:53
590
  msgctxt "call to action"
591
  msgid "Start free trial"
592
  msgstr ""
593
 
594
- #: includes/class-freemius.php:18863
595
  msgid "Hey there, did you know that %s has an affiliate program? If you like the %s you can become our ambassador and earn some cash!"
596
  msgstr ""
597
 
598
- #: includes/class-freemius.php:18872
599
  msgid "Learn more"
600
  msgstr ""
601
 
602
- #: includes/class-freemius.php:19022, templates/account.php:398, templates/account.php:501, templates/connect.php:169, templates/connect.php:408, templates/forms/license-activation.php:24, templates/account/partials/addon.php:230
603
  msgid "Activate License"
604
  msgstr ""
605
 
606
- #: includes/class-freemius.php:19023, templates/account.php:461, templates/account.php:500, templates/account/partials/site.php:256
607
  msgid "Change License"
608
  msgstr ""
609
 
610
- #: includes/class-freemius.php:19105, templates/account/partials/site.php:161
611
  msgid "Opt Out"
612
  msgstr ""
613
 
614
- #: includes/class-freemius.php:19107, includes/class-freemius.php:19112, templates/account/partials/site.php:43, templates/account/partials/site.php:161
615
  msgid "Opt In"
616
  msgstr ""
617
 
618
- #: includes/class-freemius.php:19304
 
 
 
 
 
 
 
 
619
  msgid "Please follow these steps to complete the upgrade"
620
  msgstr ""
621
 
622
- #: includes/class-freemius.php:19308
623
  msgid "Download the latest %s version"
624
  msgstr ""
625
 
626
- #: includes/class-freemius.php:19312
627
  msgid "Upload and activate the downloaded version"
628
  msgstr ""
629
 
630
- #: includes/class-freemius.php:19314
631
  msgid "How to upload and activate?"
632
  msgstr ""
633
 
634
- #: includes/class-freemius.php:19443
635
  msgid "%sClick here%s to choose the sites where you'd like to activate the license on."
636
  msgstr ""
637
 
638
- #: includes/class-freemius.php:19604
639
  msgid "Auto installation only works for opted-in users."
640
  msgstr ""
641
 
642
- #: includes/class-freemius.php:19614, includes/class-freemius.php:19647, includes/class-fs-plugin-updater.php:713, includes/class-fs-plugin-updater.php:727
643
  msgid "Invalid module ID."
644
  msgstr ""
645
 
646
- #: includes/class-freemius.php:19623, includes/class-fs-plugin-updater.php:747
647
  msgid "Premium version already active."
648
  msgstr ""
649
 
650
- #: includes/class-freemius.php:19630
651
  msgid "You do not have a valid license to access the premium version."
652
  msgstr ""
653
 
654
- #: includes/class-freemius.php:19637
655
  msgid "Plugin is a \"Serviceware\" which means it does not have a premium code version."
656
  msgstr ""
657
 
658
- #: includes/class-freemius.php:19655, includes/class-fs-plugin-updater.php:746
659
  msgid "Premium add-on version already installed."
660
  msgstr ""
661
 
662
- #: includes/class-freemius.php:20000
663
  msgid "View paid features"
664
  msgstr ""
665
 
666
- #: includes/class-freemius.php:20310
667
  msgid "Thank you so much for using %s and its add-ons!"
668
  msgstr ""
669
 
670
- #: includes/class-freemius.php:20311
671
  msgid "Thank you so much for using %s!"
672
  msgstr ""
673
 
674
- #: includes/class-freemius.php:20317
675
  msgid "You've already opted-in to our usage-tracking, which helps us keep improving the %s."
676
  msgstr ""
677
 
678
- #: includes/class-freemius.php:20321
679
  msgid "Thank you so much for using our products!"
680
  msgstr ""
681
 
682
- #: includes/class-freemius.php:20322
683
  msgid "You've already opted-in to our usage-tracking, which helps us keep improving them."
684
  msgstr ""
685
 
686
- #: includes/class-freemius.php:20341
687
  msgid "%s and its add-ons"
688
  msgstr ""
689
 
690
- #: includes/class-freemius.php:20350
691
  msgid "Products"
692
  msgstr ""
693
 
694
- #: includes/class-freemius.php:20357, templates/connect.php:259
695
  msgid "Yes"
696
  msgstr ""
697
 
698
- #: includes/class-freemius.php:20358, templates/connect.php:260
699
  msgid "send me security & feature updates, educational content and offers."
700
  msgstr ""
701
 
702
- #: includes/class-freemius.php:20359, templates/connect.php:265
703
  msgid "No"
704
  msgstr ""
705
 
706
- #: includes/class-freemius.php:20361, templates/connect.php:267
707
  msgid "do %sNOT%s send me security & feature updates, educational content and offers."
708
  msgstr ""
709
 
710
- #: includes/class-freemius.php:20371
711
  msgid "Due to the new %sEU General Data Protection Regulation (GDPR)%s compliance requirements it is required that you provide your explicit consent, again, confirming that you are onboard 🙂"
712
  msgstr ""
713
 
714
- #: includes/class-freemius.php:20373, templates/connect.php:274
715
  msgid "Please let us know if you'd like us to contact you for security & feature updates, educational content, and occasional offers:"
716
  msgstr ""
717
 
718
- #: includes/class-freemius.php:20657
719
  msgid "License key is empty."
720
  msgstr ""
721
 
722
- #: includes/class-fs-plugin-updater.php:184, includes/class-fs-plugin-updater.php:219
723
- msgid "%sRenew your license now%s to access version %s security & feature updates, and support."
724
  msgstr ""
725
 
726
- #: includes/class-fs-plugin-updater.php:776
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
727
  msgid "Installing plugin: %s"
728
  msgstr ""
729
 
730
- #: includes/class-fs-plugin-updater.php:817
731
  msgid "Unable to connect to the filesystem. Please confirm your credentials."
732
  msgstr ""
733
 
734
- #: includes/class-fs-plugin-updater.php:923
735
  msgid "The remote plugin package does not contain a folder with the desired slug and renaming did not work."
736
  msgstr ""
737
 
738
- #: includes/fs-plugin-info-dialog.php:336, templates/account/partials/addon.php:287
739
  msgctxt "verb"
740
  msgid "Purchase"
741
  msgstr ""
742
 
743
- #: includes/fs-plugin-info-dialog.php:339
744
  msgid "Start my free %s"
745
  msgstr ""
746
 
747
- #: includes/fs-plugin-info-dialog.php:380
748
  msgid "Install Free Version Now"
749
  msgstr ""
750
 
751
- #: includes/fs-plugin-info-dialog.php:381, templates/auto-installation.php:111, templates/account/partials/addon.php:267, templates/account/partials/addon.php:317
752
  msgid "Install Now"
753
  msgstr ""
754
 
755
- #: includes/fs-plugin-info-dialog.php:392
756
  msgctxt "as download latest version"
757
  msgid "Download Latest Free Version"
758
  msgstr ""
759
 
760
- #: includes/fs-plugin-info-dialog.php:393, templates/account.php:80, templates/account/partials/addon.php:21
761
  msgctxt "as download latest version"
762
  msgid "Download Latest"
763
  msgstr ""
764
 
765
- #: includes/fs-plugin-info-dialog.php:403
766
  msgid "Install Free Version Update Now"
767
  msgstr ""
768
 
769
- #: includes/fs-plugin-info-dialog.php:404, templates/account.php:452
770
  msgid "Install Update Now"
771
  msgstr ""
772
 
773
- #: includes/fs-plugin-info-dialog.php:415
774
  msgid "Newer Free Version (%s) Installed"
775
  msgstr ""
776
 
777
- #: includes/fs-plugin-info-dialog.php:416
778
  msgid "Newer Version (%s) Installed"
779
  msgstr ""
780
 
781
- #: includes/fs-plugin-info-dialog.php:424
782
  msgid "Latest Free Version Installed"
783
  msgstr ""
784
 
785
- #: includes/fs-plugin-info-dialog.php:425
786
  msgid "Latest Version Installed"
787
  msgstr ""
788
 
789
- #: includes/fs-plugin-info-dialog.php:580
790
  msgctxt "Plugin installer section title"
791
  msgid "Description"
792
  msgstr ""
793
 
794
- #: includes/fs-plugin-info-dialog.php:581
795
  msgctxt "Plugin installer section title"
796
  msgid "Installation"
797
  msgstr ""
798
 
799
- #: includes/fs-plugin-info-dialog.php:582
800
  msgctxt "Plugin installer section title"
801
  msgid "FAQ"
802
  msgstr ""
803
 
804
- #: includes/fs-plugin-info-dialog.php:583, templates/plugin-info/description.php:55
805
  msgid "Screenshots"
806
  msgstr ""
807
 
808
- #: includes/fs-plugin-info-dialog.php:584
809
  msgctxt "Plugin installer section title"
810
  msgid "Changelog"
811
  msgstr ""
812
 
813
- #: includes/fs-plugin-info-dialog.php:585
814
  msgctxt "Plugin installer section title"
815
  msgid "Reviews"
816
  msgstr ""
817
 
818
- #: includes/fs-plugin-info-dialog.php:586
819
  msgctxt "Plugin installer section title"
820
  msgid "Other Notes"
821
  msgstr ""
822
 
823
- #: includes/fs-plugin-info-dialog.php:601
824
  msgctxt "Plugin installer section title"
825
  msgid "Features & Pricing"
826
  msgstr ""
827
 
828
- #: includes/fs-plugin-info-dialog.php:611
829
  msgid "Plugin Install"
830
  msgstr ""
831
 
832
- #: includes/fs-plugin-info-dialog.php:683
833
  msgctxt "e.g. Professional Plan"
834
  msgid "%s Plan"
835
  msgstr ""
836
 
837
- #: includes/fs-plugin-info-dialog.php:709
838
  msgctxt "e.g. the best product"
839
  msgid "Best"
840
  msgstr ""
841
 
842
- #: includes/fs-plugin-info-dialog.php:715, includes/fs-plugin-info-dialog.php:735
843
  msgctxt "as every month"
844
  msgid "Monthly"
845
  msgstr ""
846
 
847
- #: includes/fs-plugin-info-dialog.php:718
848
  msgctxt "as once a year"
849
  msgid "Annual"
850
  msgstr ""
851
 
852
- #: includes/fs-plugin-info-dialog.php:721
853
  msgid "Lifetime"
854
  msgstr ""
855
 
856
- #: includes/fs-plugin-info-dialog.php:735, includes/fs-plugin-info-dialog.php:737, includes/fs-plugin-info-dialog.php:739
857
  msgctxt "e.g. billed monthly"
858
  msgid "Billed %s"
859
  msgstr ""
860
 
861
- #: includes/fs-plugin-info-dialog.php:737
862
  msgctxt "as once a year"
863
  msgid "Annually"
864
  msgstr ""
865
 
866
- #: includes/fs-plugin-info-dialog.php:739
867
  msgctxt "as once a year"
868
  msgid "Once"
869
  msgstr ""
870
 
871
- #: includes/fs-plugin-info-dialog.php:745
872
  msgid "Single Site License"
873
  msgstr ""
874
 
875
- #: includes/fs-plugin-info-dialog.php:747
876
  msgid "Unlimited Licenses"
877
  msgstr ""
878
 
879
- #: includes/fs-plugin-info-dialog.php:749
880
  msgid "Up to %s Sites"
881
  msgstr ""
882
 
883
- #: includes/fs-plugin-info-dialog.php:759, templates/plugin-info/features.php:82
884
  msgctxt "as monthly period"
885
  msgid "mo"
886
  msgstr ""
887
 
888
- #: includes/fs-plugin-info-dialog.php:766, templates/plugin-info/features.php:80
889
  msgctxt "as annual period"
890
  msgid "year"
891
  msgstr ""
892
 
893
- #: includes/fs-plugin-info-dialog.php:820
894
  msgctxt "noun"
895
  msgid "Price"
896
  msgstr ""
897
 
898
- #: includes/fs-plugin-info-dialog.php:868
899
  msgid "Save %s"
900
  msgstr ""
901
 
902
- #: includes/fs-plugin-info-dialog.php:878
903
  msgid "No commitment for %s - cancel anytime"
904
  msgstr ""
905
 
906
- #: includes/fs-plugin-info-dialog.php:881
907
  msgid "After your free %s, pay as little as %s"
908
  msgstr ""
909
 
910
- #: includes/fs-plugin-info-dialog.php:892
911
  msgid "Details"
912
  msgstr ""
913
 
914
- #: includes/fs-plugin-info-dialog.php:896, templates/account.php:87, templates/debug.php:191, templates/debug.php:228, templates/debug.php:442, templates/account/partials/addon.php:28
915
  msgctxt "product version"
916
  msgid "Version"
917
  msgstr ""
918
 
919
- #: includes/fs-plugin-info-dialog.php:903
920
  msgctxt "as the plugin author"
921
  msgid "Author"
922
  msgstr ""
923
 
924
- #: includes/fs-plugin-info-dialog.php:910
925
  msgid "Last Updated"
926
  msgstr ""
927
 
928
- #: includes/fs-plugin-info-dialog.php:915, templates/account.php:368
929
  msgctxt "x-ago"
930
  msgid "%s ago"
931
  msgstr ""
932
 
933
- #: includes/fs-plugin-info-dialog.php:924
934
  msgid "Requires WordPress Version"
935
  msgstr ""
936
 
937
- #: includes/fs-plugin-info-dialog.php:925
938
  msgid "%s or higher"
939
  msgstr ""
940
 
941
- #: includes/fs-plugin-info-dialog.php:932
942
  msgid "Compatible up to"
943
  msgstr ""
944
 
945
- #: includes/fs-plugin-info-dialog.php:940
946
  msgid "Downloaded"
947
  msgstr ""
948
 
949
- #: includes/fs-plugin-info-dialog.php:944
950
  msgid "%s time"
951
  msgstr ""
952
 
953
- #: includes/fs-plugin-info-dialog.php:946
954
  msgid "%s times"
955
  msgstr ""
956
 
957
- #: includes/fs-plugin-info-dialog.php:956
958
  msgid "WordPress.org Plugin Page"
959
  msgstr ""
960
 
961
- #: includes/fs-plugin-info-dialog.php:964
962
  msgid "Plugin Homepage"
963
  msgstr ""
964
 
965
- #: includes/fs-plugin-info-dialog.php:972, includes/fs-plugin-info-dialog.php:1054
966
  msgid "Donate to this plugin"
967
  msgstr ""
968
 
969
- #: includes/fs-plugin-info-dialog.php:979
970
  msgid "Average Rating"
971
  msgstr ""
972
 
973
- #: includes/fs-plugin-info-dialog.php:986
974
  msgid "based on %s"
975
  msgstr ""
976
 
977
- #: includes/fs-plugin-info-dialog.php:990
978
  msgid "%s rating"
979
  msgstr ""
980
 
981
- #: includes/fs-plugin-info-dialog.php:992
982
  msgid "%s ratings"
983
  msgstr ""
984
 
985
- #: includes/fs-plugin-info-dialog.php:1007
986
  msgid "%s star"
987
  msgstr ""
988
 
989
- #: includes/fs-plugin-info-dialog.php:1009
990
  msgid "%s stars"
991
  msgstr ""
992
 
993
- #: includes/fs-plugin-info-dialog.php:1020
994
  msgid "Click to see reviews that provided a rating of %s"
995
  msgstr ""
996
 
997
- #: includes/fs-plugin-info-dialog.php:1033
998
  msgid "Contributors"
999
  msgstr ""
1000
 
1001
- #: includes/fs-plugin-info-dialog.php:1062, includes/fs-plugin-info-dialog.php:1064
1002
  msgid "Warning"
1003
  msgstr ""
1004
 
1005
- #: includes/fs-plugin-info-dialog.php:1062
1006
  msgid "This plugin has not been tested with your current version of WordPress."
1007
  msgstr ""
1008
 
1009
- #: includes/fs-plugin-info-dialog.php:1064
1010
  msgid "This plugin has not been marked as compatible with your version of WordPress."
1011
  msgstr ""
1012
 
1013
- #: includes/fs-plugin-info-dialog.php:1083
1014
  msgid "Paid add-on must be deployed to Freemius."
1015
  msgstr ""
1016
 
1017
- #: includes/fs-plugin-info-dialog.php:1084
1018
  msgid "Add-on must be deployed to WordPress.org or Freemius."
1019
  msgstr ""
1020
 
1021
- #: templates/account.php:81, templates/account/partials/addon.php:22, templates/account/partials/site.php:295
1022
- msgid "Downgrading your plan will immediately stop all future recurring payments and your %s plan license will expire in %s."
 
 
 
 
 
 
 
 
 
1023
  msgstr ""
1024
 
1025
- #: templates/account.php:82, templates/account/partials/addon.php:23
 
 
 
 
1026
  msgid "Cancelling the trial will immediately block access to all premium features. Are you sure?"
1027
  msgstr ""
1028
 
1029
- #: templates/account.php:83, templates/account/partials/addon.php:24, templates/account/partials/site.php:296
1030
- msgid "You can still enjoy all %s features but you will not have access to %s updates and support."
1031
  msgstr ""
1032
 
1033
- #: templates/account.php:84, templates/account/partials/addon.php:25, templates/account/partials/site.php:297
1034
  msgid "Once your license expires you can still use the Free version but you will NOT have access to the %s features."
1035
  msgstr ""
1036
 
1037
  #. translators: %s: Plan title (e.g. "Professional")
1038
- #: templates/account.php:86, templates/account/partials/activate-license-button.php:31, templates/account/partials/addon.php:27
1039
  msgid "Activate %s Plan"
1040
  msgstr ""
1041
 
1042
  #. translators: %s: Time period (e.g. Auto renews in "2 months")
1043
- #: templates/account.php:89, templates/account/partials/addon.php:30, templates/account/partials/site.php:275
1044
  msgid "Auto renews in %s"
1045
  msgstr ""
1046
 
1047
  #. translators: %s: Time period (e.g. Expires in "2 months")
1048
- #: templates/account.php:91, templates/account/partials/addon.php:32, templates/account/partials/site.php:277
1049
  msgid "Expires in %s"
1050
  msgstr ""
1051
 
1052
- #: templates/account.php:92, templates/account/partials/addon.php:33
1053
  msgctxt "as synchronize license"
1054
  msgid "Sync License"
1055
  msgstr ""
1056
 
1057
- #: templates/account.php:93, templates/account/partials/addon.php:34
1058
  msgid "Cancel Trial"
1059
  msgstr ""
1060
 
1061
- #: templates/account.php:94, templates/account/partials/addon.php:35
1062
  msgid "Change Plan"
1063
  msgstr ""
1064
 
1065
- #: templates/account.php:95, templates/account/partials/addon.php:36
1066
  msgctxt "verb"
1067
  msgid "Upgrade"
1068
  msgstr ""
1069
 
1070
- #: templates/account.php:97, templates/account/partials/addon.php:38, templates/account/partials/site.php:298
1071
  msgctxt "verb"
1072
  msgid "Downgrade"
1073
  msgstr ""
1074
 
1075
- #: templates/account.php:99, templates/add-ons.php:126, templates/plugin-info/features.php:72, templates/account/partials/addon.php:40, templates/account/partials/site.php:31
1076
  msgid "Free"
1077
  msgstr ""
1078
 
1079
- #: templates/account.php:100, templates/account/partials/addon.php:41
1080
  msgid "Activate"
1081
  msgstr ""
1082
 
1083
- #: templates/account.php:101, templates/debug.php:361, includes/customizer/class-fs-customizer-upsell-control.php:106, templates/account/partials/addon.php:42
1084
  msgctxt "as product pricing plan"
1085
  msgid "Plan"
1086
  msgstr ""
1087
 
1088
- #: templates/account.php:154
1089
  msgid "Free Trial"
1090
  msgstr ""
1091
 
1092
- #: templates/account.php:165
1093
  msgid "Account Details"
1094
  msgstr ""
1095
 
1096
- #: templates/account.php:175
1097
  msgid "Deleting the account will automatically deactivate your %s plan license so you can use it on other sites. If you want to terminate the recurring payments as well, click the \"Cancel\" button, and first \"Downgrade\" your account. Are you sure you would like to continue with the deletion?"
1098
  msgstr ""
1099
 
1100
- #: templates/account.php:177
1101
  msgid "Deletion is not temporary. Only delete if you no longer want to use this %s anymore. Are you sure you would like to continue with the deletion?"
1102
  msgstr ""
1103
 
1104
- #: templates/account.php:180
1105
  msgid "Delete Account"
1106
  msgstr ""
1107
 
1108
- #: templates/account.php:192, templates/account/partials/addon.php:155, templates/account/partials/deactivate-license-button.php:35
1109
  msgid "Deactivate License"
1110
  msgstr ""
1111
 
1112
- #: templates/account.php:210
1113
  msgid "Are you sure you want to proceed?"
1114
  msgstr ""
1115
 
1116
- #: templates/account.php:210, templates/account/partials/addon.php:177
1117
  msgid "Cancel Subscription"
1118
  msgstr ""
1119
 
1120
- #: templates/account.php:239
1121
  msgctxt "as synchronize"
1122
  msgid "Sync"
1123
  msgstr ""
1124
 
1125
- #: templates/account.php:253, templates/debug.php:477
1126
  msgid "Name"
1127
  msgstr ""
1128
 
1129
- #: templates/account.php:259, templates/debug.php:478
1130
  msgid "Email"
1131
  msgstr ""
1132
 
1133
- #: templates/account.php:266, templates/debug.php:360, templates/debug.php:516
1134
  msgid "User ID"
1135
  msgstr ""
1136
 
1137
- #: templates/account.php:274
1138
  msgid "Site ID"
1139
  msgstr ""
1140
 
1141
- #: templates/account.php:277
1142
  msgid "No ID"
1143
  msgstr ""
1144
 
1145
- #: templates/account.php:282, templates/debug.php:233, templates/debug.php:362, templates/debug.php:443, templates/debug.php:480, templates/account/partials/site.php:219
1146
  msgid "Public Key"
1147
  msgstr ""
1148
 
1149
- #: templates/account.php:288, templates/debug.php:363, templates/debug.php:444, templates/debug.php:481, templates/account/partials/site.php:231
1150
  msgid "Secret Key"
1151
  msgstr ""
1152
 
1153
- #: templates/account.php:291
1154
  msgctxt "as secret encryption key missing"
1155
  msgid "No Secret"
1156
  msgstr ""
1157
 
1158
- #: templates/account.php:310, templates/account/partials/site.php:112, templates/account/partials/site.php:114
1159
  msgid "Trial"
1160
  msgstr ""
1161
 
1162
- #: templates/account.php:329, templates/debug.php:521, templates/account/partials/site.php:248
1163
  msgid "License Key"
1164
  msgstr ""
1165
 
1166
- #: templates/account.php:359
1167
  msgid "not verified"
1168
  msgstr ""
1169
 
1170
- #: templates/account.php:368, templates/account/partials/addon.php:116
1171
  msgid "Expired"
1172
  msgstr ""
1173
 
1174
- #: templates/account.php:420
1175
  msgid "Premium version"
1176
  msgstr ""
1177
 
1178
- #: templates/account.php:422
1179
  msgid "Free version"
1180
  msgstr ""
1181
 
1182
- #: templates/account.php:434
1183
  msgid "Verify Email"
1184
  msgstr ""
1185
 
1186
- #: templates/account.php:445
1187
  msgid "Download %s Version"
1188
  msgstr ""
1189
 
1190
- #: templates/account.php:459, templates/account.php:640, templates/account/partials/site.php:237, templates/account/partials/site.php:255
1191
  msgctxt "verb"
1192
  msgid "Show"
1193
  msgstr ""
1194
 
1195
- #: templates/account.php:473
1196
  msgid "What is your %s?"
1197
  msgstr ""
1198
 
1199
- #: templates/account.php:481, templates/account/billing.php:27
1200
  msgctxt "verb"
1201
  msgid "Edit"
1202
  msgstr ""
1203
 
1204
- #: templates/account.php:494
1205
  msgid "Sites"
1206
  msgstr ""
1207
 
1208
- #: templates/account.php:505
1209
  msgid "Search by address"
1210
  msgstr ""
1211
 
1212
- #: templates/account.php:514, templates/account.php:562, templates/debug.php:226, templates/debug.php:354, templates/debug.php:439, templates/debug.php:476, templates/debug.php:514, templates/debug.php:587, templates/account/payments.php:35, templates/debug/logger.php:21
1213
  msgid "ID"
1214
  msgstr ""
1215
 
1216
- #: templates/account.php:515, templates/debug.php:357
1217
  msgid "Address"
1218
  msgstr ""
1219
 
1220
- #: templates/account.php:516
1221
  msgid "License"
1222
  msgstr ""
1223
 
1224
- #: templates/account.php:517
1225
  msgid "Plan"
1226
  msgstr ""
1227
 
1228
- #: templates/account.php:565
1229
  msgctxt "as software license"
1230
  msgid "License"
1231
  msgstr ""
1232
 
1233
- #: templates/account.php:634
1234
  msgctxt "verb"
1235
  msgid "Hide"
1236
  msgstr ""
1237
 
1238
- #: templates/account.php:669
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1239
  msgid "Deactivating your license will block all premium features, but will enable activating the license on another site. Are you sure you want to proceed?"
1240
  msgstr ""
1241
 
@@ -1247,7 +1322,7 @@ msgstr ""
1247
  msgid "We could'nt load the add-ons list. It's probably an issue on our side, please try to come back in few minutes."
1248
  msgstr ""
1249
 
1250
- #: templates/add-ons.php:135
1251
  msgid "View details"
1252
  msgstr ""
1253
 
@@ -1285,162 +1360,166 @@ msgid "PCI compliant"
1285
  msgstr ""
1286
 
1287
  #. translators: %s: name (e.g. Hey John,)
1288
- #: templates/connect.php:110
1289
  msgctxt "greeting"
1290
  msgid "Hey %s,"
1291
  msgstr ""
1292
 
1293
- #: templates/connect.php:152
1294
  msgid "Allow & Continue"
1295
  msgstr ""
1296
 
1297
- #: templates/connect.php:156
1298
  msgid "Re-send activation email"
1299
  msgstr ""
1300
 
1301
- #: templates/connect.php:160
1302
  msgid "Thanks %s!"
1303
  msgstr ""
1304
 
1305
- #: templates/connect.php:170, templates/forms/license-activation.php:43
1306
  msgid "Agree & Activate License"
1307
  msgstr ""
1308
 
1309
- #: templates/connect.php:179
1310
  msgid "Thanks for purchasing %s! To get started, please enter your license key:"
1311
  msgstr ""
1312
 
1313
- #: templates/connect.php:186
1314
  msgid "Never miss an important update - opt in to our security & feature updates notifications, educational content, offers, and non-sensitive diagnostic tracking with %4$s."
1315
  msgstr ""
1316
 
1317
- #: templates/connect.php:187
1318
  msgid "Never miss an important update - opt in to our security and feature updates notifications, and non-sensitive diagnostic tracking with %4$s."
1319
  msgstr ""
1320
 
1321
- #: templates/connect.php:193
1322
  msgid "Never miss an important update - opt in to our security & feature updates notifications, educational content, offers, and non-sensitive diagnostic tracking with %4$s. If you skip this, that's okay! %1$s will still work just fine."
1323
  msgstr ""
1324
 
1325
- #: templates/connect.php:194
1326
  msgid "Never miss an important update - opt in to our security & feature updates notifications, and non-sensitive diagnostic tracking with %4$s. If you skip this, that's okay! %1$s will still work just fine."
1327
  msgstr ""
1328
 
1329
- #: templates/connect.php:228
1330
  msgid "We're excited to introduce the Freemius network-level integration."
1331
  msgstr ""
1332
 
1333
- #: templates/connect.php:231
1334
  msgid "During the update process we detected %d site(s) that are still pending license activation."
1335
  msgstr ""
1336
 
1337
- #: templates/connect.php:233
1338
  msgid "If you'd like to use the %s on those sites, please enter your license key below and click the activation button."
1339
  msgstr ""
1340
 
1341
- #: templates/connect.php:235
1342
  msgid "%s's paid features"
1343
  msgstr ""
1344
 
1345
- #: templates/connect.php:240
1346
  msgid "Alternatively, you can skip it for now and activate the license later, in your %s's network-level Account page."
1347
  msgstr ""
1348
 
1349
- #: templates/connect.php:242
1350
  msgid "During the update process we detected %s site(s) in the network that are still pending your attention."
1351
  msgstr ""
1352
 
1353
- #: templates/connect.php:251, templates/forms/license-activation.php:46
1354
  msgid "License key"
1355
  msgstr ""
1356
 
1357
- #: templates/connect.php:254, templates/forms/license-activation.php:19
1358
  msgid "Can't find your license key?"
1359
  msgstr ""
1360
 
1361
- #: templates/connect.php:302, templates/connect.php:617, templates/forms/deactivation/retry-skip.php:20
1362
  msgctxt "verb"
1363
  msgid "Skip"
1364
  msgstr ""
1365
 
1366
- #: templates/connect.php:305
1367
  msgid "Delegate to Site Admins"
1368
  msgstr ""
1369
 
1370
- #: templates/connect.php:305
1371
  msgid "If you click it, this decision will be delegated to the sites administrators."
1372
  msgstr ""
1373
 
1374
- #: templates/connect.php:333
1375
  msgid "Your Profile Overview"
1376
  msgstr ""
1377
 
1378
- #: templates/connect.php:334
1379
  msgid "Name and email address"
1380
  msgstr ""
1381
 
1382
- #: templates/connect.php:339
1383
  msgid "Your Site Overview"
1384
  msgstr ""
1385
 
1386
- #: templates/connect.php:340
1387
  msgid "Site URL, WP version, PHP info, plugins & themes"
1388
  msgstr ""
1389
 
1390
- #: templates/connect.php:345
1391
  msgid "Admin Notices"
1392
  msgstr ""
1393
 
1394
- #: templates/connect.php:346, templates/connect.php:362
1395
  msgid "Updates, announcements, marketing, no spam"
1396
  msgstr ""
1397
 
1398
- #: templates/connect.php:351
1399
  msgid "Current %s Events"
1400
  msgstr ""
1401
 
1402
- #: templates/connect.php:352
1403
  msgid "Activation, deactivation and uninstall"
1404
  msgstr ""
1405
 
1406
- #: templates/connect.php:361
1407
  msgid "Newsletter"
1408
  msgstr ""
1409
 
1410
- #: templates/connect.php:378, templates/forms/license-activation.php:38
1411
  msgid "The %1$s will be periodically sending data to %2$s to check for security and feature updates, and verify the validity of your license."
1412
  msgstr ""
1413
 
1414
- #: templates/connect.php:383
1415
  msgid "What permissions are being granted?"
1416
  msgstr ""
1417
 
1418
- #: templates/connect.php:404
1419
  msgid "Don't have a license key?"
1420
  msgstr ""
1421
 
1422
- #: templates/connect.php:405
1423
  msgid "Activate Free Version"
1424
  msgstr ""
1425
 
1426
- #: templates/connect.php:407
1427
  msgid "Have a license key?"
1428
  msgstr ""
1429
 
1430
- #: templates/connect.php:415
1431
  msgid "Privacy Policy"
1432
  msgstr ""
1433
 
1434
- #: templates/connect.php:417
 
 
 
 
1435
  msgid "Terms of Service"
1436
  msgstr ""
1437
 
1438
- #: templates/connect.php:750
1439
  msgctxt "as in the process of sending an email"
1440
  msgid "Sending email"
1441
  msgstr ""
1442
 
1443
- #: templates/connect.php:751
1444
  msgctxt "as activating plugin"
1445
  msgid "Activating"
1446
  msgstr ""
@@ -1468,7 +1547,7 @@ msgctxt "as code debugging"
1468
  msgid "Debugging"
1469
  msgstr ""
1470
 
1471
- #: templates/debug.php:54, templates/debug.php:238, templates/debug.php:364, templates/debug.php:482
1472
  msgid "Actions"
1473
  msgstr ""
1474
 
@@ -1492,194 +1571,198 @@ msgstr ""
1492
  msgid "Sync Data From Server"
1493
  msgstr ""
1494
 
1495
- #: templates/debug.php:90
 
 
 
 
1496
  msgid "Load DB Option"
1497
  msgstr ""
1498
 
1499
- #: templates/debug.php:93
1500
  msgid "Set DB Option"
1501
  msgstr ""
1502
 
1503
- #: templates/debug.php:170
1504
  msgid "Key"
1505
  msgstr ""
1506
 
1507
- #: templates/debug.php:171
1508
  msgid "Value"
1509
  msgstr ""
1510
 
1511
- #: templates/debug.php:187
1512
  msgctxt "as software development kit versions"
1513
  msgid "SDK Versions"
1514
  msgstr ""
1515
 
1516
- #: templates/debug.php:192
1517
  msgid "SDK Path"
1518
  msgstr ""
1519
 
1520
- #: templates/debug.php:193, templates/debug.php:232
1521
  msgid "Module Path"
1522
  msgstr ""
1523
 
1524
- #: templates/debug.php:194
1525
  msgid "Is Active"
1526
  msgstr ""
1527
 
1528
- #: templates/debug.php:222, templates/debug/plugins-themes-sync.php:35
1529
  msgid "Plugins"
1530
  msgstr ""
1531
 
1532
- #: templates/debug.php:222, templates/debug/plugins-themes-sync.php:56
1533
  msgid "Themes"
1534
  msgstr ""
1535
 
1536
- #: templates/debug.php:227, templates/debug.php:359, templates/debug.php:441, templates/debug/scheduled-crons.php:80
1537
  msgid "Slug"
1538
  msgstr ""
1539
 
1540
- #: templates/debug.php:229, templates/debug.php:440
1541
  msgid "Title"
1542
  msgstr ""
1543
 
1544
- #: templates/debug.php:230
1545
  msgctxt "as application program interface"
1546
  msgid "API"
1547
  msgstr ""
1548
 
1549
- #: templates/debug.php:231
1550
  msgid "Freemius State"
1551
  msgstr ""
1552
 
1553
- #: templates/debug.php:235
1554
  msgid "Network Blog"
1555
  msgstr ""
1556
 
1557
- #: templates/debug.php:236
1558
  msgid "Network User"
1559
  msgstr ""
1560
 
1561
- #: templates/debug.php:273
1562
  msgctxt "as connection was successful"
1563
  msgid "Connected"
1564
  msgstr ""
1565
 
1566
- #: templates/debug.php:274
1567
  msgctxt "as connection blocked"
1568
  msgid "Blocked"
1569
  msgstr ""
1570
 
1571
- #: templates/debug.php:310
1572
- msgid "Simulate Trial"
1573
  msgstr ""
1574
 
1575
- #: templates/debug.php:322
1576
  msgid "Simulate Network Upgrade"
1577
  msgstr ""
1578
 
1579
- #: templates/debug.php:348
1580
  msgid "%s Installs"
1581
  msgstr ""
1582
 
1583
- #: templates/debug.php:350
1584
  msgctxt "like websites"
1585
  msgid "Sites"
1586
  msgstr ""
1587
 
1588
- #: templates/debug.php:356, templates/account/partials/site.php:148
1589
  msgid "Blog ID"
1590
  msgstr ""
1591
 
1592
- #: templates/debug.php:421, templates/debug.php:499, templates/account/partials/addon.php:334
1593
  msgctxt "verb"
1594
  msgid "Delete"
1595
  msgstr ""
1596
 
1597
- #: templates/debug.php:435
1598
  msgid "Add Ons of module %s"
1599
  msgstr ""
1600
 
1601
- #: templates/debug.php:472
1602
  msgid "Users"
1603
  msgstr ""
1604
 
1605
- #: templates/debug.php:479
1606
  msgid "Verified"
1607
  msgstr ""
1608
 
1609
- #: templates/debug.php:510
1610
  msgid "%s Licenses"
1611
  msgstr ""
1612
 
1613
- #: templates/debug.php:515
1614
  msgid "Plugin ID"
1615
  msgstr ""
1616
 
1617
- #: templates/debug.php:517
1618
  msgid "Plan ID"
1619
  msgstr ""
1620
 
1621
- #: templates/debug.php:518
1622
  msgid "Quota"
1623
  msgstr ""
1624
 
1625
- #: templates/debug.php:519
1626
  msgid "Activated"
1627
  msgstr ""
1628
 
1629
- #: templates/debug.php:520
1630
  msgid "Blocking"
1631
  msgstr ""
1632
 
1633
- #: templates/debug.php:522
1634
  msgctxt "as expiration date"
1635
  msgid "Expiration"
1636
  msgstr ""
1637
 
1638
- #: templates/debug.php:545
1639
  msgid "Debug Log"
1640
  msgstr ""
1641
 
1642
- #: templates/debug.php:549
1643
  msgid "All Types"
1644
  msgstr ""
1645
 
1646
- #: templates/debug.php:556
1647
  msgid "All Requests"
1648
  msgstr ""
1649
 
1650
- #: templates/debug.php:561, templates/debug.php:590, templates/debug/logger.php:25
1651
  msgid "File"
1652
  msgstr ""
1653
 
1654
- #: templates/debug.php:562, templates/debug.php:588, templates/debug/logger.php:23
1655
  msgid "Function"
1656
  msgstr ""
1657
 
1658
- #: templates/debug.php:563
1659
  msgid "Process ID"
1660
  msgstr ""
1661
 
1662
- #: templates/debug.php:564
1663
  msgid "Logger"
1664
  msgstr ""
1665
 
1666
- #: templates/debug.php:565, templates/debug.php:589, templates/debug/logger.php:24
1667
  msgid "Message"
1668
  msgstr ""
1669
 
1670
- #: templates/debug.php:567
1671
  msgid "Filter"
1672
  msgstr ""
1673
 
1674
- #: templates/debug.php:575
1675
  msgid "Download"
1676
  msgstr ""
1677
 
1678
- #: templates/debug.php:586, templates/debug/logger.php:22
1679
  msgid "Type"
1680
  msgstr ""
1681
 
1682
- #: templates/debug.php:591, templates/debug/logger.php:26
1683
  msgid "Timestamp"
1684
  msgstr ""
1685
 
@@ -2023,23 +2106,19 @@ msgstr ""
2023
  msgid "By clicking \"Opt Out\", we will no longer be sending any data from %s to %s."
2024
  msgstr ""
2025
 
2026
- #: templates/forms/premium-versions-upgrade-handler.php:24
2027
  msgid "There is a new version of %s available."
2028
  msgstr ""
2029
 
2030
- #: templates/forms/premium-versions-upgrade-handler.php:25
2031
- msgid " %sRenew your license now%s to access version %s security & feature updates, and support."
2032
  msgstr ""
2033
 
2034
- #: templates/forms/premium-versions-upgrade-handler.php:34
2035
  msgid "New Version Available"
2036
  msgstr ""
2037
 
2038
- #: templates/forms/premium-versions-upgrade-handler.php:36
2039
- msgid "Renew license"
2040
- msgstr ""
2041
-
2042
- #: templates/forms/premium-versions-upgrade-handler.php:53
2043
  msgctxt "close a window"
2044
  msgid "Dismiss"
2045
  msgstr ""
@@ -2052,6 +2131,42 @@ msgstr ""
2052
  msgid "Enter the email address you've used for the upgrade below and we will resend you the license key."
2053
  msgstr ""
2054
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2055
  #: templates/forms/trial-start.php:22
2056
  msgid "You are 1-click away from starting your %1$s-day free trial of the %2$s plan."
2057
  msgstr ""
@@ -2113,15 +2228,15 @@ msgstr ""
2113
  msgid "Last license"
2114
  msgstr ""
2115
 
2116
- #: templates/account/partials/addon.php:111
2117
  msgid "Cancelled"
2118
  msgstr ""
2119
 
2120
- #: templates/account/partials/addon.php:121
2121
  msgid "No expiration"
2122
  msgstr ""
2123
 
2124
- #: templates/account/partials/addon.php:259, templates/account/partials/addon.php:312
2125
  msgid "Activate this add-on"
2126
  msgstr ""
2127
 
@@ -2149,47 +2264,47 @@ msgstr ""
2149
  msgid "Contact Support"
2150
  msgstr ""
2151
 
2152
- #: templates/forms/deactivation/form.php:56
2153
  msgid "Anonymous feedback"
2154
  msgstr ""
2155
 
2156
- #: templates/forms/deactivation/form.php:63
2157
  msgid "Deactivate"
2158
  msgstr ""
2159
 
2160
- #: templates/forms/deactivation/form.php:65
2161
  msgid "Activate %s"
2162
  msgstr ""
2163
 
2164
- #: templates/forms/deactivation/form.php:76
2165
- msgid "Quick feedback"
2166
  msgstr ""
2167
 
2168
- #: templates/forms/deactivation/form.php:80
2169
  msgid "If you have a moment, please let us know why you are %s"
2170
  msgstr ""
2171
 
2172
- #: templates/forms/deactivation/form.php:80
2173
  msgid "deactivating"
2174
  msgstr ""
2175
 
2176
- #: templates/forms/deactivation/form.php:80
2177
  msgid "switching"
2178
  msgstr ""
2179
 
2180
- #: templates/forms/deactivation/form.php:269
2181
  msgid "Submit & %s"
2182
  msgstr ""
2183
 
2184
- #: templates/forms/deactivation/form.php:290
2185
  msgid "Kindly tell us the reason so we can improve."
2186
  msgstr ""
2187
 
2188
- #: templates/forms/deactivation/form.php:411
2189
  msgid "Yes - %s"
2190
  msgstr ""
2191
 
2192
- #: templates/forms/deactivation/form.php:418
2193
  msgid "Skip & %s"
2194
  msgstr ""
2195
 
1
+ # Copyright (C) 2019 freemius
2
  # This file is distributed under the same license as the freemius package.
3
  msgid ""
4
  msgstr ""
16
  "X-Poedit-SourceCharset: UTF-8\n"
17
  "Plural-Forms: nplurals=2; plural=(n != 1);\n"
18
 
19
+ #: includes/class-freemius.php:1688
20
  msgid "Freemius SDK couldn't find the plugin's main file. Please contact sdk@freemius.com with the current error."
21
  msgstr ""
22
 
23
+ #: includes/class-freemius.php:1690
24
  msgid "Error"
25
  msgstr ""
26
 
27
+ #: includes/class-freemius.php:2011
28
  msgid "I found a better %s"
29
  msgstr ""
30
 
31
+ #: includes/class-freemius.php:2013
32
  msgid "What's the %s's name?"
33
  msgstr ""
34
 
35
+ #: includes/class-freemius.php:2019
36
  msgid "It's a temporary %s. I'm just debugging an issue."
37
  msgstr ""
38
 
39
+ #: includes/class-freemius.php:2021
40
  msgid "Deactivation"
41
  msgstr ""
42
 
43
+ #: includes/class-freemius.php:2022
44
  msgid "Theme Switch"
45
  msgstr ""
46
 
47
+ #: includes/class-freemius.php:2031, templates/forms/resend-key.php:24
48
  msgid "Other"
49
  msgstr ""
50
 
51
+ #: includes/class-freemius.php:2039
52
  msgid "I no longer need the %s"
53
  msgstr ""
54
 
55
+ #: includes/class-freemius.php:2046
56
  msgid "I only needed the %s for a short period"
57
  msgstr ""
58
 
59
+ #: includes/class-freemius.php:2052
60
  msgid "The %s broke my site"
61
  msgstr ""
62
 
63
+ #: includes/class-freemius.php:2059
64
  msgid "The %s suddenly stopped working"
65
  msgstr ""
66
 
67
+ #: includes/class-freemius.php:2069
68
  msgid "I can't pay for it anymore"
69
  msgstr ""
70
 
71
+ #: includes/class-freemius.php:2071
72
  msgid "What price would you feel comfortable paying?"
73
  msgstr ""
74
 
75
+ #: includes/class-freemius.php:2077
76
  msgid "I don't like to share my information with you"
77
  msgstr ""
78
 
79
+ #: includes/class-freemius.php:2098
80
  msgid "The %s didn't work"
81
  msgstr ""
82
 
83
+ #: includes/class-freemius.php:2108
84
  msgid "I couldn't understand how to make it work"
85
  msgstr ""
86
 
87
+ #: includes/class-freemius.php:2116
88
  msgid "The %s is great, but I need specific feature that you don't support"
89
  msgstr ""
90
 
91
+ #: includes/class-freemius.php:2118
92
  msgid "What feature?"
93
  msgstr ""
94
 
95
+ #: includes/class-freemius.php:2122
96
  msgid "The %s is not working"
97
  msgstr ""
98
 
99
+ #: includes/class-freemius.php:2124
100
  msgid "Kindly share what didn't work so we can fix it for future users..."
101
  msgstr ""
102
 
103
+ #: includes/class-freemius.php:2128
104
  msgid "It's not what I was looking for"
105
  msgstr ""
106
 
107
+ #: includes/class-freemius.php:2130
108
  msgid "What you've been looking for?"
109
  msgstr ""
110
 
111
+ #: includes/class-freemius.php:2134
112
  msgid "The %s didn't work as expected"
113
  msgstr ""
114
 
115
+ #: includes/class-freemius.php:2136
116
  msgid "What did you expect?"
117
  msgstr ""
118
 
119
+ #: includes/class-freemius.php:2947, templates/debug.php:20
120
  msgid "Freemius Debug"
121
  msgstr ""
122
 
123
+ #: includes/class-freemius.php:3675
124
  msgid "I don't know what is cURL or how to install it, help me!"
125
  msgstr ""
126
 
127
+ #: includes/class-freemius.php:3677
128
  msgid "We'll make sure to contact your hosting company and resolve the issue. You will get a follow-up email to %s once we have an update."
129
  msgstr ""
130
 
131
+ #: includes/class-freemius.php:3684
132
  msgid "Great, please install cURL and enable it in your php.ini file. In addition, search for the 'disable_functions' directive in your php.ini file and remove any disabled methods starting with 'curl_'. To make sure it was successfully activated, use 'phpinfo()'. Once activated, deactivate the %s and reactivate it back again."
133
  msgstr ""
134
 
135
+ #: includes/class-freemius.php:3789
136
  msgid "Yes - do your thing"
137
  msgstr ""
138
 
139
+ #: includes/class-freemius.php:3794
140
  msgid "No - just deactivate"
141
  msgstr ""
142
 
143
+ #: includes/class-freemius.php:3839, includes/class-freemius.php:4348, includes/class-freemius.php:5447, includes/class-freemius.php:11555, includes/class-freemius.php:14926, includes/class-freemius.php:14978, includes/class-freemius.php:15040, includes/class-freemius.php:17273, includes/class-freemius.php:17283, includes/class-freemius.php:17892, includes/class-freemius.php:18752, includes/class-freemius.php:18867, includes/class-freemius.php:19011, templates/add-ons.php:43
144
  msgctxt "exclamation"
145
  msgid "Oops"
146
  msgstr ""
147
 
148
+ #: includes/class-freemius.php:3908
149
  msgid "Thank for giving us the chance to fix it! A message was just sent to our technical staff. We will get back to you as soon as we have an update to %s. Appreciate your patience."
150
  msgstr ""
151
 
152
+ #: includes/class-freemius.php:4345
153
  msgctxt "addonX cannot run without pluginY"
154
  msgid "%s cannot run without %s."
155
  msgstr ""
156
 
157
+ #: includes/class-freemius.php:4346
158
  msgctxt "addonX cannot run..."
159
  msgid "%s cannot run without the plugin."
160
  msgstr ""
161
 
162
+ #: includes/class-freemius.php:4492, includes/class-freemius.php:4517, includes/class-freemius.php:17963
163
  msgid "Unexpected API error. Please contact the %s's author with the following error."
164
  msgstr ""
165
 
166
+ #: includes/class-freemius.php:5135
167
  msgid "Premium %s version was successfully activated."
168
  msgstr ""
169
 
170
+ #: includes/class-freemius.php:5147, includes/class-freemius.php:7009
171
  msgctxt "Used to express elation, enthusiasm, or triumph (especially in electronic communication)."
172
  msgid "W00t"
173
  msgstr ""
174
 
175
+ #: includes/class-freemius.php:5162
176
  msgid "You have a %s license."
177
  msgstr ""
178
 
179
+ #: includes/class-freemius.php:5166, includes/class-freemius.php:14347, includes/class-freemius.php:14358, includes/class-freemius.php:17187, includes/class-freemius.php:17501, includes/class-freemius.php:17567, includes/class-freemius.php:17717
180
  msgctxt "interjection expressing joy or exuberance"
181
  msgid "Yee-haw"
182
  msgstr ""
183
 
184
+ #: includes/class-freemius.php:5430
185
  msgid "%s free trial was successfully cancelled. Since the add-on is premium only it was automatically deactivated. If you like to use it in the future, you'll have to purchase a license."
186
  msgstr ""
187
 
188
+ #: includes/class-freemius.php:5434
189
  msgid "%s is a premium only add-on. You have to purchase a license first before activating the plugin."
190
  msgstr ""
191
 
192
+ #: includes/class-freemius.php:5443, templates/add-ons.php:103, templates/account/partials/addon.php:288
193
  msgid "More information about %s"
194
  msgstr ""
195
 
196
+ #: includes/class-freemius.php:5444
197
  msgid "Purchase License"
198
  msgstr ""
199
 
200
+ #: includes/class-freemius.php:6377, templates/connect.php:163
201
  msgid "You should receive an activation email for %s to your mailbox at %s. Please make sure you click the activation button in that email to %s."
202
  msgstr ""
203
 
204
+ #: includes/class-freemius.php:6381
205
  msgid "start the trial"
206
  msgstr ""
207
 
208
+ #: includes/class-freemius.php:6382, templates/connect.php:167
209
  msgid "complete the install"
210
  msgstr ""
211
 
212
+ #: includes/class-freemius.php:6495
213
  msgid "You are just one step away - %s"
214
  msgstr ""
215
 
216
+ #: includes/class-freemius.php:6498
217
  msgctxt "%s - plugin name. As complete \"PluginX\" activation now"
218
  msgid "Complete \"%s\" Activation Now"
219
  msgstr ""
220
 
221
+ #: includes/class-freemius.php:6576
222
  msgid "We made a few tweaks to the %s, %s"
223
  msgstr ""
224
 
225
+ #: includes/class-freemius.php:6580
226
+ msgid "Opt in to make \"%s\" better!"
227
  msgstr ""
228
 
229
+ #: includes/class-freemius.php:7008
230
  msgid "The upgrade of %s was successfully completed."
231
  msgstr ""
232
 
233
+ #: includes/class-freemius.php:8935, includes/class-fs-plugin-updater.php:886, includes/class-fs-plugin-updater.php:1081, includes/class-fs-plugin-updater.php:1088, templates/auto-installation.php:32
234
  msgid "Add-On"
235
  msgstr ""
236
 
237
+ #: includes/class-freemius.php:8937, templates/debug.php:359, templates/debug.php:520
238
  msgid "Plugin"
239
  msgstr ""
240
 
241
+ #: includes/class-freemius.php:8938, templates/debug.php:359, templates/debug.php:520, templates/forms/deactivation/form.php:67
242
  msgid "Theme"
243
  msgstr ""
244
 
245
+ #: includes/class-freemius.php:11422
246
  msgid "Invalid site details collection."
247
  msgstr ""
248
 
249
+ #: includes/class-freemius.php:11542
250
  msgid "We couldn't find your email address in the system, are you sure it's the right address?"
251
  msgstr ""
252
 
253
+ #: includes/class-freemius.php:11544
254
  msgid "We can't see any active licenses associated with that email address, are you sure it's the right address?"
255
  msgstr ""
256
 
257
+ #: includes/class-freemius.php:11818
258
  msgid "Account is pending activation."
259
  msgstr ""
260
 
261
+ #: includes/class-freemius.php:11930, templates/forms/premium-versions-upgrade-handler.php:47
262
+ msgid "Buy a license now"
263
+ msgstr ""
264
+
265
+ #: includes/class-freemius.php:11942, templates/forms/premium-versions-upgrade-handler.php:46
266
+ msgid "Renew your license now"
267
+ msgstr ""
268
+
269
+ #: includes/class-freemius.php:11946
270
+ msgid "%s to access version %s security & feature updates, and support."
271
+ msgstr ""
272
+
273
+ #: includes/class-freemius.php:14329
274
  msgid "%s activation was successfully completed."
275
  msgstr ""
276
 
277
+ #: includes/class-freemius.php:14343
278
  msgid "Your account was successfully activated with the %s plan."
279
  msgstr ""
280
 
281
+ #: includes/class-freemius.php:14354, includes/class-freemius.php:17563
282
  msgid "Your trial has been successfully started."
283
  msgstr ""
284
 
285
+ #: includes/class-freemius.php:14924, includes/class-freemius.php:14976, includes/class-freemius.php:15038
286
  msgid "Couldn't activate %s."
287
  msgstr ""
288
 
289
+ #: includes/class-freemius.php:14925, includes/class-freemius.php:14977, includes/class-freemius.php:15039
290
  msgid "Please contact us with the following message:"
291
  msgstr ""
292
 
293
+ #: includes/class-freemius.php:15388, includes/class-freemius.php:19849
294
  msgid "Upgrade"
295
  msgstr ""
296
 
297
+ #: includes/class-freemius.php:15394
298
  msgid "Start Trial"
299
  msgstr ""
300
 
301
+ #: includes/class-freemius.php:15396
302
  msgid "Pricing"
303
  msgstr ""
304
 
305
+ #: includes/class-freemius.php:15458, includes/class-freemius.php:15460
306
  msgid "Affiliation"
307
  msgstr ""
308
 
309
+ #: includes/class-freemius.php:15488, includes/class-freemius.php:15490, templates/account.php:150, templates/debug.php:324
310
  msgid "Account"
311
  msgstr ""
312
 
313
+ #: includes/class-freemius.php:15503, includes/class-freemius.php:15505, includes/customizer/class-fs-customizer-support-section.php:60
314
  msgid "Contact Us"
315
  msgstr ""
316
 
317
+ #: includes/class-freemius.php:15515, includes/class-freemius.php:15517, includes/class-freemius.php:19859, templates/account.php:100, templates/account/partials/addon.php:41
318
  msgid "Add-Ons"
319
  msgstr ""
320
 
321
+ #: includes/class-freemius.php:15551
322
+ msgctxt "ASCII arrow left icon"
323
+ msgid "&#x2190;"
324
+ msgstr ""
325
+
326
+ #: includes/class-freemius.php:15551
327
+ msgctxt "ASCII arrow right icon"
328
+ msgid "&#x27a4;"
329
+ msgstr ""
330
+
331
+ #: includes/class-freemius.php:15553, templates/pricing.php:97
332
  msgctxt "noun"
333
  msgid "Pricing"
334
  msgstr ""
335
 
336
+ #: includes/class-freemius.php:15766, includes/customizer/class-fs-customizer-support-section.php:67
337
  msgid "Support Forum"
338
  msgstr ""
339
 
340
+ #: includes/class-freemius.php:16552
341
  msgid "Your email has been successfully verified - you are AWESOME!"
342
  msgstr ""
343
 
344
+ #: includes/class-freemius.php:16553
345
  msgctxt "a positive response"
346
  msgid "Right on"
347
  msgstr ""
348
 
349
+ #: includes/class-freemius.php:17178
350
  msgid "Your %s Add-on plan was successfully upgraded."
351
  msgstr ""
352
 
353
+ #: includes/class-freemius.php:17180
354
  msgid "%s Add-on was successfully purchased."
355
  msgstr ""
356
 
357
+ #: includes/class-freemius.php:17183
358
  msgid "Download the latest version"
359
  msgstr ""
360
 
361
+ #: includes/class-freemius.php:17269
362
  msgctxt "%1s - plugin title, %2s - API domain"
363
  msgid "Your server is blocking the access to Freemius' API, which is crucial for %1s synchronization. Please contact your host to whitelist %2s"
364
  msgstr ""
365
 
366
+ #: includes/class-freemius.php:17272, includes/class-freemius.php:17688, includes/class-freemius.php:17765
367
  msgid "Error received from the server:"
368
  msgstr ""
369
 
370
+ #: includes/class-freemius.php:17282
371
  msgid "It seems like one of the authentication parameters is wrong. Update your Public Key, Secret Key & User ID, and try again."
372
  msgstr ""
373
 
374
+ #: includes/class-freemius.php:17464, includes/class-freemius.php:17693, includes/class-freemius.php:17736, includes/class-freemius.php:17839
375
  msgctxt "something somebody says when they are thinking about what you have just said."
376
  msgid "Hmm"
377
  msgstr ""
378
 
379
+ #: includes/class-freemius.php:17477
380
  msgid "It looks like you are still on the %s plan. If you did upgrade or change your plan, it's probably an issue on our side - sorry."
381
  msgstr ""
382
 
383
+ #: includes/class-freemius.php:17478, templates/account.php:102, templates/add-ons.php:134, templates/account/partials/addon.php:43
384
  msgctxt "trial period"
385
  msgid "Trial"
386
  msgstr ""
387
 
388
+ #: includes/class-freemius.php:17483
389
  msgid "I have upgraded my account but when I try to Sync the License, the plan remains %s."
390
  msgstr ""
391
 
392
+ #: includes/class-freemius.php:17487, includes/class-freemius.php:17545
393
  msgid "Please contact us here"
394
  msgstr ""
395
 
396
+ #: includes/class-freemius.php:17497
397
  msgid "Your plan was successfully upgraded."
398
  msgstr ""
399
 
400
+ #: includes/class-freemius.php:17515
401
  msgid "Your plan was successfully changed to %s."
402
  msgstr ""
403
 
404
+ #: includes/class-freemius.php:17531
405
  msgid "Your license has expired. You can still continue using the free %s forever."
406
  msgstr ""
407
 
408
+ #: includes/class-freemius.php:17533
409
  msgid "Your license has expired. %1$sUpgrade now%2$s to continue using the %3$s without interruptions."
410
  msgstr ""
411
 
412
+ #: includes/class-freemius.php:17541
413
  msgid "Your license has been cancelled. If you think it's a mistake, please contact support."
414
  msgstr ""
415
 
416
+ #: includes/class-freemius.php:17554
417
  msgid "Your license has expired. You can still continue using all the %s features, but you'll need to renew your license to continue getting updates and support."
418
  msgstr ""
419
 
420
+ #: includes/class-freemius.php:17577
421
  msgid "Your free trial has expired. You can still continue using all our free features."
422
  msgstr ""
423
 
424
+ #: includes/class-freemius.php:17579
425
  msgid "Your free trial has expired. %1$sUpgrade now%2$s to continue using the %3$s without interruptions."
426
  msgstr ""
427
 
428
+ #: includes/class-freemius.php:17684
429
  msgid "It looks like the license could not be activated."
430
  msgstr ""
431
 
432
+ #: includes/class-freemius.php:17714
433
  msgid "Your license was successfully activated."
434
  msgstr ""
435
 
436
+ #: includes/class-freemius.php:17740
437
  msgid "It looks like your site currently doesn't have an active license."
438
  msgstr ""
439
 
440
+ #: includes/class-freemius.php:17764
441
  msgid "It looks like the license deactivation failed."
442
  msgstr ""
443
 
444
+ #: includes/class-freemius.php:17792
445
  msgid "Your license was successfully deactivated, you are back to the %s plan."
446
  msgstr ""
447
 
448
+ #: includes/class-freemius.php:17793
449
  msgid "O.K"
450
  msgstr ""
451
 
452
+ #: includes/class-freemius.php:17846
453
+ msgid "Seems like we are having some temporary issue with your subscription cancellation. Please try again in few minutes."
454
  msgstr ""
455
 
456
+ #: includes/class-freemius.php:17855
457
+ msgid "Your subscription was successfully cancelled. Your %s plan license will expire in %s."
458
  msgstr ""
459
 
460
+ #: includes/class-freemius.php:17897
461
  msgid "You are already running the %s in a trial mode."
462
  msgstr ""
463
 
464
+ #: includes/class-freemius.php:17908
465
  msgid "You already utilized a trial before."
466
  msgstr ""
467
 
468
+ #: includes/class-freemius.php:17922
469
  msgid "Plan %s do not exist, therefore, can't start a trial."
470
  msgstr ""
471
 
472
+ #: includes/class-freemius.php:17933
473
  msgid "Plan %s does not support a trial period."
474
  msgstr ""
475
 
476
+ #: includes/class-freemius.php:17944
477
  msgid "None of the %s's plans supports a trial period."
478
  msgstr ""
479
 
480
+ #: includes/class-freemius.php:17994
481
  msgid "It looks like you are not in trial mode anymore so there's nothing to cancel :)"
482
  msgstr ""
483
 
484
+ #: includes/class-freemius.php:18030
485
+ msgid "Seems like we are having some temporary issue with your trial cancellation. Please try again in few minutes."
486
  msgstr ""
487
 
488
+ #: includes/class-freemius.php:18049
489
+ msgid "Your %s free trial was successfully cancelled."
490
  msgstr ""
491
 
492
+ #: includes/class-freemius.php:18356
493
  msgid "Version %s was released."
494
  msgstr ""
495
 
496
+ #: includes/class-freemius.php:18356
497
  msgid "Please download %s."
498
  msgstr ""
499
 
500
+ #: includes/class-freemius.php:18363
501
  msgid "the latest %s version here"
502
  msgstr ""
503
 
504
+ #: includes/class-freemius.php:18368
505
  msgid "New"
506
  msgstr ""
507
 
508
+ #: includes/class-freemius.php:18373
509
  msgid "Seems like you got the latest release."
510
  msgstr ""
511
 
512
+ #: includes/class-freemius.php:18374
513
  msgid "You are all good!"
514
  msgstr ""
515
 
516
+ #: includes/class-freemius.php:18642
517
  msgid "Verification mail was just sent to %s. If you can't find it after 5 min, please check your spam box."
518
  msgstr ""
519
 
520
+ #: includes/class-freemius.php:18779
521
  msgid "Site successfully opted in."
522
  msgstr ""
523
 
524
+ #: includes/class-freemius.php:18780, includes/class-freemius.php:19591
525
  msgid "Awesome"
526
  msgstr ""
527
 
528
+ #: includes/class-freemius.php:18796, templates/forms/optout.php:32
529
  msgid "We appreciate your help in making the %s better by letting us track some usage data."
530
  msgstr ""
531
 
532
+ #: includes/class-freemius.php:18797
533
  msgid "Thank you!"
534
  msgstr ""
535
 
536
+ #: includes/class-freemius.php:18804
537
  msgid "We will no longer be sending any usage data of %s on %s to %s."
538
  msgstr ""
539
 
540
+ #: includes/class-freemius.php:18933
541
  msgid "Please check your mailbox, you should receive an email via %s to confirm the ownership change. From security reasons, you must confirm the change within the next 15 min. If you cannot find the email, please check your spam folder."
542
  msgstr ""
543
 
544
+ #: includes/class-freemius.php:18939
545
  msgid "Thanks for confirming the ownership change. An email was just sent to %s for final approval."
546
  msgstr ""
547
 
548
+ #: includes/class-freemius.php:18944
549
  msgid "%s is the new owner of the account."
550
  msgstr ""
551
 
552
+ #: includes/class-freemius.php:18946
553
  msgctxt "as congratulations"
554
  msgid "Congrats"
555
  msgstr ""
556
 
557
+ #: includes/class-freemius.php:18966
558
  msgid "Sorry, we could not complete the email update. Another user with the same email is already registered."
559
  msgstr ""
560
 
561
+ #: includes/class-freemius.php:18967
562
  msgid "If you would like to give up the ownership of the %s's account to %s click the Change Ownership button."
563
  msgstr ""
564
 
565
+ #: includes/class-freemius.php:18974
566
  msgid "Change Ownership"
567
  msgstr ""
568
 
569
+ #: includes/class-freemius.php:18982
570
  msgid "Your email was successfully updated. You should receive an email with confirmation instructions in few moments."
571
  msgstr ""
572
 
573
+ #: includes/class-freemius.php:18994
574
  msgid "Please provide your full name."
575
  msgstr ""
576
 
577
+ #: includes/class-freemius.php:18999
578
  msgid "Your name was successfully updated."
579
  msgstr ""
580
 
581
+ #: includes/class-freemius.php:19060
582
  msgid "You have successfully updated your %s."
583
  msgstr ""
584
 
585
+ #: includes/class-freemius.php:19200
586
  msgid "Just letting you know that the add-ons information of %s is being pulled from an external server."
587
  msgstr ""
588
 
589
+ #: includes/class-freemius.php:19201
590
  msgctxt "advance notice of something that will need attention."
591
  msgid "Heads up"
592
  msgstr ""
593
 
594
+ #: includes/class-freemius.php:19631
595
  msgctxt "exclamation"
596
  msgid "Hey"
597
  msgstr ""
598
 
599
+ #: includes/class-freemius.php:19631
600
  msgid "How do you like %s so far? Test all our %s premium features with a %d-day free trial."
601
  msgstr ""
602
 
603
+ #: includes/class-freemius.php:19639
604
  msgid "No commitment for %s days - cancel anytime!"
605
  msgstr ""
606
 
607
+ #: includes/class-freemius.php:19640
608
  msgid "No credit card required"
609
  msgstr ""
610
 
611
+ #: includes/class-freemius.php:19647, templates/forms/trial-start.php:53
612
  msgctxt "call to action"
613
  msgid "Start free trial"
614
  msgstr ""
615
 
616
+ #: includes/class-freemius.php:19724
617
  msgid "Hey there, did you know that %s has an affiliate program? If you like the %s you can become our ambassador and earn some cash!"
618
  msgstr ""
619
 
620
+ #: includes/class-freemius.php:19733
621
  msgid "Learn more"
622
  msgstr ""
623
 
624
+ #: includes/class-freemius.php:19883, templates/account.php:406, templates/account.php:509, templates/connect.php:171, templates/connect.php:421, templates/forms/license-activation.php:24, templates/account/partials/addon.php:235
625
  msgid "Activate License"
626
  msgstr ""
627
 
628
+ #: includes/class-freemius.php:19884, templates/account.php:469, templates/account.php:508, templates/account/partials/site.php:256
629
  msgid "Change License"
630
  msgstr ""
631
 
632
+ #: includes/class-freemius.php:19966, templates/account/partials/site.php:161
633
  msgid "Opt Out"
634
  msgstr ""
635
 
636
+ #: includes/class-freemius.php:19968, includes/class-freemius.php:19973, templates/account/partials/site.php:43, templates/account/partials/site.php:161
637
  msgid "Opt In"
638
  msgstr ""
639
 
640
+ #: includes/class-freemius.php:20197
641
+ msgid " The paid version of %1s is already installed. Please activate it to start benefiting the %2s features. %3s"
642
+ msgstr ""
643
+
644
+ #: includes/class-freemius.php:20205
645
+ msgid "Activate %s features"
646
+ msgstr ""
647
+
648
+ #: includes/class-freemius.php:20218
649
  msgid "Please follow these steps to complete the upgrade"
650
  msgstr ""
651
 
652
+ #: includes/class-freemius.php:20222
653
  msgid "Download the latest %s version"
654
  msgstr ""
655
 
656
+ #: includes/class-freemius.php:20226
657
  msgid "Upload and activate the downloaded version"
658
  msgstr ""
659
 
660
+ #: includes/class-freemius.php:20228
661
  msgid "How to upload and activate?"
662
  msgstr ""
663
 
664
+ #: includes/class-freemius.php:20362
665
  msgid "%sClick here%s to choose the sites where you'd like to activate the license on."
666
  msgstr ""
667
 
668
+ #: includes/class-freemius.php:20523
669
  msgid "Auto installation only works for opted-in users."
670
  msgstr ""
671
 
672
+ #: includes/class-freemius.php:20533, includes/class-freemius.php:20566, includes/class-fs-plugin-updater.php:1060, includes/class-fs-plugin-updater.php:1074
673
  msgid "Invalid module ID."
674
  msgstr ""
675
 
676
+ #: includes/class-freemius.php:20542, includes/class-fs-plugin-updater.php:1096
677
  msgid "Premium version already active."
678
  msgstr ""
679
 
680
+ #: includes/class-freemius.php:20549
681
  msgid "You do not have a valid license to access the premium version."
682
  msgstr ""
683
 
684
+ #: includes/class-freemius.php:20556
685
  msgid "Plugin is a \"Serviceware\" which means it does not have a premium code version."
686
  msgstr ""
687
 
688
+ #: includes/class-freemius.php:20574, includes/class-fs-plugin-updater.php:1095
689
  msgid "Premium add-on version already installed."
690
  msgstr ""
691
 
692
+ #: includes/class-freemius.php:20919
693
  msgid "View paid features"
694
  msgstr ""
695
 
696
+ #: includes/class-freemius.php:21239
697
  msgid "Thank you so much for using %s and its add-ons!"
698
  msgstr ""
699
 
700
+ #: includes/class-freemius.php:21240
701
  msgid "Thank you so much for using %s!"
702
  msgstr ""
703
 
704
+ #: includes/class-freemius.php:21246
705
  msgid "You've already opted-in to our usage-tracking, which helps us keep improving the %s."
706
  msgstr ""
707
 
708
+ #: includes/class-freemius.php:21250
709
  msgid "Thank you so much for using our products!"
710
  msgstr ""
711
 
712
+ #: includes/class-freemius.php:21251
713
  msgid "You've already opted-in to our usage-tracking, which helps us keep improving them."
714
  msgstr ""
715
 
716
+ #: includes/class-freemius.php:21270
717
  msgid "%s and its add-ons"
718
  msgstr ""
719
 
720
+ #: includes/class-freemius.php:21279
721
  msgid "Products"
722
  msgstr ""
723
 
724
+ #: includes/class-freemius.php:21286, templates/connect.php:272
725
  msgid "Yes"
726
  msgstr ""
727
 
728
+ #: includes/class-freemius.php:21287, templates/connect.php:273
729
  msgid "send me security & feature updates, educational content and offers."
730
  msgstr ""
731
 
732
+ #: includes/class-freemius.php:21288, templates/connect.php:278
733
  msgid "No"
734
  msgstr ""
735
 
736
+ #: includes/class-freemius.php:21290, templates/connect.php:280
737
  msgid "do %sNOT%s send me security & feature updates, educational content and offers."
738
  msgstr ""
739
 
740
+ #: includes/class-freemius.php:21300
741
  msgid "Due to the new %sEU General Data Protection Regulation (GDPR)%s compliance requirements it is required that you provide your explicit consent, again, confirming that you are onboard 🙂"
742
  msgstr ""
743
 
744
+ #: includes/class-freemius.php:21302, templates/connect.php:287
745
  msgid "Please let us know if you'd like us to contact you for security & feature updates, educational content, and occasional offers:"
746
  msgstr ""
747
 
748
+ #: includes/class-freemius.php:21584
749
  msgid "License key is empty."
750
  msgstr ""
751
 
752
+ #: includes/class-fs-plugin-updater.php:184, templates/forms/premium-versions-upgrade-handler.php:57
753
+ msgid "Renew license"
754
  msgstr ""
755
 
756
+ #: includes/class-fs-plugin-updater.php:189, templates/forms/premium-versions-upgrade-handler.php:58
757
+ msgid "Buy license"
758
+ msgstr ""
759
+
760
+ #: includes/class-fs-plugin-updater.php:278
761
+ msgid "There is a %s of %s available."
762
+ msgstr ""
763
+
764
+ #: includes/class-fs-plugin-updater.php:282
765
+ msgid "new version"
766
+ msgstr ""
767
+
768
+ #: includes/class-fs-plugin-updater.php:305
769
+ msgid "Important Upgrade Notice:"
770
+ msgstr ""
771
+
772
+ #: includes/class-fs-plugin-updater.php:1125
773
  msgid "Installing plugin: %s"
774
  msgstr ""
775
 
776
+ #: includes/class-fs-plugin-updater.php:1166
777
  msgid "Unable to connect to the filesystem. Please confirm your credentials."
778
  msgstr ""
779
 
780
+ #: includes/class-fs-plugin-updater.php:1348
781
  msgid "The remote plugin package does not contain a folder with the desired slug and renaming did not work."
782
  msgstr ""
783
 
784
+ #: includes/fs-plugin-info-dialog.php:369, templates/account/partials/addon.php:292
785
  msgctxt "verb"
786
  msgid "Purchase"
787
  msgstr ""
788
 
789
+ #: includes/fs-plugin-info-dialog.php:372
790
  msgid "Start my free %s"
791
  msgstr ""
792
 
793
+ #: includes/fs-plugin-info-dialog.php:413
794
  msgid "Install Free Version Now"
795
  msgstr ""
796
 
797
+ #: includes/fs-plugin-info-dialog.php:414, templates/auto-installation.php:111, templates/account/partials/addon.php:272, templates/account/partials/addon.php:322
798
  msgid "Install Now"
799
  msgstr ""
800
 
801
+ #: includes/fs-plugin-info-dialog.php:425
802
  msgctxt "as download latest version"
803
  msgid "Download Latest Free Version"
804
  msgstr ""
805
 
806
+ #: includes/fs-plugin-info-dialog.php:426, templates/account.php:80, templates/account/partials/addon.php:21
807
  msgctxt "as download latest version"
808
  msgid "Download Latest"
809
  msgstr ""
810
 
811
+ #: includes/fs-plugin-info-dialog.php:436
812
  msgid "Install Free Version Update Now"
813
  msgstr ""
814
 
815
+ #: includes/fs-plugin-info-dialog.php:437, templates/account.php:460
816
  msgid "Install Update Now"
817
  msgstr ""
818
 
819
+ #: includes/fs-plugin-info-dialog.php:448
820
  msgid "Newer Free Version (%s) Installed"
821
  msgstr ""
822
 
823
+ #: includes/fs-plugin-info-dialog.php:449
824
  msgid "Newer Version (%s) Installed"
825
  msgstr ""
826
 
827
+ #: includes/fs-plugin-info-dialog.php:457
828
  msgid "Latest Free Version Installed"
829
  msgstr ""
830
 
831
+ #: includes/fs-plugin-info-dialog.php:458
832
  msgid "Latest Version Installed"
833
  msgstr ""
834
 
835
+ #: includes/fs-plugin-info-dialog.php:613
836
  msgctxt "Plugin installer section title"
837
  msgid "Description"
838
  msgstr ""
839
 
840
+ #: includes/fs-plugin-info-dialog.php:614
841
  msgctxt "Plugin installer section title"
842
  msgid "Installation"
843
  msgstr ""
844
 
845
+ #: includes/fs-plugin-info-dialog.php:615
846
  msgctxt "Plugin installer section title"
847
  msgid "FAQ"
848
  msgstr ""
849
 
850
+ #: includes/fs-plugin-info-dialog.php:616, templates/plugin-info/description.php:55
851
  msgid "Screenshots"
852
  msgstr ""
853
 
854
+ #: includes/fs-plugin-info-dialog.php:617
855
  msgctxt "Plugin installer section title"
856
  msgid "Changelog"
857
  msgstr ""
858
 
859
+ #: includes/fs-plugin-info-dialog.php:618
860
  msgctxt "Plugin installer section title"
861
  msgid "Reviews"
862
  msgstr ""
863
 
864
+ #: includes/fs-plugin-info-dialog.php:619
865
  msgctxt "Plugin installer section title"
866
  msgid "Other Notes"
867
  msgstr ""
868
 
869
+ #: includes/fs-plugin-info-dialog.php:634
870
  msgctxt "Plugin installer section title"
871
  msgid "Features & Pricing"
872
  msgstr ""
873
 
874
+ #: includes/fs-plugin-info-dialog.php:644
875
  msgid "Plugin Install"
876
  msgstr ""
877
 
878
+ #: includes/fs-plugin-info-dialog.php:716
879
  msgctxt "e.g. Professional Plan"
880
  msgid "%s Plan"
881
  msgstr ""
882
 
883
+ #: includes/fs-plugin-info-dialog.php:742
884
  msgctxt "e.g. the best product"
885
  msgid "Best"
886
  msgstr ""
887
 
888
+ #: includes/fs-plugin-info-dialog.php:748, includes/fs-plugin-info-dialog.php:768
889
  msgctxt "as every month"
890
  msgid "Monthly"
891
  msgstr ""
892
 
893
+ #: includes/fs-plugin-info-dialog.php:751
894
  msgctxt "as once a year"
895
  msgid "Annual"
896
  msgstr ""
897
 
898
+ #: includes/fs-plugin-info-dialog.php:754
899
  msgid "Lifetime"
900
  msgstr ""
901
 
902
+ #: includes/fs-plugin-info-dialog.php:768, includes/fs-plugin-info-dialog.php:770, includes/fs-plugin-info-dialog.php:772
903
  msgctxt "e.g. billed monthly"
904
  msgid "Billed %s"
905
  msgstr ""
906
 
907
+ #: includes/fs-plugin-info-dialog.php:770
908
  msgctxt "as once a year"
909
  msgid "Annually"
910
  msgstr ""
911
 
912
+ #: includes/fs-plugin-info-dialog.php:772
913
  msgctxt "as once a year"
914
  msgid "Once"
915
  msgstr ""
916
 
917
+ #: includes/fs-plugin-info-dialog.php:778
918
  msgid "Single Site License"
919
  msgstr ""
920
 
921
+ #: includes/fs-plugin-info-dialog.php:780
922
  msgid "Unlimited Licenses"
923
  msgstr ""
924
 
925
+ #: includes/fs-plugin-info-dialog.php:782
926
  msgid "Up to %s Sites"
927
  msgstr ""
928
 
929
+ #: includes/fs-plugin-info-dialog.php:792, templates/plugin-info/features.php:82
930
  msgctxt "as monthly period"
931
  msgid "mo"
932
  msgstr ""
933
 
934
+ #: includes/fs-plugin-info-dialog.php:799, templates/plugin-info/features.php:80
935
  msgctxt "as annual period"
936
  msgid "year"
937
  msgstr ""
938
 
939
+ #: includes/fs-plugin-info-dialog.php:853
940
  msgctxt "noun"
941
  msgid "Price"
942
  msgstr ""
943
 
944
+ #: includes/fs-plugin-info-dialog.php:901
945
  msgid "Save %s"
946
  msgstr ""
947
 
948
+ #: includes/fs-plugin-info-dialog.php:911
949
  msgid "No commitment for %s - cancel anytime"
950
  msgstr ""
951
 
952
+ #: includes/fs-plugin-info-dialog.php:914
953
  msgid "After your free %s, pay as little as %s"
954
  msgstr ""
955
 
956
+ #: includes/fs-plugin-info-dialog.php:925
957
  msgid "Details"
958
  msgstr ""
959
 
960
+ #: includes/fs-plugin-info-dialog.php:929, templates/account.php:91, templates/debug.php:201, templates/debug.php:238, templates/debug.php:452, templates/account/partials/addon.php:32
961
  msgctxt "product version"
962
  msgid "Version"
963
  msgstr ""
964
 
965
+ #: includes/fs-plugin-info-dialog.php:936
966
  msgctxt "as the plugin author"
967
  msgid "Author"
968
  msgstr ""
969
 
970
+ #: includes/fs-plugin-info-dialog.php:943
971
  msgid "Last Updated"
972
  msgstr ""
973
 
974
+ #: includes/fs-plugin-info-dialog.php:948, templates/account.php:376
975
  msgctxt "x-ago"
976
  msgid "%s ago"
977
  msgstr ""
978
 
979
+ #: includes/fs-plugin-info-dialog.php:957
980
  msgid "Requires WordPress Version"
981
  msgstr ""
982
 
983
+ #: includes/fs-plugin-info-dialog.php:958
984
  msgid "%s or higher"
985
  msgstr ""
986
 
987
+ #: includes/fs-plugin-info-dialog.php:965
988
  msgid "Compatible up to"
989
  msgstr ""
990
 
991
+ #: includes/fs-plugin-info-dialog.php:973
992
  msgid "Downloaded"
993
  msgstr ""
994
 
995
+ #: includes/fs-plugin-info-dialog.php:977
996
  msgid "%s time"
997
  msgstr ""
998
 
999
+ #: includes/fs-plugin-info-dialog.php:979
1000
  msgid "%s times"
1001
  msgstr ""
1002
 
1003
+ #: includes/fs-plugin-info-dialog.php:989
1004
  msgid "WordPress.org Plugin Page"
1005
  msgstr ""
1006
 
1007
+ #: includes/fs-plugin-info-dialog.php:997
1008
  msgid "Plugin Homepage"
1009
  msgstr ""
1010
 
1011
+ #: includes/fs-plugin-info-dialog.php:1005, includes/fs-plugin-info-dialog.php:1087
1012
  msgid "Donate to this plugin"
1013
  msgstr ""
1014
 
1015
+ #: includes/fs-plugin-info-dialog.php:1012
1016
  msgid "Average Rating"
1017
  msgstr ""
1018
 
1019
+ #: includes/fs-plugin-info-dialog.php:1019
1020
  msgid "based on %s"
1021
  msgstr ""
1022
 
1023
+ #: includes/fs-plugin-info-dialog.php:1023
1024
  msgid "%s rating"
1025
  msgstr ""
1026
 
1027
+ #: includes/fs-plugin-info-dialog.php:1025
1028
  msgid "%s ratings"
1029
  msgstr ""
1030
 
1031
+ #: includes/fs-plugin-info-dialog.php:1040
1032
  msgid "%s star"
1033
  msgstr ""
1034
 
1035
+ #: includes/fs-plugin-info-dialog.php:1042
1036
  msgid "%s stars"
1037
  msgstr ""
1038
 
1039
+ #: includes/fs-plugin-info-dialog.php:1053
1040
  msgid "Click to see reviews that provided a rating of %s"
1041
  msgstr ""
1042
 
1043
+ #: includes/fs-plugin-info-dialog.php:1066
1044
  msgid "Contributors"
1045
  msgstr ""
1046
 
1047
+ #: includes/fs-plugin-info-dialog.php:1095, includes/fs-plugin-info-dialog.php:1097
1048
  msgid "Warning"
1049
  msgstr ""
1050
 
1051
+ #: includes/fs-plugin-info-dialog.php:1095
1052
  msgid "This plugin has not been tested with your current version of WordPress."
1053
  msgstr ""
1054
 
1055
+ #: includes/fs-plugin-info-dialog.php:1097
1056
  msgid "This plugin has not been marked as compatible with your version of WordPress."
1057
  msgstr ""
1058
 
1059
+ #: includes/fs-plugin-info-dialog.php:1116
1060
  msgid "Paid add-on must be deployed to Freemius."
1061
  msgstr ""
1062
 
1063
+ #: includes/fs-plugin-info-dialog.php:1117
1064
  msgid "Add-on must be deployed to WordPress.org or Freemius."
1065
  msgstr ""
1066
 
1067
+ #: templates/account.php:81, templates/forms/subscription-cancellation.php:96, templates/account/partials/addon.php:22, templates/account/partials/site.php:295
1068
+ msgid "Downgrading your plan"
1069
+ msgstr ""
1070
+
1071
+ #: templates/account.php:82, templates/forms/subscription-cancellation.php:97, templates/account/partials/addon.php:23, templates/account/partials/site.php:296
1072
+ msgid "Cancelling the subscription"
1073
+ msgstr ""
1074
+
1075
+ #. translators: %1s: Either 'Downgrading your plan' or 'Cancelling the subscription'
1076
+ #: templates/account.php:84, templates/forms/subscription-cancellation.php:99, templates/account/partials/addon.php:25, templates/account/partials/site.php:298
1077
+ msgid "%1s will immediately stop all future recurring payments and your %s plan license will expire in %s."
1078
  msgstr ""
1079
 
1080
+ #: templates/account.php:85, templates/forms/subscription-cancellation.php:100, templates/account/partials/addon.php:26, templates/account/partials/site.php:299
1081
+ msgid "Please note that we will not be able to grandfather outdated pricing for renewals/new subscriptions after a cancellation. If you choose to renew the subscription manually in the future, after a price increase, which typically occurs once a year, you will be charged the updated price."
1082
+ msgstr ""
1083
+
1084
+ #: templates/account.php:86, templates/forms/subscription-cancellation.php:106, templates/account/partials/addon.php:27
1085
  msgid "Cancelling the trial will immediately block access to all premium features. Are you sure?"
1086
  msgstr ""
1087
 
1088
+ #: templates/account.php:87, templates/forms/subscription-cancellation.php:101, templates/account/partials/addon.php:28, templates/account/partials/site.php:300
1089
+ msgid "You can still enjoy all %s features but you will not have access to %s security & feature updates, nor support."
1090
  msgstr ""
1091
 
1092
+ #: templates/account.php:88, templates/forms/subscription-cancellation.php:102, templates/account/partials/addon.php:29, templates/account/partials/site.php:301
1093
  msgid "Once your license expires you can still use the Free version but you will NOT have access to the %s features."
1094
  msgstr ""
1095
 
1096
  #. translators: %s: Plan title (e.g. "Professional")
1097
+ #: templates/account.php:90, templates/account/partials/activate-license-button.php:31, templates/account/partials/addon.php:31
1098
  msgid "Activate %s Plan"
1099
  msgstr ""
1100
 
1101
  #. translators: %s: Time period (e.g. Auto renews in "2 months")
1102
+ #: templates/account.php:93, templates/account/partials/addon.php:34, templates/account/partials/site.php:275
1103
  msgid "Auto renews in %s"
1104
  msgstr ""
1105
 
1106
  #. translators: %s: Time period (e.g. Expires in "2 months")
1107
+ #: templates/account.php:95, templates/account/partials/addon.php:36, templates/account/partials/site.php:277
1108
  msgid "Expires in %s"
1109
  msgstr ""
1110
 
1111
+ #: templates/account.php:96, templates/account/partials/addon.php:37
1112
  msgctxt "as synchronize license"
1113
  msgid "Sync License"
1114
  msgstr ""
1115
 
1116
+ #: templates/account.php:97, templates/account/partials/addon.php:38
1117
  msgid "Cancel Trial"
1118
  msgstr ""
1119
 
1120
+ #: templates/account.php:98, templates/account/partials/addon.php:39
1121
  msgid "Change Plan"
1122
  msgstr ""
1123
 
1124
+ #: templates/account.php:99, templates/account/partials/addon.php:40
1125
  msgctxt "verb"
1126
  msgid "Upgrade"
1127
  msgstr ""
1128
 
1129
+ #: templates/account.php:101, templates/account/partials/addon.php:42, templates/account/partials/site.php:302
1130
  msgctxt "verb"
1131
  msgid "Downgrade"
1132
  msgstr ""
1133
 
1134
+ #: templates/account.php:103, templates/add-ons.php:130, templates/plugin-info/features.php:72, templates/account/partials/addon.php:44, templates/account/partials/site.php:31
1135
  msgid "Free"
1136
  msgstr ""
1137
 
1138
+ #: templates/account.php:104, templates/account/partials/addon.php:45
1139
  msgid "Activate"
1140
  msgstr ""
1141
 
1142
+ #: templates/account.php:105, templates/debug.php:371, includes/customizer/class-fs-customizer-upsell-control.php:106, templates/account/partials/addon.php:46
1143
  msgctxt "as product pricing plan"
1144
  msgid "Plan"
1145
  msgstr ""
1146
 
1147
+ #: templates/account.php:158
1148
  msgid "Free Trial"
1149
  msgstr ""
1150
 
1151
+ #: templates/account.php:169
1152
  msgid "Account Details"
1153
  msgstr ""
1154
 
1155
+ #: templates/account.php:179
1156
  msgid "Deleting the account will automatically deactivate your %s plan license so you can use it on other sites. If you want to terminate the recurring payments as well, click the \"Cancel\" button, and first \"Downgrade\" your account. Are you sure you would like to continue with the deletion?"
1157
  msgstr ""
1158
 
1159
+ #: templates/account.php:181
1160
  msgid "Deletion is not temporary. Only delete if you no longer want to use this %s anymore. Are you sure you would like to continue with the deletion?"
1161
  msgstr ""
1162
 
1163
+ #: templates/account.php:184
1164
  msgid "Delete Account"
1165
  msgstr ""
1166
 
1167
+ #: templates/account.php:196, templates/account/partials/addon.php:159, templates/account/partials/deactivate-license-button.php:35
1168
  msgid "Deactivate License"
1169
  msgstr ""
1170
 
1171
+ #: templates/account.php:219, templates/forms/subscription-cancellation.php:125
1172
  msgid "Are you sure you want to proceed?"
1173
  msgstr ""
1174
 
1175
+ #: templates/account.php:219, templates/account/partials/addon.php:182
1176
  msgid "Cancel Subscription"
1177
  msgstr ""
1178
 
1179
+ #: templates/account.php:247
1180
  msgctxt "as synchronize"
1181
  msgid "Sync"
1182
  msgstr ""
1183
 
1184
+ #: templates/account.php:261, templates/debug.php:487
1185
  msgid "Name"
1186
  msgstr ""
1187
 
1188
+ #: templates/account.php:267, templates/debug.php:488
1189
  msgid "Email"
1190
  msgstr ""
1191
 
1192
+ #: templates/account.php:274, templates/debug.php:370, templates/debug.php:526
1193
  msgid "User ID"
1194
  msgstr ""
1195
 
1196
+ #: templates/account.php:282
1197
  msgid "Site ID"
1198
  msgstr ""
1199
 
1200
+ #: templates/account.php:285
1201
  msgid "No ID"
1202
  msgstr ""
1203
 
1204
+ #: templates/account.php:290, templates/debug.php:243, templates/debug.php:372, templates/debug.php:453, templates/debug.php:490, templates/account/partials/site.php:219
1205
  msgid "Public Key"
1206
  msgstr ""
1207
 
1208
+ #: templates/account.php:296, templates/debug.php:373, templates/debug.php:454, templates/debug.php:491, templates/account/partials/site.php:231
1209
  msgid "Secret Key"
1210
  msgstr ""
1211
 
1212
+ #: templates/account.php:299
1213
  msgctxt "as secret encryption key missing"
1214
  msgid "No Secret"
1215
  msgstr ""
1216
 
1217
+ #: templates/account.php:318, templates/account/partials/site.php:112, templates/account/partials/site.php:114
1218
  msgid "Trial"
1219
  msgstr ""
1220
 
1221
+ #: templates/account.php:337, templates/debug.php:531, templates/account/partials/site.php:248
1222
  msgid "License Key"
1223
  msgstr ""
1224
 
1225
+ #: templates/account.php:367
1226
  msgid "not verified"
1227
  msgstr ""
1228
 
1229
+ #: templates/account.php:376, templates/account/partials/addon.php:120
1230
  msgid "Expired"
1231
  msgstr ""
1232
 
1233
+ #: templates/account.php:428
1234
  msgid "Premium version"
1235
  msgstr ""
1236
 
1237
+ #: templates/account.php:430
1238
  msgid "Free version"
1239
  msgstr ""
1240
 
1241
+ #: templates/account.php:442
1242
  msgid "Verify Email"
1243
  msgstr ""
1244
 
1245
+ #: templates/account.php:453
1246
  msgid "Download %s Version"
1247
  msgstr ""
1248
 
1249
+ #: templates/account.php:467, templates/account.php:649, templates/account/partials/site.php:237, templates/account/partials/site.php:255
1250
  msgctxt "verb"
1251
  msgid "Show"
1252
  msgstr ""
1253
 
1254
+ #: templates/account.php:481
1255
  msgid "What is your %s?"
1256
  msgstr ""
1257
 
1258
+ #: templates/account.php:489, templates/account/billing.php:27
1259
  msgctxt "verb"
1260
  msgid "Edit"
1261
  msgstr ""
1262
 
1263
+ #: templates/account.php:502
1264
  msgid "Sites"
1265
  msgstr ""
1266
 
1267
+ #: templates/account.php:513
1268
  msgid "Search by address"
1269
  msgstr ""
1270
 
1271
+ #: templates/account.php:522, templates/account.php:570, templates/debug.php:236, templates/debug.php:364, templates/debug.php:449, templates/debug.php:486, templates/debug.php:524, templates/debug.php:597, templates/account/payments.php:35, templates/debug/logger.php:21
1272
  msgid "ID"
1273
  msgstr ""
1274
 
1275
+ #: templates/account.php:523, templates/debug.php:367
1276
  msgid "Address"
1277
  msgstr ""
1278
 
1279
+ #: templates/account.php:524
1280
  msgid "License"
1281
  msgstr ""
1282
 
1283
+ #: templates/account.php:525
1284
  msgid "Plan"
1285
  msgstr ""
1286
 
1287
+ #: templates/account.php:573
1288
  msgctxt "as software license"
1289
  msgid "License"
1290
  msgstr ""
1291
 
1292
+ #: templates/account.php:643
1293
  msgctxt "verb"
1294
  msgid "Hide"
1295
  msgstr ""
1296
 
1297
+ #: templates/account.php:686
1298
+ msgid "Cancelling %s"
1299
+ msgstr ""
1300
+
1301
+ #: templates/account.php:686, templates/account.php:703, templates/forms/subscription-cancellation.php:27, templates/forms/deactivation/form.php:117
1302
+ msgid "trial"
1303
+ msgstr ""
1304
+
1305
+ #: templates/account.php:701, templates/forms/deactivation/form.php:134
1306
+ msgid "Cancelling %s..."
1307
+ msgstr ""
1308
+
1309
+ #: templates/account.php:704, templates/forms/subscription-cancellation.php:28, templates/forms/deactivation/form.php:118
1310
+ msgid "subscription"
1311
+ msgstr ""
1312
+
1313
+ #: templates/account.php:718
1314
  msgid "Deactivating your license will block all premium features, but will enable activating the license on another site. Are you sure you want to proceed?"
1315
  msgstr ""
1316
 
1322
  msgid "We could'nt load the add-ons list. It's probably an issue on our side, please try to come back in few minutes."
1323
  msgstr ""
1324
 
1325
+ #: templates/add-ons.php:139
1326
  msgid "View details"
1327
  msgstr ""
1328
 
1360
  msgstr ""
1361
 
1362
  #. translators: %s: name (e.g. Hey John,)
1363
+ #: templates/connect.php:112
1364
  msgctxt "greeting"
1365
  msgid "Hey %s,"
1366
  msgstr ""
1367
 
1368
+ #: templates/connect.php:154
1369
  msgid "Allow & Continue"
1370
  msgstr ""
1371
 
1372
+ #: templates/connect.php:158
1373
  msgid "Re-send activation email"
1374
  msgstr ""
1375
 
1376
+ #: templates/connect.php:162
1377
  msgid "Thanks %s!"
1378
  msgstr ""
1379
 
1380
+ #: templates/connect.php:172, templates/forms/license-activation.php:43
1381
  msgid "Agree & Activate License"
1382
  msgstr ""
1383
 
1384
+ #: templates/connect.php:181
1385
  msgid "Thanks for purchasing %s! To get started, please enter your license key:"
1386
  msgstr ""
1387
 
1388
+ #: templates/connect.php:188
1389
  msgid "Never miss an important update - opt in to our security & feature updates notifications, educational content, offers, and non-sensitive diagnostic tracking with %4$s."
1390
  msgstr ""
1391
 
1392
+ #: templates/connect.php:189
1393
  msgid "Never miss an important update - opt in to our security and feature updates notifications, and non-sensitive diagnostic tracking with %4$s."
1394
  msgstr ""
1395
 
1396
+ #: templates/connect.php:195
1397
  msgid "Never miss an important update - opt in to our security & feature updates notifications, educational content, offers, and non-sensitive diagnostic tracking with %4$s. If you skip this, that's okay! %1$s will still work just fine."
1398
  msgstr ""
1399
 
1400
+ #: templates/connect.php:196
1401
  msgid "Never miss an important update - opt in to our security & feature updates notifications, and non-sensitive diagnostic tracking with %4$s. If you skip this, that's okay! %1$s will still work just fine."
1402
  msgstr ""
1403
 
1404
+ #: templates/connect.php:230
1405
  msgid "We're excited to introduce the Freemius network-level integration."
1406
  msgstr ""
1407
 
1408
+ #: templates/connect.php:233
1409
  msgid "During the update process we detected %d site(s) that are still pending license activation."
1410
  msgstr ""
1411
 
1412
+ #: templates/connect.php:235
1413
  msgid "If you'd like to use the %s on those sites, please enter your license key below and click the activation button."
1414
  msgstr ""
1415
 
1416
+ #: templates/connect.php:237
1417
  msgid "%s's paid features"
1418
  msgstr ""
1419
 
1420
+ #: templates/connect.php:242
1421
  msgid "Alternatively, you can skip it for now and activate the license later, in your %s's network-level Account page."
1422
  msgstr ""
1423
 
1424
+ #: templates/connect.php:244
1425
  msgid "During the update process we detected %s site(s) in the network that are still pending your attention."
1426
  msgstr ""
1427
 
1428
+ #: templates/connect.php:253, templates/forms/license-activation.php:46
1429
  msgid "License key"
1430
  msgstr ""
1431
 
1432
+ #: templates/connect.php:256, templates/forms/license-activation.php:19
1433
  msgid "Can't find your license key?"
1434
  msgstr ""
1435
 
1436
+ #: templates/connect.php:315, templates/connect.php:630, templates/forms/deactivation/retry-skip.php:20
1437
  msgctxt "verb"
1438
  msgid "Skip"
1439
  msgstr ""
1440
 
1441
+ #: templates/connect.php:318
1442
  msgid "Delegate to Site Admins"
1443
  msgstr ""
1444
 
1445
+ #: templates/connect.php:318
1446
  msgid "If you click it, this decision will be delegated to the sites administrators."
1447
  msgstr ""
1448
 
1449
+ #: templates/connect.php:346
1450
  msgid "Your Profile Overview"
1451
  msgstr ""
1452
 
1453
+ #: templates/connect.php:347
1454
  msgid "Name and email address"
1455
  msgstr ""
1456
 
1457
+ #: templates/connect.php:352
1458
  msgid "Your Site Overview"
1459
  msgstr ""
1460
 
1461
+ #: templates/connect.php:353
1462
  msgid "Site URL, WP version, PHP info, plugins & themes"
1463
  msgstr ""
1464
 
1465
+ #: templates/connect.php:358
1466
  msgid "Admin Notices"
1467
  msgstr ""
1468
 
1469
+ #: templates/connect.php:359, templates/connect.php:375
1470
  msgid "Updates, announcements, marketing, no spam"
1471
  msgstr ""
1472
 
1473
+ #: templates/connect.php:364
1474
  msgid "Current %s Events"
1475
  msgstr ""
1476
 
1477
+ #: templates/connect.php:365
1478
  msgid "Activation, deactivation and uninstall"
1479
  msgstr ""
1480
 
1481
+ #: templates/connect.php:374
1482
  msgid "Newsletter"
1483
  msgstr ""
1484
 
1485
+ #: templates/connect.php:391, templates/forms/license-activation.php:38
1486
  msgid "The %1$s will be periodically sending data to %2$s to check for security and feature updates, and verify the validity of your license."
1487
  msgstr ""
1488
 
1489
+ #: templates/connect.php:396
1490
  msgid "What permissions are being granted?"
1491
  msgstr ""
1492
 
1493
+ #: templates/connect.php:417
1494
  msgid "Don't have a license key?"
1495
  msgstr ""
1496
 
1497
+ #: templates/connect.php:418
1498
  msgid "Activate Free Version"
1499
  msgstr ""
1500
 
1501
+ #: templates/connect.php:420
1502
  msgid "Have a license key?"
1503
  msgstr ""
1504
 
1505
+ #: templates/connect.php:428
1506
  msgid "Privacy Policy"
1507
  msgstr ""
1508
 
1509
+ #: templates/connect.php:430
1510
+ msgid "License Agreement"
1511
+ msgstr ""
1512
+
1513
+ #: templates/connect.php:430
1514
  msgid "Terms of Service"
1515
  msgstr ""
1516
 
1517
+ #: templates/connect.php:766
1518
  msgctxt "as in the process of sending an email"
1519
  msgid "Sending email"
1520
  msgstr ""
1521
 
1522
+ #: templates/connect.php:767
1523
  msgctxt "as activating plugin"
1524
  msgid "Activating"
1525
  msgstr ""
1547
  msgid "Debugging"
1548
  msgstr ""
1549
 
1550
+ #: templates/debug.php:54, templates/debug.php:248, templates/debug.php:374, templates/debug.php:492
1551
  msgid "Actions"
1552
  msgstr ""
1553
 
1571
  msgid "Sync Data From Server"
1572
  msgstr ""
1573
 
1574
+ #: templates/debug.php:95
1575
+ msgid "Migrate Options to Network"
1576
+ msgstr ""
1577
+
1578
+ #: templates/debug.php:100
1579
  msgid "Load DB Option"
1580
  msgstr ""
1581
 
1582
+ #: templates/debug.php:103
1583
  msgid "Set DB Option"
1584
  msgstr ""
1585
 
1586
+ #: templates/debug.php:180
1587
  msgid "Key"
1588
  msgstr ""
1589
 
1590
+ #: templates/debug.php:181
1591
  msgid "Value"
1592
  msgstr ""
1593
 
1594
+ #: templates/debug.php:197
1595
  msgctxt "as software development kit versions"
1596
  msgid "SDK Versions"
1597
  msgstr ""
1598
 
1599
+ #: templates/debug.php:202
1600
  msgid "SDK Path"
1601
  msgstr ""
1602
 
1603
+ #: templates/debug.php:203, templates/debug.php:242
1604
  msgid "Module Path"
1605
  msgstr ""
1606
 
1607
+ #: templates/debug.php:204
1608
  msgid "Is Active"
1609
  msgstr ""
1610
 
1611
+ #: templates/debug.php:232, templates/debug/plugins-themes-sync.php:35
1612
  msgid "Plugins"
1613
  msgstr ""
1614
 
1615
+ #: templates/debug.php:232, templates/debug/plugins-themes-sync.php:56
1616
  msgid "Themes"
1617
  msgstr ""
1618
 
1619
+ #: templates/debug.php:237, templates/debug.php:369, templates/debug.php:451, templates/debug/scheduled-crons.php:80
1620
  msgid "Slug"
1621
  msgstr ""
1622
 
1623
+ #: templates/debug.php:239, templates/debug.php:450
1624
  msgid "Title"
1625
  msgstr ""
1626
 
1627
+ #: templates/debug.php:240
1628
  msgctxt "as application program interface"
1629
  msgid "API"
1630
  msgstr ""
1631
 
1632
+ #: templates/debug.php:241
1633
  msgid "Freemius State"
1634
  msgstr ""
1635
 
1636
+ #: templates/debug.php:245
1637
  msgid "Network Blog"
1638
  msgstr ""
1639
 
1640
+ #: templates/debug.php:246
1641
  msgid "Network User"
1642
  msgstr ""
1643
 
1644
+ #: templates/debug.php:283
1645
  msgctxt "as connection was successful"
1646
  msgid "Connected"
1647
  msgstr ""
1648
 
1649
+ #: templates/debug.php:284
1650
  msgctxt "as connection blocked"
1651
  msgid "Blocked"
1652
  msgstr ""
1653
 
1654
+ #: templates/debug.php:320
1655
+ msgid "Simulate Trial Promotion"
1656
  msgstr ""
1657
 
1658
+ #: templates/debug.php:332
1659
  msgid "Simulate Network Upgrade"
1660
  msgstr ""
1661
 
1662
+ #: templates/debug.php:358
1663
  msgid "%s Installs"
1664
  msgstr ""
1665
 
1666
+ #: templates/debug.php:360
1667
  msgctxt "like websites"
1668
  msgid "Sites"
1669
  msgstr ""
1670
 
1671
+ #: templates/debug.php:366, templates/account/partials/site.php:148
1672
  msgid "Blog ID"
1673
  msgstr ""
1674
 
1675
+ #: templates/debug.php:431, templates/debug.php:509, templates/account/partials/addon.php:339
1676
  msgctxt "verb"
1677
  msgid "Delete"
1678
  msgstr ""
1679
 
1680
+ #: templates/debug.php:445
1681
  msgid "Add Ons of module %s"
1682
  msgstr ""
1683
 
1684
+ #: templates/debug.php:482
1685
  msgid "Users"
1686
  msgstr ""
1687
 
1688
+ #: templates/debug.php:489
1689
  msgid "Verified"
1690
  msgstr ""
1691
 
1692
+ #: templates/debug.php:520
1693
  msgid "%s Licenses"
1694
  msgstr ""
1695
 
1696
+ #: templates/debug.php:525
1697
  msgid "Plugin ID"
1698
  msgstr ""
1699
 
1700
+ #: templates/debug.php:527
1701
  msgid "Plan ID"
1702
  msgstr ""
1703
 
1704
+ #: templates/debug.php:528
1705
  msgid "Quota"
1706
  msgstr ""
1707
 
1708
+ #: templates/debug.php:529
1709
  msgid "Activated"
1710
  msgstr ""
1711
 
1712
+ #: templates/debug.php:530
1713
  msgid "Blocking"
1714
  msgstr ""
1715
 
1716
+ #: templates/debug.php:532
1717
  msgctxt "as expiration date"
1718
  msgid "Expiration"
1719
  msgstr ""
1720
 
1721
+ #: templates/debug.php:555
1722
  msgid "Debug Log"
1723
  msgstr ""
1724
 
1725
+ #: templates/debug.php:559
1726
  msgid "All Types"
1727
  msgstr ""
1728
 
1729
+ #: templates/debug.php:566
1730
  msgid "All Requests"
1731
  msgstr ""
1732
 
1733
+ #: templates/debug.php:571, templates/debug.php:600, templates/debug/logger.php:25
1734
  msgid "File"
1735
  msgstr ""
1736
 
1737
+ #: templates/debug.php:572, templates/debug.php:598, templates/debug/logger.php:23
1738
  msgid "Function"
1739
  msgstr ""
1740
 
1741
+ #: templates/debug.php:573
1742
  msgid "Process ID"
1743
  msgstr ""
1744
 
1745
+ #: templates/debug.php:574
1746
  msgid "Logger"
1747
  msgstr ""
1748
 
1749
+ #: templates/debug.php:575, templates/debug.php:599, templates/debug/logger.php:24
1750
  msgid "Message"
1751
  msgstr ""
1752
 
1753
+ #: templates/debug.php:577
1754
  msgid "Filter"
1755
  msgstr ""
1756
 
1757
+ #: templates/debug.php:585
1758
  msgid "Download"
1759
  msgstr ""
1760
 
1761
+ #: templates/debug.php:596, templates/debug/logger.php:22
1762
  msgid "Type"
1763
  msgstr ""
1764
 
1765
+ #: templates/debug.php:601, templates/debug/logger.php:26
1766
  msgid "Timestamp"
1767
  msgstr ""
1768
 
2106
  msgid "By clicking \"Opt Out\", we will no longer be sending any data from %s to %s."
2107
  msgstr ""
2108
 
2109
+ #: templates/forms/premium-versions-upgrade-handler.php:40
2110
  msgid "There is a new version of %s available."
2111
  msgstr ""
2112
 
2113
+ #: templates/forms/premium-versions-upgrade-handler.php:41
2114
+ msgid " %s to access version %s security & feature updates, and support."
2115
  msgstr ""
2116
 
2117
+ #: templates/forms/premium-versions-upgrade-handler.php:54
2118
  msgid "New Version Available"
2119
  msgstr ""
2120
 
2121
+ #: templates/forms/premium-versions-upgrade-handler.php:75
 
 
 
 
2122
  msgctxt "close a window"
2123
  msgid "Dismiss"
2124
  msgstr ""
2131
  msgid "Enter the email address you've used for the upgrade below and we will resend you the license key."
2132
  msgstr ""
2133
 
2134
+ #: templates/forms/subscription-cancellation.php:37
2135
+ msgid "Deactivating or uninstalling the %s will automatically disable the license, which you'll be able to use on another site."
2136
+ msgstr ""
2137
+
2138
+ #: templates/forms/subscription-cancellation.php:47
2139
+ msgid "In case you are NOT planning on using this %s on this site (or any other site) - would you like to cancel the %s as well?"
2140
+ msgstr ""
2141
+
2142
+ #: templates/forms/subscription-cancellation.php:52
2143
+ msgid "license"
2144
+ msgstr ""
2145
+
2146
+ #: templates/forms/subscription-cancellation.php:57
2147
+ msgid "Cancel %s - I no longer need any security & feature updates, nor support for %s because I'm not planning to use the %s on this, or any other site."
2148
+ msgstr ""
2149
+
2150
+ #: templates/forms/subscription-cancellation.php:68
2151
+ msgid "Don't cancel %s - I'm still interested in getting security & feature updates, as well as be able to contact support."
2152
+ msgstr ""
2153
+
2154
+ #: templates/forms/subscription-cancellation.php:103
2155
+ msgid "Once your license expires you will no longer be able to use the %s, unless you activate it again with a valid premium license."
2156
+ msgstr ""
2157
+
2158
+ #: templates/forms/subscription-cancellation.php:136
2159
+ msgid "Cancel %s?"
2160
+ msgstr ""
2161
+
2162
+ #: templates/forms/subscription-cancellation.php:143
2163
+ msgid "Proceed"
2164
+ msgstr ""
2165
+
2166
+ #: templates/forms/subscription-cancellation.php:191, templates/forms/deactivation/form.php:150
2167
+ msgid "Cancel %s & Proceed"
2168
+ msgstr ""
2169
+
2170
  #: templates/forms/trial-start.php:22
2171
  msgid "You are 1-click away from starting your %1$s-day free trial of the %2$s plan."
2172
  msgstr ""
2228
  msgid "Last license"
2229
  msgstr ""
2230
 
2231
+ #: templates/account/partials/addon.php:115
2232
  msgid "Cancelled"
2233
  msgstr ""
2234
 
2235
+ #: templates/account/partials/addon.php:125
2236
  msgid "No expiration"
2237
  msgstr ""
2238
 
2239
+ #: templates/account/partials/addon.php:264, templates/account/partials/addon.php:317
2240
  msgid "Activate this add-on"
2241
  msgstr ""
2242
 
2264
  msgid "Contact Support"
2265
  msgstr ""
2266
 
2267
+ #: templates/forms/deactivation/form.php:59
2268
  msgid "Anonymous feedback"
2269
  msgstr ""
2270
 
2271
+ #: templates/forms/deactivation/form.php:66
2272
  msgid "Deactivate"
2273
  msgstr ""
2274
 
2275
+ #: templates/forms/deactivation/form.php:68
2276
  msgid "Activate %s"
2277
  msgstr ""
2278
 
2279
+ #: templates/forms/deactivation/form.php:80
2280
+ msgid "Quick Feedback"
2281
  msgstr ""
2282
 
2283
+ #: templates/forms/deactivation/form.php:84
2284
  msgid "If you have a moment, please let us know why you are %s"
2285
  msgstr ""
2286
 
2287
+ #: templates/forms/deactivation/form.php:84
2288
  msgid "deactivating"
2289
  msgstr ""
2290
 
2291
+ #: templates/forms/deactivation/form.php:84
2292
  msgid "switching"
2293
  msgstr ""
2294
 
2295
+ #: templates/forms/deactivation/form.php:332
2296
  msgid "Submit & %s"
2297
  msgstr ""
2298
 
2299
+ #: templates/forms/deactivation/form.php:353
2300
  msgid "Kindly tell us the reason so we can improve."
2301
  msgstr ""
2302
 
2303
+ #: templates/forms/deactivation/form.php:478
2304
  msgid "Yes - %s"
2305
  msgstr ""
2306
 
2307
+ #: templates/forms/deactivation/form.php:485
2308
  msgid "Skip & %s"
2309
  msgstr ""
2310
 
vendor/freemius/start.php CHANGED
@@ -15,7 +15,7 @@
15
  *
16
  * @var string
17
  */
18
- $this_sdk_version = '2.1.2';
19
 
20
  #region SDK Selection Logic --------------------------------------------------------------------
21
 
@@ -44,9 +44,16 @@
44
  * @author Vova Feldman (@svovaf)
45
  * @since 1.2.2.6
46
  */
47
- $file_path = fs_normalize_path( __FILE__ );
48
- $fs_root_path = dirname( $file_path );
49
- $themes_directory = get_theme_root();
 
 
 
 
 
 
 
50
  $themes_directory_name = basename( $themes_directory );
51
  $theme_candidate_basename = basename( dirname( $fs_root_path ) ) . '/' . basename( $fs_root_path );
52
 
@@ -99,8 +106,8 @@
99
  * @since 1.2.1.7
100
  */
101
  $has_changes = false;
102
- foreach ( $fs_active_plugins->plugins as $sdk_path => &$data ) {
103
- if ( ! file_exists( WP_PLUGIN_DIR . '/' . $sdk_path ) ) {
104
  unset( $fs_active_plugins->plugins[ $sdk_path ] );
105
  $has_changes = true;
106
  }
@@ -120,6 +127,10 @@
120
  require_once dirname( __FILE__ ) . '/includes/supplements/fs-essential-functions-1.1.7.1.php';
121
  }
122
 
 
 
 
 
123
  // Update current SDK info based on the SDK path.
124
  if ( ! isset( $fs_active_plugins->plugins[ $this_sdk_relative_path ] ) ||
125
  $this_sdk_version != $fs_active_plugins->plugins[ $this_sdk_relative_path ]->version
@@ -205,7 +216,7 @@
205
  $sdk_starter_path = fs_normalize_path( WP_PLUGIN_DIR . '/' . $this_sdk_relative_path . '/start.php' );
206
  } else {
207
  $sdk_starter_path = fs_normalize_path(
208
- get_theme_root()
209
  . '/'
210
  . str_replace( "../{$themes_directory_name}/", '', $this_sdk_relative_path )
211
  . '/start.php' );
@@ -267,7 +278,7 @@
267
 
268
  $plugins_or_theme_dir_path = ( ! isset( $newest_sdk->type ) || 'theme' !== $newest_sdk->type ) ?
269
  WP_PLUGIN_DIR :
270
- get_theme_root();
271
 
272
  $newest_sdk_starter = fs_normalize_path(
273
  $plugins_or_theme_dir_path
@@ -375,7 +386,7 @@
375
  }
376
 
377
  $plugins_or_theme_dir_path = fs_normalize_path( trailingslashit( $is_theme ?
378
- get_theme_root() :
379
  WP_PLUGIN_DIR ) );
380
 
381
  if ( 0 === strpos( $file_path, $plugins_or_theme_dir_path ) ) {
15
  *
16
  * @var string
17
  */
18
+ $this_sdk_version = '2.2.4';
19
 
20
  #region SDK Selection Logic --------------------------------------------------------------------
21
 
44
  * @author Vova Feldman (@svovaf)
45
  * @since 1.2.2.6
46
  */
47
+ $file_path = fs_normalize_path( __FILE__ );
48
+ $fs_root_path = dirname( $file_path );
49
+ /**
50
+ * Get the themes directory where the active theme is located (not passing the stylesheet will make WordPress
51
+ * assume that the themes directory is inside `wp-content`.
52
+ *
53
+ * @author Leo Fajardo (@leorw)
54
+ * @since 2.2.3
55
+ */
56
+ $themes_directory = get_theme_root( get_stylesheet() );
57
  $themes_directory_name = basename( $themes_directory );
58
  $theme_candidate_basename = basename( dirname( $fs_root_path ) ) . '/' . basename( $fs_root_path );
59
 
106
  * @since 1.2.1.7
107
  */
108
  $has_changes = false;
109
+ foreach ( $fs_active_plugins->plugins as $sdk_path => $data ) {
110
+ if ( ! file_exists( ( isset( $data->type ) && 'theme' === $data->type ? $themes_directory : WP_PLUGIN_DIR ) . '/' . $sdk_path ) ) {
111
  unset( $fs_active_plugins->plugins[ $sdk_path ] );
112
  $has_changes = true;
113
  }
127
  require_once dirname( __FILE__ ) . '/includes/supplements/fs-essential-functions-1.1.7.1.php';
128
  }
129
 
130
+ if ( ! function_exists( 'fs_get_plugins' ) ) {
131
+ require_once dirname( __FILE__ ) . '/includes/supplements/fs-essential-functions-2.2.1.php';
132
+ }
133
+
134
  // Update current SDK info based on the SDK path.
135
  if ( ! isset( $fs_active_plugins->plugins[ $this_sdk_relative_path ] ) ||
136
  $this_sdk_version != $fs_active_plugins->plugins[ $this_sdk_relative_path ]->version
216
  $sdk_starter_path = fs_normalize_path( WP_PLUGIN_DIR . '/' . $this_sdk_relative_path . '/start.php' );
217
  } else {
218
  $sdk_starter_path = fs_normalize_path(
219
+ $themes_directory
220
  . '/'
221
  . str_replace( "../{$themes_directory_name}/", '', $this_sdk_relative_path )
222
  . '/start.php' );
278
 
279
  $plugins_or_theme_dir_path = ( ! isset( $newest_sdk->type ) || 'theme' !== $newest_sdk->type ) ?
280
  WP_PLUGIN_DIR :
281
+ $themes_directory;
282
 
283
  $newest_sdk_starter = fs_normalize_path(
284
  $plugins_or_theme_dir_path
386
  }
387
 
388
  $plugins_or_theme_dir_path = fs_normalize_path( trailingslashit( $is_theme ?
389
+ $themes_directory :
390
  WP_PLUGIN_DIR ) );
391
 
392
  if ( 0 === strpos( $file_path, $plugins_or_theme_dir_path ) ) {
vendor/freemius/templates/account.php CHANGED
@@ -76,29 +76,33 @@
76
  $query_params['tabs'] = 'true';
77
  }
78
 
79
- // Aliases.
80
- $download_latest_text = fs_text_x_inline( 'Download Latest', 'as download latest version', 'download-latest', $slug );
81
- $downgrade_x_confirm_text = fs_text_inline( 'Downgrading your plan will immediately stop all future recurring payments and your %s plan license will expire in %s.', 'downgrade-x-confirm', $slug );
82
- $cancel_trial_confirm_text = fs_text_inline( 'Cancelling the trial will immediately block access to all premium features. Are you sure?', 'cancel-trial-confirm', $slug );
83
- $after_downgrade_non_blocking_text = fs_text_inline( 'You can still enjoy all %s features but you will not have access to %s updates and support.', 'after-downgrade-non-blocking', $slug );
84
- $after_downgrade_blocking_text = fs_text_inline( 'Once your license expires you can still use the Free version but you will NOT have access to the %s features.', 'after-downgrade-blocking', $slug );
85
- /* translators: %s: Plan title (e.g. "Professional") */
86
- $activate_plan_text = fs_text_inline( 'Activate %s Plan', 'activate-x-plan', $slug );
87
- $version_text = fs_text_x_inline( 'Version', 'product version', 'version', $slug );
88
- /* translators: %s: Time period (e.g. Auto renews in "2 months") */
89
- $renews_in_text = fs_text_inline( 'Auto renews in %s', 'renews-in', $slug );
90
- /* translators: %s: Time period (e.g. Expires in "2 months") */
91
- $expires_in_text = fs_text_inline( 'Expires in %s', 'expires-in', $slug );
92
- $sync_license_text = fs_text_x_inline( 'Sync License', 'as synchronize license', 'sync-license', $slug );
93
- $cancel_trial_text = fs_text_inline( 'Cancel Trial', 'cancel-trial', $slug );
94
- $change_plan_text = fs_text_inline( 'Change Plan', 'change-plan', $slug );
95
- $upgrade_text = fs_text_x_inline( 'Upgrade', 'verb', 'upgrade', $slug );
96
- $addons_text = fs_text_inline( 'Add-Ons', 'add-ons', $slug );
97
- $downgrade_text = fs_text_x_inline( 'Downgrade', 'verb', 'downgrade', $slug );
98
- $trial_text = fs_text_x_inline( 'Trial', 'trial period', 'trial', $slug );
99
- $free_text = fs_text_inline( 'Free', 'free', $slug );
100
- $activate_text = fs_text_inline( 'Activate', 'activate', $slug );
101
- $plan_text = fs_text_x_inline( 'Plan', 'as product pricing plan', 'plan', $slug );
 
 
 
 
102
 
103
  $show_plan_row = true;
104
  $show_license_row = is_object( $license );
@@ -203,11 +207,16 @@
203
  <input type="hidden" name="fs_action" value="downgrade_account">
204
  <?php wp_nonce_field( 'downgrade_account' ) ?>
205
  <a href="#"
206
- onclick="if ( confirm('<?php echo esc_attr( sprintf( $downgrade_x_confirm_text, $plan->title, human_time_diff( time(), strtotime( $license->expiration ) ) ) ) ?> <?php if ( ! $license->is_block_features ) {
 
 
 
 
 
207
  echo esc_attr( sprintf( $after_downgrade_non_blocking_text, $plan->title, $fs->get_module_label( true ) ) );
208
  } else {
209
  echo esc_attr( sprintf( $after_downgrade_blocking_text, $plan->title ) );
210
- }?> <?php fs_esc_attr_echo_inline( 'Are you sure you want to proceed?', 'proceed-confirmation', $slug ) ?>') ) this.parentNode.submit(); return false;"><i class="dashicons dashicons-download"></i> <?php echo esc_html( $fs->is_only_premium() ? fs_text_inline( 'Cancel Subscription', 'cancel-subscription', $slug ) : $downgrade_text ) ?></a>
211
  </form>
212
  </li>
213
  <li>&nbsp;&bull;&nbsp;</li>
@@ -224,8 +233,7 @@
224
  <form action="<?php echo $fs->_get_admin_page_url( 'account' ) ?>" method="POST">
225
  <input type="hidden" name="fs_action" value="cancel_trial">
226
  <?php wp_nonce_field( 'cancel_trial' ) ?>
227
- <a href="#"
228
- onclick="if (confirm('<?php echo esc_attr( $cancel_trial_confirm_text ) ?>')) this.parentNode.submit(); return false;"><i
229
  class="dashicons dashicons-download"></i> <?php echo esc_html( $cancel_trial_text ) ?></a>
230
  </form>
231
  </li>
@@ -603,6 +611,7 @@
603
  </div>
604
  </div>
605
  </div>
 
606
  <script type="text/javascript">
607
  (function ($) {
608
  var setLoading = function ($this, label) {
@@ -665,12 +674,56 @@
665
  setLoading($(this), '<?php fs_esc_js_echo_inline('Activating', 'activating' ) ?>...');
666
  });
667
 
668
- $('.fs-deactivate-license').click(function () {
669
- if (confirm('<?php fs_esc_attr_echo_inline( 'Deactivating your license will block all premium features, but will enable activating the license on another site. Are you sure you want to proceed?', 'deactivate-license-confirm', $slug ) ?>')) {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
670
  var $this = $(this);
671
 
672
- setLoading($this, '<?php fs_esc_js_echo_inline('Deactivating', 'deactivating' ) ?>...');
673
- $this[0].parentNode.submit();
 
 
 
 
674
  }
675
 
676
  return false;
76
  $query_params['tabs'] = 'true';
77
  }
78
 
79
+ // Aliases.
80
+ $download_latest_text = fs_text_x_inline( 'Download Latest', 'as download latest version', 'download-latest', $slug );
81
+ $downgrading_plan_text = fs_text_inline( 'Downgrading your plan', 'downgrading-plan', $slug );
82
+ $cancelling_subscription_text = fs_text_inline( 'Cancelling the subscription', 'cancelling-subscription', $slug );
83
+ /* translators: %1s: Either 'Downgrading your plan' or 'Cancelling the subscription' */
84
+ $downgrade_x_confirm_text = fs_text_inline( '%1s will immediately stop all future recurring payments and your %s plan license will expire in %s.', 'downgrade-x-confirm', $slug );
85
+ $prices_increase_text = fs_text_inline( 'Please note that we will not be able to grandfather outdated pricing for renewals/new subscriptions after a cancellation. If you choose to renew the subscription manually in the future, after a price increase, which typically occurs once a year, you will be charged the updated price.', 'pricing-increase-warning', $slug );
86
+ $cancel_trial_confirm_text = fs_text_inline( 'Cancelling the trial will immediately block access to all premium features. Are you sure?', 'cancel-trial-confirm', $slug );
87
+ $after_downgrade_non_blocking_text = fs_text_inline( 'You can still enjoy all %s features but you will not have access to %s security & feature updates, nor support.', 'after-downgrade-non-blocking', $slug );
88
+ $after_downgrade_blocking_text = fs_text_inline( 'Once your license expires you can still use the Free version but you will NOT have access to the %s features.', 'after-downgrade-blocking', $slug );
89
+ /* translators: %s: Plan title (e.g. "Professional") */
90
+ $activate_plan_text = fs_text_inline( 'Activate %s Plan', 'activate-x-plan', $slug );
91
+ $version_text = fs_text_x_inline( 'Version', 'product version', 'version', $slug );
92
+ /* translators: %s: Time period (e.g. Auto renews in "2 months") */
93
+ $renews_in_text = fs_text_inline( 'Auto renews in %s', 'renews-in', $slug );
94
+ /* translators: %s: Time period (e.g. Expires in "2 months") */
95
+ $expires_in_text = fs_text_inline( 'Expires in %s', 'expires-in', $slug );
96
+ $sync_license_text = fs_text_x_inline( 'Sync License', 'as synchronize license', 'sync-license', $slug );
97
+ $cancel_trial_text = fs_text_inline( 'Cancel Trial', 'cancel-trial', $slug );
98
+ $change_plan_text = fs_text_inline( 'Change Plan', 'change-plan', $slug );
99
+ $upgrade_text = fs_text_x_inline( 'Upgrade', 'verb', 'upgrade', $slug );
100
+ $addons_text = fs_text_inline( 'Add-Ons', 'add-ons', $slug );
101
+ $downgrade_text = fs_text_x_inline( 'Downgrade', 'verb', 'downgrade', $slug );
102
+ $trial_text = fs_text_x_inline( 'Trial', 'trial period', 'trial', $slug );
103
+ $free_text = fs_text_inline( 'Free', 'free', $slug );
104
+ $activate_text = fs_text_inline( 'Activate', 'activate', $slug );
105
+ $plan_text = fs_text_x_inline( 'Plan', 'as product pricing plan', 'plan', $slug );
106
 
107
  $show_plan_row = true;
108
  $show_license_row = is_object( $license );
207
  <input type="hidden" name="fs_action" value="downgrade_account">
208
  <?php wp_nonce_field( 'downgrade_account' ) ?>
209
  <a href="#"
210
+ onclick="if ( confirm('<?php echo esc_attr( sprintf(
211
+ $downgrade_x_confirm_text,
212
+ ( $fs->is_only_premium() ? $cancelling_subscription_text : $downgrading_plan_text ),
213
+ $plan->title,
214
+ human_time_diff( time(), strtotime( $license->expiration ) )
215
+ ) ) ?> <?php if ( ! $license->is_block_features ) {
216
  echo esc_attr( sprintf( $after_downgrade_non_blocking_text, $plan->title, $fs->get_module_label( true ) ) );
217
  } else {
218
  echo esc_attr( sprintf( $after_downgrade_blocking_text, $plan->title ) );
219
+ }?> <?php echo esc_attr( $prices_increase_text ) ?> <?php fs_esc_attr_echo_inline( 'Are you sure you want to proceed?', 'proceed-confirmation', $slug ) ?>') ) this.parentNode.submit(); return false;"><i class="dashicons dashicons-download"></i> <?php echo esc_html( $fs->is_only_premium() ? fs_text_inline( 'Cancel Subscription', 'cancel-subscription', $slug ) : $downgrade_text ) ?></a>
220
  </form>
221
  </li>
222
  <li>&nbsp;&bull;&nbsp;</li>
233
  <form action="<?php echo $fs->_get_admin_page_url( 'account' ) ?>" method="POST">
234
  <input type="hidden" name="fs_action" value="cancel_trial">
235
  <?php wp_nonce_field( 'cancel_trial' ) ?>
236
+ <a href="#" class="fs-cancel-trial"><i
 
237
  class="dashicons dashicons-download"></i> <?php echo esc_html( $cancel_trial_text ) ?></a>
238
  </form>
239
  </li>
611
  </div>
612
  </div>
613
  </div>
614
+ <?php $fs->_maybe_add_subscription_cancellation_dialog_box( true ) ?>
615
  <script type="text/javascript">
616
  (function ($) {
617
  var setLoading = function ($this, label) {
674
  setLoading($(this), '<?php fs_esc_js_echo_inline('Activating', 'activating' ) ?>...');
675
  });
676
 
677
+ var $deactivateLicenseOrCancelTrial = $( '.fs-deactivate-license, .fs-cancel-trial' ),
678
+ $subscriptionCancellationModal = $( '.fs-modal-subscription-cancellation-<?php echo $fs->get_id() ?>' );
679
+
680
+ if ( 0 !== $subscriptionCancellationModal.length ) {
681
+ $subscriptionCancellationModal.on( '<?php echo $fs->get_action_tag( 'subscription_cancellation_action' ) ?>', function( evt, cancelSubscription ) {
682
+ setLoading(
683
+ $deactivateLicenseOrCancelTrial,
684
+ ( ! $deactivateLicenseOrCancelTrial.hasClass( 'fs-cancel-trial' ) ?
685
+ '<?php fs_esc_js_echo_inline( 'Deactivating', 'deactivating', $slug ) ?>' :
686
+ '<?php echo esc_html( sprintf( fs_text_inline( 'Cancelling %s', 'cancelling-x', $slug ), fs_text_inline( 'trial', 'trial', $slug ) ) ) ?>' ) + '...'
687
+ );
688
+
689
+ $subscriptionCancellationModal.find( '.fs-modal-footer .button' ).addClass( 'disabled' );
690
+ $deactivateLicenseOrCancelTrial.unbind( 'click' );
691
+
692
+ if ( false === cancelSubscription || $deactivateLicenseOrCancelTrial.hasClass( 'fs-cancel-trial' ) ) {
693
+ $subscriptionCancellationModal.find( '.fs-modal-footer .button-primary' ).text( $deactivateLicenseOrCancelTrial.text() );
694
+
695
+ $deactivateLicenseOrCancelTrial[0].parentNode.submit();
696
+ } else {
697
+ var $form = $( 'input[value="downgrade_account"],input[value="cancel_trial"]' ).parent();
698
+ $form.prepend( '<input type="hidden" name="deactivate_license" value="true" />' );
699
+
700
+ $subscriptionCancellationModal.find( '.fs-modal-footer .button-primary' ).text( '<?php echo esc_js( sprintf(
701
+ fs_text_inline( 'Cancelling %s...', 'cancelling-x' , $slug ),
702
+ $is_paid_trial ?
703
+ fs_text_inline( 'trial', 'trial', $slug ) :
704
+ fs_text_inline( 'subscription', 'subscription', $slug )
705
+ ) ) ?>' );
706
+
707
+ $form.submit();
708
+ }
709
+ });
710
+ }
711
+
712
+ $deactivateLicenseOrCancelTrial.click(function() {
713
+ var $this = $( this );
714
+ if ( $this.hasClass( 'fs-cancel-trial' ) ) {
715
+ $subscriptionCancellationModal.find( '.fs-modal-panel' ).find( 'ul.subscription-actions, .fs-price-increase-warning' ).remove();
716
+ $subscriptionCancellationModal.find( '.fs-modal-panel > p' ).text( <?php echo json_encode( $cancel_trial_confirm_text ) ?> );
717
+ $subscriptionCancellationModal.trigger( 'showModal' );
718
+ } else if (confirm('<?php fs_esc_attr_echo_inline( 'Deactivating your license will block all premium features, but will enable activating the license on another site. Are you sure you want to proceed?', 'deactivate-license-confirm', $slug ) ?>')) {
719
  var $this = $(this);
720
 
721
+ if ( 0 !== $subscriptionCancellationModal.length ) {
722
+ $subscriptionCancellationModal.trigger( 'showModal' );
723
+ } else {
724
+ setLoading( $this, '<?php fs_esc_js_echo_inline( 'Deactivating', 'deactivating', $slug ) ?>...' );
725
+ $this[0].parentNode.submit();
726
+ }
727
  }
728
 
729
  return false;
vendor/freemius/templates/account/partials/addon.php CHANGED
@@ -1,345 +1,350 @@
1
- <?php
2
- /**
3
- * @var array $VARS
4
- * @var Freemius $fs
5
- */
6
- $fs = $VARS['parent_fs'];
7
- $addon_id = $VARS['addon_id'];
8
- $odd = $VARS['odd'];
9
- $slug = $fs->get_slug();
10
-
11
-
12
- $addon = $fs->get_addon( $addon_id );
13
- $is_addon_activated = $fs->is_addon_activated( $addon_id );
14
- $is_addon_connected = $fs->is_addon_connected( $addon_id );
15
-
16
- $fs_addon = $is_addon_connected ?
17
- freemius( $addon_id ) :
18
- false;
19
-
20
- // Aliases.
21
- $download_latest_text = fs_text_x_inline( 'Download Latest', 'as download latest version', 'download-latest', $slug );
22
- $downgrade_x_confirm_text = fs_text_inline( 'Downgrading your plan will immediately stop all future recurring payments and your %s plan license will expire in %s.', 'downgrade-x-confirm', $slug );
23
- $cancel_trial_confirm_text = fs_text_inline( 'Cancelling the trial will immediately block access to all premium features. Are you sure?', 'cancel-trial-confirm', $slug );
24
- $after_downgrade_non_blocking_text = fs_text_inline( 'You can still enjoy all %s features but you will not have access to %s updates and support.', 'after-downgrade-non-blocking', $slug );
25
- $after_downgrade_blocking_text = fs_text_inline( 'Once your license expires you can still use the Free version but you will NOT have access to the %s features.', 'after-downgrade-blocking', $slug );
26
- /* translators: %s: Plan title (e.g. "Professional") */
27
- $activate_plan_text = fs_text_inline( 'Activate %s Plan', 'activate-x-plan', $slug );
28
- $version_text = fs_text_x_inline( 'Version', 'product version', 'version', $slug );
29
- /* translators: %s: Time period (e.g. Auto renews in "2 months") */
30
- $renews_in_text = fs_text_inline( 'Auto renews in %s', 'renews-in', $slug );
31
- /* translators: %s: Time period (e.g. Expires in "2 months") */
32
- $expires_in_text = fs_text_inline( 'Expires in %s', 'expires-in', $slug );
33
- $sync_license_text = fs_text_x_inline( 'Sync License', 'as synchronize license', 'sync-license', $slug );
34
- $cancel_trial_text = fs_text_inline( 'Cancel Trial', 'cancel-trial', $slug );
35
- $change_plan_text = fs_text_inline( 'Change Plan', 'change-plan', $slug );
36
- $upgrade_text = fs_text_x_inline( 'Upgrade', 'verb', 'upgrade', $slug );
37
- $addons_text = fs_text_inline( 'Add-Ons', 'add-ons', $slug );
38
- $downgrade_text = fs_text_x_inline( 'Downgrade', 'verb', 'downgrade', $slug );
39
- $trial_text = fs_text_x_inline( 'Trial', 'trial period', 'trial', $slug );
40
- $free_text = fs_text_inline( 'Free', 'free', $slug );
41
- $activate_text = fs_text_inline( 'Activate', 'activate', $slug );
42
- $plan_text = fs_text_x_inline( 'Plan', 'as product pricing plan', 'plan', $slug );
43
-
44
- // Defaults.
45
- $plan = null;
46
- $is_paid_trial = false;
47
- $license = null;
48
- $site = null;
49
- $is_active_subscription = false;
50
- $subscription = null;
51
- $is_paying = false;
52
-
53
- if ( is_object( $fs_addon ) ) {
54
- $is_paying = $fs_addon->is_paying();
55
- $user = $fs_addon->get_user();
56
- $site = $fs_addon->get_site();
57
- $license = $fs_addon->_get_license();
58
- $subscription = ( is_object( $license ) ?
59
- $fs_addon->_get_subscription( $license->id ) :
60
- null );
61
- $plan = $fs_addon->get_plan();
62
- $is_active_subscription = ( is_object( $subscription ) && $subscription->is_active() );
63
- $is_paid_trial = $fs_addon->is_paid_trial();
64
- $show_upgrade = ( $fs_addon->has_paid_plan() && ! $is_paying && ! $is_paid_trial && ! $fs_addon->_has_premium_license() );
65
- $is_current_license_expired = is_object( $license ) && $license->is_expired();
66
- }
67
- ?>
68
- <tr<?php if ( $odd ) {
69
- echo ' class="alternate"';
70
- } ?>>
71
- <td>
72
- <!-- Title -->
73
- <?php echo $addon->title ?>
74
- </td>
75
- <?php if ( $is_addon_connected ) : ?>
76
- <!-- ID -->
77
- <td><?php echo $site->id ?></td>
78
- <!--/ ID -->
79
-
80
- <!-- Version -->
81
- <td><?php echo $fs_addon->get_plugin_version() ?></td>
82
- <!--/ Version -->
83
-
84
- <!-- Plan Title -->
85
- <td><?php echo strtoupper( is_string( $plan->name ) ? $plan->title : $free_text ) ?></td>
86
- <!--/ Plan Title -->
87
-
88
- <?php if ( $fs_addon->is_trial() || is_object( $license ) ) : ?>
89
-
90
- <!-- Expiration -->
91
- <td>
92
- <?php
93
- $tags = array();
94
-
95
- if ( $fs_addon->is_trial() ) {
96
- $tags[] = array( 'label' => $trial_text, 'type' => 'success' );
97
-
98
- $tags[] = array(
99
- 'label' => sprintf(
100
- ( $is_paid_trial ?
101
- $renews_in_text :
102
- $expires_in_text ),
103
- human_time_diff( time(), strtotime( $site->trial_ends ) )
104
- ),
105
- 'type' => ( $is_paid_trial ? 'success' : 'warn' )
106
- );
107
- } else {
108
- if ( is_object( $license ) ) {
109
- if ( $license->is_cancelled ) {
110
- $tags[] = array(
111
- 'label' => fs_text_inline( 'Cancelled', 'cancelled', $slug ),
112
- 'type' => 'error'
113
- );
114
- } else if ( $license->is_expired() ) {
115
- $tags[] = array(
116
- 'label' => fs_text_inline( 'Expired', 'expired', $slug ),
117
- 'type' => 'error'
118
- );
119
- } else if ( $license->is_lifetime() ) {
120
- $tags[] = array(
121
- 'label' => fs_text_inline( 'No expiration', 'no-expiration', $slug ),
122
- 'type' => 'success'
123
- );
124
- } else if ( ! $is_active_subscription && ! $license->is_first_payment_pending() ) {
125
- $tags[] = array(
126
- 'label' => sprintf( $expires_in_text, human_time_diff( time(), strtotime( $license->expiration ) ) ),
127
- 'type' => 'warn'
128
- );
129
- } else if ( $is_active_subscription && ! $subscription->is_first_payment_pending() ) {
130
- $tags[] = array(
131
- 'label' => sprintf( $renews_in_text, human_time_diff( time(), strtotime( $subscription->next_payment ) ) ),
132
- 'type' => 'success'
133
- );
134
- }
135
- }
136
- }
137
-
138
- foreach ( $tags as $t ) {
139
- printf( '<label class="fs-tag fs-%s">%s</label>' . "\n", $t['type'], $t['label'] );
140
- }
141
- ?>
142
- </td>
143
- <!--/ Expiration -->
144
-
145
- <?php endif ?>
146
-
147
- <?php
148
- $buttons = array();
149
- if ( $is_addon_activated ) {
150
- if ( $is_paying ) {
151
- $buttons[] = fs_ui_get_action_button(
152
- $fs->get_id(),
153
- 'account',
154
- 'deactivate_license',
155
- fs_text_inline( 'Deactivate License', 'deactivate-license', $slug ),
156
- '',
157
- array( 'plugin_id' => $addon_id ),
158
- false
159
- );
160
-
161
- $human_readable_license_expiration = human_time_diff( time(), strtotime( $license->expiration ) );
162
- $downgrade_confirmation_message = sprintf(
163
- $downgrade_x_confirm_text,
164
- $plan->title,
165
- $human_readable_license_expiration
166
- );
167
-
168
- $after_downgrade_message = ! $license->is_block_features ?
169
- sprintf( $after_downgrade_non_blocking_text, $plan->title, $fs_addon->get_module_label( true ) ) :
170
- sprintf( $after_downgrade_blocking_text, $plan->title );
171
-
172
- if ( ! $license->is_lifetime() && $is_active_subscription ) {
173
- $buttons[] = fs_ui_get_action_button(
174
- $fs->get_id(),
175
- 'account',
176
- 'downgrade_account',
177
- esc_html( $fs_addon->is_only_premium() ? fs_text_inline( 'Cancel Subscription', 'cancel-subscription', $slug ) : $downgrade_text ),
178
- '',
179
- array( 'plugin_id' => $addon_id ),
180
- false,
181
- false,
182
- false,
183
- ( $downgrade_confirmation_message . ' ' . $after_downgrade_message ),
184
- 'POST'
185
- );
186
- }
187
- } else if ( $is_paid_trial ) {
188
- $buttons[] = fs_ui_get_action_button(
189
- $fs->get_id(),
190
- 'account',
191
- 'cancel_trial',
192
- esc_html( $cancel_trial_text ),
193
- '',
194
- array( 'plugin_id' => $addon_id ),
195
- false,
196
- false,
197
- 'dashicons dashicons-download',
198
- $cancel_trial_confirm_text,
199
- 'POST'
200
- );
201
- } else {
202
- $premium_license = $fs_addon->_get_available_premium_license();
203
-
204
- if ( is_object( $premium_license ) ) {
205
- $premium_plan = $fs_addon->_get_plan_by_id( $premium_license->plan_id );
206
- $site = $fs_addon->get_site();
207
-
208
- $buttons[] = fs_ui_get_action_button(
209
- $fs->get_id(),
210
- 'account',
211
- 'activate_license',
212
- esc_html( sprintf( $activate_plan_text, $premium_plan->title, ( $site->is_localhost() && $premium_license->is_free_localhost ) ? '[localhost]' : ( 1 < $premium_license->left() ? $premium_license->left() . ' left' : '' ) ) ),
213
- '',
214
- array(
215
- 'plugin_id' => $addon_id,
216
- 'license_id' => $premium_license->id,
217
- )
218
- );
219
- }
220
- }
221
-
222
- if ( 0 == count( $buttons ) ) {
223
- if ( $show_upgrade && $fs_addon->is_premium() ) {
224
- $fs_addon->_add_license_activation_dialog_box();
225
-
226
- $buttons[] = fs_ui_get_action_button(
227
- $fs->get_id(),
228
- 'account',
229
- 'activate_license',
230
- fs_esc_html_inline( 'Activate License', 'activate-license', $slug ),
231
- 'activate-license-trigger ' . $fs_addon->get_unique_affix(),
232
- array(
233
- 'plugin_id' => $addon_id,
234
- ),
235
- false,
236
- true
237
- );
238
- }
239
-
240
- // Add sync license only if non of the other CTAs are visible.
241
- $buttons[] = fs_ui_get_action_button(
242
- $fs->get_id(),
243
- 'account',
244
- $fs->get_unique_affix() . '_sync_license',
245
- esc_html( $sync_license_text ),
246
- '',
247
- array( 'plugin_id' => $addon_id ),
248
- false,
249
- true
250
- );
251
-
252
- }
253
- } else if ( ! $show_upgrade ) {
254
- if ( $fs->is_addon_installed( $addon_id ) ) {
255
- $addon_file = $fs->get_addon_basename( $addon_id );
256
- $buttons[] = sprintf(
257
- '<a class="button button-primary edit" href="%s" title="%s">%s</a>',
258
- wp_nonce_url( 'plugins.php?action=activate&amp;plugin=' . $addon_file, 'activate-plugin_' . $addon_file ),
259
- fs_esc_attr_inline( 'Activate this add-on', 'activate-this-addon', $slug ),
260
- $activate_text
261
- );
262
- } else {
263
- if ( $fs->is_allowed_to_install() ) {
264
- $buttons[] = sprintf(
265
- '<a class="button button-primary edit" href="%s">%s</a>',
266
- wp_nonce_url( self_admin_url( 'update.php?action=install-plugin&plugin=' . $addon->slug ), 'install-plugin_' . $addon->slug ),
267
- fs_text_inline( 'Install Now', 'install-now', $slug )
268
- );
269
- } else {
270
- $buttons[] = sprintf(
271
- '<a target="_blank" class="button button-primary edit" href="%s">%s</a>',
272
- $fs->_get_latest_download_local_url( $addon_id ),
273
- esc_html( $download_latest_text )
274
- );
275
- }
276
- }
277
- }
278
-
279
- if ( $show_upgrade ) {
280
- $buttons[] = sprintf( '<a href="%s" class="thickbox button button-small button-primary" aria-label="%s" data-title="%s"><i class="dashicons dashicons-cart"></i> %s</a>',
281
- esc_url( network_admin_url( 'plugin-install.php?tab=plugin-information&parent_plugin_id=' . $fs->get_id() . '&plugin=' . $addon->slug .
282
- '&TB_iframe=true&width=600&height=550' ) ),
283
- esc_attr( sprintf( fs_text_inline( 'More information about %s', 'more-information-about-x', $slug ), $addon->title ) ),
284
- esc_attr( $addon->title ),
285
- ( $fs_addon->has_free_plan() ?
286
- $upgrade_text :
287
- fs_text_x_inline( 'Purchase', 'verb', 'purchase', $slug ) )
288
- );
289
- }
290
-
291
- $buttons_count = count( $buttons );
292
- ?>
293
-
294
- <!-- Actions -->
295
- <td><?php if ( $buttons_count > 1 ) : ?>
296
- <div class="button-group"><?php endif ?>
297
- <?php foreach ( $buttons as $button ) {
298
- echo $button;
299
- } ?>
300
- <?php if ( $buttons_count > 1 ) : ?></div><?php endif ?></td>
301
- <!--/ Actions -->
302
-
303
- <?php else : ?>
304
- <?php // Add-on NOT Installed or was never connected.
305
- ?>
306
- <!-- Action -->
307
- <td colspan="4">
308
- <?php if ( $fs->is_addon_installed( $addon_id ) ) : ?>
309
- <?php $addon_file = $fs->get_addon_basename( $addon_id ) ?>
310
- <a class="button button-primary"
311
- href="<?php echo wp_nonce_url( 'plugins.php?action=activate&amp;plugin=' . $addon_file, 'activate-plugin_' . $addon_file ) ?>"
312
- title="<?php fs_esc_attr_echo_inline( 'Activate this add-on', 'activate-this-addon', $slug ) ?>"
313
- class="edit"><?php echo esc_html( $activate_text ) ?></a>
314
- <?php else : ?>
315
- <?php if ( $fs->is_allowed_to_install() ) : ?>
316
- <a class="button button-primary"
317
- href="<?php echo wp_nonce_url( self_admin_url( 'update.php?action=install-plugin&plugin=' . $addon->slug ), 'install-plugin_' . $addon->slug ) ?>"><?php fs_esc_html_echo_inline( 'Install Now', 'install-now', $slug ) ?></a>
318
- <?php else : ?>
319
- <a target="_blank" class="button button-primary"
320
- href="<?php echo $fs->_get_latest_download_local_url( $addon_id ) ?>"><?php echo esc_html( $download_latest_text ) ?></a>
321
- <?php endif ?>
322
- <?php endif ?>
323
- </td>
324
- <!--/ Action -->
325
- <?php endif ?>
326
- <?php if ( ! $is_paying && WP_FS__DEV_MODE ) : ?>
327
- <!-- Optional Delete Action -->
328
- <td>
329
- <?php
330
- if ( $is_addon_activated ) {
331
- fs_ui_action_button(
332
- $fs->get_id(), 'account',
333
- 'delete_account',
334
- fs_text_x_inline( 'Delete', 'verb', 'delete', $slug ),
335
- '',
336
- array( 'plugin_id' => $addon_id ),
337
- false,
338
- $show_upgrade
339
- );
340
- }
341
- ?>
342
- </td>
343
- <!--/ Optional Delete Action -->
344
- <?php endif ?>
 
 
 
 
 
345
  </tr>
1
+ <?php
2
+ /**
3
+ * @var array $VARS
4
+ * @var Freemius $fs
5
+ */
6
+ $fs = $VARS['parent_fs'];
7
+ $addon_id = $VARS['addon_id'];
8
+ $odd = $VARS['odd'];
9
+ $slug = $fs->get_slug();
10
+
11
+
12
+ $addon = $fs->get_addon( $addon_id );
13
+ $is_addon_activated = $fs->is_addon_activated( $addon_id );
14
+ $is_addon_connected = $fs->is_addon_connected( $addon_id );
15
+
16
+ $fs_addon = $is_addon_connected ?
17
+ freemius( $addon_id ) :
18
+ false;
19
+
20
+ // Aliases.
21
+ $download_latest_text = fs_text_x_inline( 'Download Latest', 'as download latest version', 'download-latest', $slug );
22
+ $downgrading_plan_text = fs_text_inline( 'Downgrading your plan', 'downgrading-plan', $slug );
23
+ $cancelling_subscription_text = fs_text_inline( 'Cancelling the subscription', 'cancelling-subscription', $slug );
24
+ /* translators: %1s: Either 'Downgrading your plan' or 'Cancelling the subscription' */
25
+ $downgrade_x_confirm_text = fs_text_inline( '%1s will immediately stop all future recurring payments and your %s plan license will expire in %s.', 'downgrade-x-confirm', $slug );
26
+ $prices_increase_text = fs_text_inline( 'Please note that we will not be able to grandfather outdated pricing for renewals/new subscriptions after a cancellation. If you choose to renew the subscription manually in the future, after a price increase, which typically occurs once a year, you will be charged the updated price.', 'pricing-increase-warning', $slug );
27
+ $cancel_trial_confirm_text = fs_text_inline( 'Cancelling the trial will immediately block access to all premium features. Are you sure?', 'cancel-trial-confirm', $slug );
28
+ $after_downgrade_non_blocking_text = fs_text_inline( 'You can still enjoy all %s features but you will not have access to %s security & feature updates, nor support.', 'after-downgrade-non-blocking', $slug );
29
+ $after_downgrade_blocking_text = fs_text_inline( 'Once your license expires you can still use the Free version but you will NOT have access to the %s features.', 'after-downgrade-blocking', $slug );
30
+ /* translators: %s: Plan title (e.g. "Professional") */
31
+ $activate_plan_text = fs_text_inline( 'Activate %s Plan', 'activate-x-plan', $slug );
32
+ $version_text = fs_text_x_inline( 'Version', 'product version', 'version', $slug );
33
+ /* translators: %s: Time period (e.g. Auto renews in "2 months") */
34
+ $renews_in_text = fs_text_inline( 'Auto renews in %s', 'renews-in', $slug );
35
+ /* translators: %s: Time period (e.g. Expires in "2 months") */
36
+ $expires_in_text = fs_text_inline( 'Expires in %s', 'expires-in', $slug );
37
+ $sync_license_text = fs_text_x_inline( 'Sync License', 'as synchronize license', 'sync-license', $slug );
38
+ $cancel_trial_text = fs_text_inline( 'Cancel Trial', 'cancel-trial', $slug );
39
+ $change_plan_text = fs_text_inline( 'Change Plan', 'change-plan', $slug );
40
+ $upgrade_text = fs_text_x_inline( 'Upgrade', 'verb', 'upgrade', $slug );
41
+ $addons_text = fs_text_inline( 'Add-Ons', 'add-ons', $slug );
42
+ $downgrade_text = fs_text_x_inline( 'Downgrade', 'verb', 'downgrade', $slug );
43
+ $trial_text = fs_text_x_inline( 'Trial', 'trial period', 'trial', $slug );
44
+ $free_text = fs_text_inline( 'Free', 'free', $slug );
45
+ $activate_text = fs_text_inline( 'Activate', 'activate', $slug );
46
+ $plan_text = fs_text_x_inline( 'Plan', 'as product pricing plan', 'plan', $slug );
47
+
48
+ // Defaults.
49
+ $plan = null;
50
+ $is_paid_trial = false;
51
+ $license = null;
52
+ $site = null;
53
+ $is_active_subscription = false;
54
+ $subscription = null;
55
+ $is_paying = false;
56
+
57
+ if ( is_object( $fs_addon ) ) {
58
+ $is_paying = $fs_addon->is_paying();
59
+ $user = $fs_addon->get_user();
60
+ $site = $fs_addon->get_site();
61
+ $license = $fs_addon->_get_license();
62
+ $subscription = ( is_object( $license ) ?
63
+ $fs_addon->_get_subscription( $license->id ) :
64
+ null );
65
+ $plan = $fs_addon->get_plan();
66
+ $is_active_subscription = ( is_object( $subscription ) && $subscription->is_active() );
67
+ $is_paid_trial = $fs_addon->is_paid_trial();
68
+ $show_upgrade = ( $fs_addon->has_paid_plan() && ! $is_paying && ! $is_paid_trial && ! $fs_addon->_has_premium_license() );
69
+ $is_current_license_expired = is_object( $license ) && $license->is_expired();
70
+ }
71
+ ?>
72
+ <tr<?php if ( $odd ) {
73
+ echo ' class="alternate"';
74
+ } ?>>
75
+ <td>
76
+ <!-- Title -->
77
+ <?php echo $addon->title ?>
78
+ </td>
79
+ <?php if ( $is_addon_connected ) : ?>
80
+ <!-- ID -->
81
+ <td><?php echo $site->id ?></td>
82
+ <!--/ ID -->
83
+
84
+ <!-- Version -->
85
+ <td><?php echo $fs_addon->get_plugin_version() ?></td>
86
+ <!--/ Version -->
87
+
88
+ <!-- Plan Title -->
89
+ <td><?php echo strtoupper( is_string( $plan->name ) ? $plan->title : $free_text ) ?></td>
90
+ <!--/ Plan Title -->
91
+
92
+ <?php if ( $fs_addon->is_trial() || is_object( $license ) ) : ?>
93
+
94
+ <!-- Expiration -->
95
+ <td>
96
+ <?php
97
+ $tags = array();
98
+
99
+ if ( $fs_addon->is_trial() ) {
100
+ $tags[] = array( 'label' => $trial_text, 'type' => 'success' );
101
+
102
+ $tags[] = array(
103
+ 'label' => sprintf(
104
+ ( $is_paid_trial ?
105
+ $renews_in_text :
106
+ $expires_in_text ),
107
+ human_time_diff( time(), strtotime( $site->trial_ends ) )
108
+ ),
109
+ 'type' => ( $is_paid_trial ? 'success' : 'warn' )
110
+ );
111
+ } else {
112
+ if ( is_object( $license ) ) {
113
+ if ( $license->is_cancelled ) {
114
+ $tags[] = array(
115
+ 'label' => fs_text_inline( 'Cancelled', 'cancelled', $slug ),
116
+ 'type' => 'error'
117
+ );
118
+ } else if ( $license->is_expired() ) {
119
+ $tags[] = array(
120
+ 'label' => fs_text_inline( 'Expired', 'expired', $slug ),
121
+ 'type' => 'error'
122
+ );
123
+ } else if ( $license->is_lifetime() ) {
124
+ $tags[] = array(
125
+ 'label' => fs_text_inline( 'No expiration', 'no-expiration', $slug ),
126
+ 'type' => 'success'
127
+ );
128
+ } else if ( ! $is_active_subscription && ! $license->is_first_payment_pending() ) {
129
+ $tags[] = array(
130
+ 'label' => sprintf( $expires_in_text, human_time_diff( time(), strtotime( $license->expiration ) ) ),
131
+ 'type' => 'warn'
132
+ );
133
+ } else if ( $is_active_subscription && ! $subscription->is_first_payment_pending() ) {
134
+ $tags[] = array(
135
+ 'label' => sprintf( $renews_in_text, human_time_diff( time(), strtotime( $subscription->next_payment ) ) ),
136
+ 'type' => 'success'
137
+ );
138
+ }
139
+ }
140
+ }
141
+
142
+ foreach ( $tags as $t ) {
143
+ printf( '<label class="fs-tag fs-%s">%s</label>' . "\n", $t['type'], $t['label'] );
144
+ }
145
+ ?>
146
+ </td>
147
+ <!--/ Expiration -->
148
+
149
+ <?php endif ?>
150
+
151
+ <?php
152
+ $buttons = array();
153
+ if ( $is_addon_activated ) {
154
+ if ( $is_paying ) {
155
+ $buttons[] = fs_ui_get_action_button(
156
+ $fs->get_id(),
157
+ 'account',
158
+ 'deactivate_license',
159
+ fs_text_inline( 'Deactivate License', 'deactivate-license', $slug ),
160
+ '',
161
+ array( 'plugin_id' => $addon_id ),
162
+ false
163
+ );
164
+
165
+ $human_readable_license_expiration = human_time_diff( time(), strtotime( $license->expiration ) );
166
+ $downgrade_confirmation_message = sprintf(
167
+ $downgrade_x_confirm_text,
168
+ ( $fs_addon->is_only_premium() ? $cancelling_subscription_text : $downgrading_plan_text ),
169
+ $plan->title,
170
+ $human_readable_license_expiration
171
+ );
172
+
173
+ $after_downgrade_message = ! $license->is_block_features ?
174
+ sprintf( $after_downgrade_non_blocking_text, $plan->title, $fs_addon->get_module_label( true ) ) :
175
+ sprintf( $after_downgrade_blocking_text, $plan->title );
176
+
177
+ if ( ! $license->is_lifetime() && $is_active_subscription ) {
178
+ $buttons[] = fs_ui_get_action_button(
179
+ $fs->get_id(),
180
+ 'account',
181
+ 'downgrade_account',
182
+ esc_html( $fs_addon->is_only_premium() ? fs_text_inline( 'Cancel Subscription', 'cancel-subscription', $slug ) : $downgrade_text ),
183
+ '',
184
+ array( 'plugin_id' => $addon_id ),
185
+ false,
186
+ false,
187
+ false,
188
+ ( $downgrade_confirmation_message . ' ' . $after_downgrade_message . ' ' . $prices_increase_text ),
189
+ 'POST'
190
+ );
191
+ }
192
+ } else if ( $is_paid_trial ) {
193
+ $buttons[] = fs_ui_get_action_button(
194
+ $fs->get_id(),
195
+ 'account',
196
+ 'cancel_trial',
197
+ esc_html( $cancel_trial_text ),
198
+ '',
199
+ array( 'plugin_id' => $addon_id ),
200
+ false,
201
+ false,
202
+ 'dashicons dashicons-download',
203
+ $cancel_trial_confirm_text,
204
+ 'POST'
205
+ );
206
+ } else {
207
+ $premium_license = $fs_addon->_get_available_premium_license();
208
+
209
+ if ( is_object( $premium_license ) ) {
210
+ $premium_plan = $fs_addon->_get_plan_by_id( $premium_license->plan_id );
211
+ $site = $fs_addon->get_site();
212
+
213
+ $buttons[] = fs_ui_get_action_button(
214
+ $fs->get_id(),
215
+ 'account',
216
+ 'activate_license',
217
+ esc_html( sprintf( $activate_plan_text, $premium_plan->title, ( $site->is_localhost() && $premium_license->is_free_localhost ) ? '[localhost]' : ( 1 < $premium_license->left() ? $premium_license->left() . ' left' : '' ) ) ),
218
+ '',
219
+ array(
220
+ 'plugin_id' => $addon_id,
221
+ 'license_id' => $premium_license->id,
222
+ )
223
+ );
224
+ }
225
+ }
226
+
227
+ if ( 0 == count( $buttons ) ) {
228
+ if ( $show_upgrade && $fs_addon->is_premium() ) {
229
+ $fs_addon->_add_license_activation_dialog_box();
230
+
231
+ $buttons[] = fs_ui_get_action_button(
232
+ $fs->get_id(),
233
+ 'account',
234
+ 'activate_license',
235
+ fs_esc_html_inline( 'Activate License', 'activate-license', $slug ),
236
+ 'activate-license-trigger ' . $fs_addon->get_unique_affix(),
237
+ array(
238
+ 'plugin_id' => $addon_id,
239
+ ),
240
+ false,
241
+ true
242
+ );
243
+ }
244
+
245
+ // Add sync license only if non of the other CTAs are visible.
246
+ $buttons[] = fs_ui_get_action_button(
247
+ $fs->get_id(),
248
+ 'account',
249
+ $fs->get_unique_affix() . '_sync_license',
250
+ esc_html( $sync_license_text ),
251
+ '',
252
+ array( 'plugin_id' => $addon_id ),
253
+ false,
254
+ true
255
+ );
256
+
257
+ }
258
+ } else if ( ! $show_upgrade ) {
259
+ if ( $fs->is_addon_installed( $addon_id ) ) {
260
+ $addon_file = $fs->get_addon_basename( $addon_id );
261
+ $buttons[] = sprintf(
262
+ '<a class="button button-primary edit" href="%s" title="%s">%s</a>',
263
+ wp_nonce_url( 'plugins.php?action=activate&amp;plugin=' . $addon_file, 'activate-plugin_' . $addon_file ),
264
+ fs_esc_attr_inline( 'Activate this add-on', 'activate-this-addon', $slug ),
265
+ $activate_text
266
+ );
267
+ } else {
268
+ if ( $fs->is_allowed_to_install() ) {
269
+ $buttons[] = sprintf(
270
+ '<a class="button button-primary edit" href="%s">%s</a>',
271
+ wp_nonce_url( self_admin_url( 'update.php?action=install-plugin&plugin=' . $addon->slug ), 'install-plugin_' . $addon->slug ),
272
+ fs_text_inline( 'Install Now', 'install-now', $slug )
273
+ );
274
+ } else {
275
+ $buttons[] = sprintf(
276
+ '<a target="_blank" class="button button-primary edit" href="%s">%s</a>',
277
+ $fs->_get_latest_download_local_url( $addon_id ),
278
+ esc_html( $download_latest_text )
279
+ );
280
+ }
281
+ }
282
+ }
283
+
284
+ if ( $show_upgrade ) {
285
+ $buttons[] = sprintf( '<a href="%s" class="thickbox button button-small button-primary" aria-label="%s" data-title="%s"><i class="dashicons dashicons-cart"></i> %s</a>',
286
+ esc_url( network_admin_url( 'plugin-install.php?fs_allow_updater_and_dialog=true&tab=plugin-information&parent_plugin_id=' . $fs->get_id() . '&plugin=' . $addon->slug .
287
+ '&TB_iframe=true&width=600&height=550' ) ),
288
+ esc_attr( sprintf( fs_text_inline( 'More information about %s', 'more-information-about-x', $slug ), $addon->title ) ),
289
+ esc_attr( $addon->title ),
290
+ ( $fs_addon->has_free_plan() ?
291
+ $upgrade_text :
292
+ fs_text_x_inline( 'Purchase', 'verb', 'purchase', $slug ) )
293
+ );
294
+ }
295
+
296
+ $buttons_count = count( $buttons );
297
+ ?>
298
+
299
+ <!-- Actions -->
300
+ <td><?php if ( $buttons_count > 1 ) : ?>
301
+ <div class="button-group"><?php endif ?>
302
+ <?php foreach ( $buttons as $button ) {
303
+ echo $button;
304
+ } ?>
305
+ <?php if ( $buttons_count > 1 ) : ?></div><?php endif ?></td>
306
+ <!--/ Actions -->
307
+
308
+ <?php else : ?>
309
+ <?php // Add-on NOT Installed or was never connected.
310
+ ?>
311
+ <!-- Action -->
312
+ <td colspan="4">
313
+ <?php if ( $fs->is_addon_installed( $addon_id ) ) : ?>
314
+ <?php $addon_file = $fs->get_addon_basename( $addon_id ) ?>
315
+ <a class="button button-primary"
316
+ href="<?php echo wp_nonce_url( 'plugins.php?action=activate&amp;plugin=' . $addon_file, 'activate-plugin_' . $addon_file ) ?>"
317
+ title="<?php fs_esc_attr_echo_inline( 'Activate this add-on', 'activate-this-addon', $slug ) ?>"
318
+ class="edit"><?php echo esc_html( $activate_text ) ?></a>
319
+ <?php else : ?>
320
+ <?php if ( $fs->is_allowed_to_install() ) : ?>
321
+ <a class="button button-primary"
322
+ href="<?php echo wp_nonce_url( self_admin_url( 'update.php?action=install-plugin&plugin=' . $addon->slug ), 'install-plugin_' . $addon->slug ) ?>"><?php fs_esc_html_echo_inline( 'Install Now', 'install-now', $slug ) ?></a>
323
+ <?php else : ?>
324
+ <a target="_blank" class="button button-primary"
325
+ href="<?php echo $fs->_get_latest_download_local_url( $addon_id ) ?>"><?php echo esc_html( $download_latest_text ) ?></a>
326
+ <?php endif ?>
327
+ <?php endif ?>
328
+ </td>
329
+ <!--/ Action -->
330
+ <?php endif ?>
331
+ <?php if ( ! $is_paying && WP_FS__DEV_MODE ) : ?>
332
+ <!-- Optional Delete Action -->
333
+ <td>
334
+ <?php
335
+ if ( $is_addon_activated ) {
336
+ fs_ui_action_button(
337
+ $fs->get_id(), 'account',
338
+ 'delete_account',
339
+ fs_text_x_inline( 'Delete', 'verb', 'delete', $slug ),
340
+ '',
341
+ array( 'plugin_id' => $addon_id ),
342
+ false,
343
+ $show_upgrade
344
+ );
345
+ }
346
+ ?>
347
+ </td>
348
+ <!--/ Optional Delete Action -->
349
+ <?php endif ?>
350
  </tr>
vendor/freemius/templates/account/partials/site.php CHANGED
@@ -292,14 +292,19 @@
292
  </td>
293
  <td><?php if ( $is_active_subscription ) : ?>
294
  <?php
295
- $downgrade_x_confirm_text = fs_text_inline( 'Downgrading your plan will immediately stop all future recurring payments and your %s plan license will expire in %s.', 'downgrade-x-confirm', $slug );
296
- $after_downgrade_non_blocking_text = fs_text_inline( 'You can still enjoy all %s features but you will not have access to %s updates and support.', 'after-downgrade-non-blocking', $slug );
297
- $after_downgrade_blocking_text = fs_text_inline( 'Once your license expires you can still use the Free version but you will NOT have access to the %s features.', 'after-downgrade-blocking', $slug );
298
- $downgrade_text = fs_text_x_inline( 'Downgrade', 'verb', 'downgrade', $slug );
 
 
 
 
299
 
300
  $human_readable_license_expiration = human_time_diff( time(), strtotime( $license->expiration ) );
301
  $downgrade_confirmation_message = sprintf(
302
  $downgrade_x_confirm_text,
 
303
  $plan->title,
304
  $human_readable_license_expiration
305
  );
@@ -313,7 +318,7 @@
313
  <input type="hidden" name="fs_action" value="<?php echo $action ?>">
314
  <?php wp_nonce_field( trim( "{$action}:{$blog_id}", ':' ) ) ?>
315
  <input type="hidden" name="blog_id" value="<?php echo $blog_id ?>">
316
- <button class="button button-small" onclick="if (confirm('<?php echo ( $downgrade_confirmation_message . ' ' . $after_downgrade_message ) ?>')) { this.parentNode.submit(); } else { return false; }"><?php echo $downgrade_text ?></button>
317
  </form>
318
  <?php endif ?></td>
319
  </tr>
292
  </td>
293
  <td><?php if ( $is_active_subscription ) : ?>
294
  <?php
295
+ $downgrading_plan_text = fs_text_inline( 'Downgrading your plan', 'downgrading-plan', $slug );
296
+ $cancelling_subscription_text = fs_text_inline( 'Cancelling the subscription', 'cancelling-subscription', $slug );
297
+ /* translators: %1s: Either 'Downgrading your plan' or 'Cancelling the subscription' */
298
+ $downgrade_x_confirm_text = fs_text_inline( '%1s will immediately stop all future recurring payments and your %s plan license will expire in %s.', 'downgrade-x-confirm', $slug );
299
+ $prices_increase_text = fs_text_inline( 'Please note that we will not be able to grandfather outdated pricing for renewals/new subscriptions after a cancellation. If you choose to renew the subscription manually in the future, after a price increase, which typically occurs once a year, you will be charged the updated price.', 'pricing-increase-warning', $slug );
300
+ $after_downgrade_non_blocking_text = fs_text_inline( 'You can still enjoy all %s features but you will not have access to %s security & feature updates, nor support.', 'after-downgrade-non-blocking', $slug );
301
+ $after_downgrade_blocking_text = fs_text_inline( 'Once your license expires you can still use the Free version but you will NOT have access to the %s features.', 'after-downgrade-blocking', $slug );
302
+ $downgrade_text = fs_text_x_inline( 'Downgrade', 'verb', 'downgrade', $slug );
303
 
304
  $human_readable_license_expiration = human_time_diff( time(), strtotime( $license->expiration ) );
305
  $downgrade_confirmation_message = sprintf(
306
  $downgrade_x_confirm_text,
307
+ ( $fs->is_only_premium() ? $cancelling_subscription_text : $downgrading_plan_text ),
308
  $plan->title,
309
  $human_readable_license_expiration
310
  );
318
  <input type="hidden" name="fs_action" value="<?php echo $action ?>">
319
  <?php wp_nonce_field( trim( "{$action}:{$blog_id}", ':' ) ) ?>
320
  <input type="hidden" name="blog_id" value="<?php echo $blog_id ?>">
321
+ <button class="button button-small" onclick="if (confirm('<?php echo esc_attr( $downgrade_confirmation_message . ' ' . $after_downgrade_message . ' ' . $prices_increase_text ) ?>')) { this.parentNode.submit(); } else { return false; }"><?php echo $downgrade_text ?></button>
322
  </form>
323
  <?php endif ?></td>
324
  </tr>
vendor/freemius/templates/add-ons.php CHANGED
@@ -98,7 +98,7 @@
98
  <li class="fs-card fs-addon" data-slug="<?php echo $addon->slug ?>">
99
  <?php
100
  echo sprintf( '<a href="%s" class="thickbox fs-overlay" aria-label="%s" data-title="%s"></a>',
101
- esc_url( network_admin_url( 'plugin-install.php?tab=plugin-information&parent_plugin_id=' . $fs->get_id() . '&plugin=' . $addon->slug .
102
  '&TB_iframe=true&width=600&height=550' ) ),
103
  esc_attr( sprintf( fs_text_inline( 'More information about %s', 'more-information-about-x', $slug ), $addon->title ) ),
104
  esc_attr( $addon->title )
98
  <li class="fs-card fs-addon" data-slug="<?php echo $addon->slug ?>">
99
  <?php
100
  echo sprintf( '<a href="%s" class="thickbox fs-overlay" aria-label="%s" data-title="%s"></a>',
101
+ esc_url( network_admin_url( 'plugin-install.php?fs_allow_updater_and_dialog=true&tab=plugin-information&parent_plugin_id=' . $fs->get_id() . '&plugin=' . $addon->slug .
102
  '&TB_iframe=true&width=600&height=550' ) ),
103
  esc_attr( sprintf( fs_text_inline( 'More information about %s', 'more-information-about-x', $slug ), $addon->title ) ),
104
  esc_attr( $addon->title )
vendor/freemius/templates/admin-notice.php CHANGED
@@ -11,8 +11,32 @@
11
  }
12
 
13
  $dismiss_text = fs_text_x_inline( 'Dismiss', 'as close a window', 'dismiss' );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
14
  ?>
15
- <div<?php if ( ! empty( $VARS['id'] ) ) : ?> data-id="<?php echo $VARS['id'] ?>"<?php endif ?><?php if ( ! empty( $VARS['manager_id'] ) ) : ?> data-manager-id="<?php echo $VARS['manager_id'] ?>"<?php endif ?>
16
  class="<?php
17
  switch ( $VARS['type'] ) {
18
  case 'error':
@@ -33,6 +57,10 @@
33
  echo ' fs-sticky';
34
  } ?><?php if ( ! empty( $VARS['plugin'] ) ) {
35
  echo ' fs-has-title';
 
 
 
 
36
  } ?>"><?php if ( ! empty( $VARS['plugin'] ) ) : ?>
37
  <label class="fs-plugin-title"><?php echo $VARS['plugin'] ?></label>
38
  <?php endif ?>
11
  }
12
 
13
  $dismiss_text = fs_text_x_inline( 'Dismiss', 'as close a window', 'dismiss' );
14
+
15
+ $slug = '';
16
+ $type = '';
17
+
18
+ if ( ! empty( $VARS['manager_id'] ) ) {
19
+ /**
20
+ * @var array $VARS
21
+ */
22
+ $slug = $VARS['manager_id'];
23
+
24
+ $type = WP_FS__MODULE_TYPE_PLUGIN;
25
+
26
+ if ( false !== strpos( $slug, ':' ) ) {
27
+ $parts = explode( ':', $slug );
28
+
29
+ $slug = $parts[0];
30
+
31
+ $parts_count = count( $parts );
32
+
33
+ if ( 1 < $parts_count && WP_FS__MODULE_TYPE_THEME == $parts[1] ) {
34
+ $type = $parts[1];
35
+ }
36
+ }
37
+ }
38
  ?>
39
+ <div<?php if ( ! empty( $VARS['id'] ) ) : ?> data-id="<?php echo $VARS['id'] ?>"<?php endif ?><?php if ( ! empty( $VARS['manager_id'] ) ) : ?> data-manager-id="<?php echo $VARS['manager_id'] ?>"<?php endif ?><?php if ( ! empty( $slug ) ) : ?> data-slug="<?php echo $slug ?>"<?php endif ?><?php if ( ! empty( $type ) ) : ?> data-type="<?php echo $type ?>"<?php endif ?>
40
  class="<?php
41
  switch ( $VARS['type'] ) {
42
  case 'error':
57
  echo ' fs-sticky';
58
  } ?><?php if ( ! empty( $VARS['plugin'] ) ) {
59
  echo ' fs-has-title';
60
+ } ?><?php if ( ! empty( $slug ) ) {
61
+ echo " fs-slug-{$slug}";
62
+ } ?><?php if ( ! empty( $type ) ) {
63
+ echo " fs-type-{$type}";
64
  } ?>"><?php if ( ! empty( $VARS['plugin'] ) ) : ?>
65
  <label class="fs-plugin-title"><?php echo $VARS['plugin'] ?></label>
66
  <?php endif ?>
vendor/freemius/templates/checkout.php CHANGED
@@ -174,7 +174,7 @@
174
  fs_require_once_template('secure-https-header.php', $view_params);
175
  ?>
176
  <div id="fs_checkout" class="wrap fs-section fs-full-size-wrapper">
177
- <div id="frame"></div>
178
  <script type="text/javascript">
179
  // http://stackoverflow.com/questions/4583703/jquery-post-request-not-ajax
180
  jQuery(function ($) {
@@ -234,7 +234,7 @@
234
  src = base_url + '/?<?php echo http_build_query( $query_params ) ?>#' + encodeURIComponent(document.location.href),
235
  // Append the i-frame into the DOM.
236
  frame = $('<i' + 'frame " src="' + src + '" width="100%" height="' + frame_height + 'px" scrolling="no" frameborder="0" style="background: transparent; width: 1px; min-width: 100%;"><\/i' + 'frame>')
237
- .appendTo('#frame');
238
 
239
  FS.PostMessage.init(base_url, [frame[0]]);
240
  FS.PostMessage.receiveOnce('height', function (data) {
174
  fs_require_once_template('secure-https-header.php', $view_params);
175
  ?>
176
  <div id="fs_checkout" class="wrap fs-section fs-full-size-wrapper">
177
+ <div id="fs_frame"></div>
178
  <script type="text/javascript">
179
  // http://stackoverflow.com/questions/4583703/jquery-post-request-not-ajax
180
  jQuery(function ($) {
234
  src = base_url + '/?<?php echo http_build_query( $query_params ) ?>#' + encodeURIComponent(document.location.href),
235
  // Append the i-frame into the DOM.
236
  frame = $('<i' + 'frame " src="' + src + '" width="100%" height="' + frame_height + 'px" scrolling="no" frameborder="0" style="background: transparent; width: 1px; min-width: 100%;"><\/i' + 'frame>')
237
+ .appendTo('#fs_frame');
238
 
239
  FS.PostMessage.init(base_url, [frame[0]]);
240
  FS.PostMessage.receiveOnce('height', function (data) {
vendor/freemius/templates/connect.php CHANGED
@@ -40,10 +40,12 @@
40
 
41
  $freemius_site_www = 'https://freemius.com';
42
 
43
- $freemius_site_url = $freemius_site_www . '/' . ( $fs->is_premium() ?
44
- 'wordpress/' :
45
- // Insights platform information.
46
- 'wordpress/usage-tracking/' . $fs->get_id() . "/{$slug}/" );
 
 
47
 
48
  if ( $fs->is_premium() ) {
49
  $freemius_site_url .= '?' . http_build_query( array(
@@ -425,7 +427,7 @@
425
  <a href="https://freemius.com/privacy/" target="_blank"
426
  tabindex="1"><?php fs_esc_html_echo_inline( 'Privacy Policy', 'privacy-policy', $slug ) ?></a>
427
  &nbsp;&nbsp;-&nbsp;&nbsp;
428
- <a href="<?php echo $freemius_site_www ?>/terms/" target="_blank" tabindex="1"><?php fs_echo_inline( 'Terms of Service', 'tos', $slug ) ?></a>
429
  </div>
430
  </div>
431
  <?php
40
 
41
  $freemius_site_www = 'https://freemius.com';
42
 
43
+ $freemius_usage_tracking_url = $freemius_site_www . '/wordpress/usage-tracking/' . $fs->get_id() . "/{$slug}/";
44
+ $freemius_plugin_terms_url = $freemius_site_www . '/terms/' . $fs->get_id() . "/{$slug}/";
45
+
46
+ $freemius_site_url = $fs->is_premium() ?
47
+ $freemius_site_www :
48
+ $freemius_usage_tracking_url;
49
 
50
  if ( $fs->is_premium() ) {
51
  $freemius_site_url .= '?' . http_build_query( array(
427
  <a href="https://freemius.com/privacy/" target="_blank"
428
  tabindex="1"><?php fs_esc_html_echo_inline( 'Privacy Policy', 'privacy-policy', $slug ) ?></a>
429
  &nbsp;&nbsp;-&nbsp;&nbsp;
430
+ <a href="<?php echo $require_license_key ? $freemius_plugin_terms_url : $freemius_usage_tracking_url ?>" target="_blank" tabindex="1"><?php $require_license_key ? fs_echo_inline( 'License Agreement', 'license-agreement', $slug ) : fs_echo_inline( 'Terms of Service', 'tos', $slug ) ?></a>
431
  </div>
432
  </div>
433
  <?php
vendor/freemius/templates/contact.php CHANGED
@@ -86,7 +86,7 @@
86
  }
87
  ?>
88
  <div id="fs_contact" class="wrap fs-section fs-full-size-wrapper">
89
- <div id="frame"></div>
90
  <script type="text/javascript">
91
  (function ($) {
92
  $(function () {
@@ -99,14 +99,14 @@
99
 
100
  // Append the i-frame into the DOM.
101
  frame = $('<i' + 'frame " src="' + src + '" width="100%" height="' + frame_height + 'px" scrolling="no" frameborder="0" style="background: transparent; width: 1px; min-width: 100%;"><\/i' + 'frame>')
102
- .appendTo('#frame');
103
 
104
  FS.PostMessage.init(base_url);
105
  FS.PostMessage.receive('height', function (data) {
106
  var h = data.height;
107
  if (!isNaN(h) && h > 0 && h != frame_height) {
108
  frame_height = h;
109
- $('#frame i' + 'frame').height(frame_height + 'px');
110
  }
111
  });
112
  });
86
  }
87
  ?>
88
  <div id="fs_contact" class="wrap fs-section fs-full-size-wrapper">
89
+ <div id="fs_frame"></div>
90
  <script type="text/javascript">
91
  (function ($) {
92
  $(function () {
99
 
100
  // Append the i-frame into the DOM.
101
  frame = $('<i' + 'frame " src="' + src + '" width="100%" height="' + frame_height + 'px" scrolling="no" frameborder="0" style="background: transparent; width: 1px; min-width: 100%;"><\/i' + 'frame>')
102
+ .appendTo('#fs_frame');
103
 
104
  FS.PostMessage.init(base_url);
105
  FS.PostMessage.receive('height', function (data) {
106
  var h = data.height;
107
  if (!isNaN(h) && h > 0 && h != frame_height) {
108
  frame_height = h;
109
+ $('#fs_frame i' + 'frame').height(frame_height + 'px');
110
  }
111
  });
112
  });
vendor/freemius/templates/debug.php CHANGED
@@ -86,6 +86,16 @@
86
  <button class="button button-primary"><?php fs_esc_html_echo_inline( 'Sync Data From Server' ) ?></button>
87
  </form>
88
  </td>
 
 
 
 
 
 
 
 
 
 
89
  <td>
90
  <button id="fs_load_db_option" class="button"><?php fs_esc_html_echo_inline( 'Load DB Option' ) ?></button>
91
  </td>
@@ -103,6 +113,7 @@
103
  if (optionName) {
104
  $.post(ajaxurl, {
105
  action : 'fs_get_db_option',
 
106
  option_name: optionName
107
  }, function (response) {
108
  if (response.data.value)
@@ -122,6 +133,7 @@
122
  if (optionValue) {
123
  $.post(ajaxurl, {
124
  action : 'fs_set_db_option',
 
125
  option_name : optionName,
126
  option_value: optionValue
127
  }, function () {
@@ -195,7 +207,7 @@
195
  </tr>
196
  </thead>
197
  <tbody>
198
- <?php foreach ( $fs_active_plugins->plugins as $sdk_path => &$data ) : ?>
199
  <?php $is_active = ( WP_FS__SDK_VERSION == $data->version ) ?>
200
  <tr<?php if ( $is_active ) {
201
  echo ' style="background: #E6FFE6; font-weight: bold"';
@@ -307,7 +319,7 @@
307
  <input type="hidden" name="module_id" value="<?php echo $fs->get_id() ?>">
308
  <?php wp_nonce_field( 'simulate_trial' ) ?>
309
 
310
- <button type="submit" class="button button-primary simulate-trial"><?php fs_esc_html_echo_inline( 'Simulate Trial' ) ?></button>
311
  </form>
312
  <?php endif ?>
313
  <?php if ( $fs->is_registered() ) : ?>
86
  <button class="button button-primary"><?php fs_esc_html_echo_inline( 'Sync Data From Server' ) ?></button>
87
  </form>
88
  </td>
89
+ <?php if ( fs_is_network_admin() && true !== $fs_options->get_option( 'ms_migration_complete', false, true ) ) : ?>
90
+ <td>
91
+ <!-- Migrate Options to Network -->
92
+ <form action="" method="POST">
93
+ <input type="hidden" name="fs_action" value="migrate_options_to_network">
94
+ <?php wp_nonce_field( 'migrate_options_to_network' ) ?>
95
+ <button class="button button-primary"><?php fs_esc_html_echo_inline( 'Migrate Options to Network' ) ?></button>
96
+ </form>
97
+ </td>
98
+ <?php endif ?>
99
  <td>
100
  <button id="fs_load_db_option" class="button"><?php fs_esc_html_echo_inline( 'Load DB Option' ) ?></button>
101
  </td>
113
  if (optionName) {
114
  $.post(ajaxurl, {
115
  action : 'fs_get_db_option',
116
+ _wpnonce : '<?php echo wp_create_nonce( 'fs_get_db_option' ) ?>',
117
  option_name: optionName
118
  }, function (response) {
119
  if (response.data.value)
133
  if (optionValue) {
134
  $.post(ajaxurl, {
135
  action : 'fs_set_db_option',
136
+ _wpnonce : '<?php echo wp_create_nonce( 'fs_set_db_option' ) ?>',
137
  option_name : optionName,
138
  option_value: optionValue
139
  }, function () {
207
  </tr>
208
  </thead>
209
  <tbody>
210
+ <?php foreach ( $fs_active_plugins->plugins as $sdk_path => $data ) : ?>
211
  <?php $is_active = ( WP_FS__SDK_VERSION == $data->version ) ?>
212
  <tr<?php if ( $is_active ) {
213
  echo ' style="background: #E6FFE6; font-weight: bold"';
319
  <input type="hidden" name="module_id" value="<?php echo $fs->get_id() ?>">
320
  <?php wp_nonce_field( 'simulate_trial' ) ?>
321
 
322
+ <button type="submit" class="button button-primary simulate-trial"><?php fs_esc_html_echo_inline( 'Simulate Trial Promotion' ) ?></button>
323
  </form>
324
  <?php endif ?>
325
  <?php if ( $fs->is_registered() ) : ?>
vendor/freemius/templates/forms/deactivation/form.php CHANGED
@@ -10,6 +10,9 @@
10
  exit;
11
  }
12
 
 
 
 
13
  $fs = freemius( $VARS['id'] );
14
  $slug = $fs->get_slug();
15
 
@@ -66,14 +69,15 @@ HTML;
66
 
67
  fs_enqueue_local_style( 'fs_dialog_boxes', '/admin/dialog-boxes.css' );
68
  ?>
 
69
  <script type="text/javascript">
70
  (function ($) {
71
- var reasonsHtml = <?php echo json_encode( $reasons_list_items_html ); ?>,
72
  modalHtml =
73
  '<div class="fs-modal fs-modal-deactivation-feedback<?php echo empty( $confirmation_message ) ? ' no-confirmation-message' : ''; ?>">'
74
  + ' <div class="fs-modal-dialog">'
75
  + ' <div class="fs-modal-header">'
76
- + ' <h4><?php fs_esc_attr_echo_inline( 'Quick feedback', 'quick-feedback' , $slug ) ?></h4>'
77
  + ' </div>'
78
  + ' <div class="fs-modal-body">'
79
  + ' <div class="fs-modal-panel" data-panel-id="confirm"><p><?php echo $confirmation_message; ?></p></div>'
@@ -82,7 +86,7 @@ HTML;
82
  + ' <div class="fs-modal-footer">'
83
  + ' <?php echo $anonymous_feedback_checkbox_html ?>'
84
  + ' <a href="#" class="button button-secondary button-deactivate"></a>'
85
- + ' <a href="#" class="button button-primary button-close"><?php fs_esc_js_echo_inline( 'Cancel', 'cancel' , $slug ) ?></a>'
86
  + ' </div>'
87
  + ' </div>'
88
  + '</div>',
@@ -94,23 +98,82 @@ HTML;
94
  isAnonymous = <?php echo ( $is_anonymous ? 'true' : 'false' ); ?>,
95
  otherReasonID = <?php echo Freemius::REASON_OTHER; ?>,
96
  dontShareDataReasonID = <?php echo Freemius::REASON_DONT_LIKE_TO_SHARE_MY_INFORMATION; ?>,
97
- deleteThemeUpdateData = <?php echo $fs->is_theme() && $fs->is_premium() && ! $fs->has_active_valid_license() ? 'true' : 'false' ?>;
 
98
 
99
  $modal.appendTo($('body'));
100
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
101
  registerEventHandlers();
102
 
103
  function registerEventHandlers() {
104
- <?php
105
- if ( $fs->is_plugin() ) { ?>
106
  $deactivateLink.click(function (evt) {
107
  evt.preventDefault();
108
 
109
- redirectLink = $(this).attr('href');
110
 
111
- showModal();
 
 
 
 
112
  });
 
113
  <?php
 
114
  /**
115
  * For "theme" module type, the modal is shown when the current user clicks on
116
  * the "Activate" button of any other theme. The "Activate" button is actually
@@ -122,8 +185,8 @@ HTML;
122
  *
123
  * @since 1.2.2.7 Don't trigger the deactivation feedback form if activating the premium version of the theme.
124
  */
125
- } else { ?>
126
- $('body').on('click', '.theme-browser .theme:not([data-slug=<?php echo $slug ?>-premium]) .theme-actions .button.activate', function (evt) {
127
  evt.preventDefault();
128
 
129
  redirectLink = $(this).attr('href');
@@ -245,7 +308,7 @@ HTML;
245
  });
246
 
247
  $modal.on('click', 'input[type="radio"]', function () {
248
- var $selectedReasonOption = $(this);
249
 
250
  // If the selection has not changed, do not proceed.
251
  if (selectedReasonID === $selectedReasonOption.val())
@@ -303,11 +366,15 @@ HTML;
303
  }
304
 
305
  // If the user has not clicked the close button and the clicked element is inside the modal dialog, just return.
306
- if (!$target.hasClass('button-close') && ( $target.parents('.fs-modal-body').length > 0 || $target.parents('.fs-modal-footer').length > 0 )) {
 
 
 
307
  return;
308
  }
309
 
310
  closeModal();
 
311
  return false;
312
  });
313
  }
@@ -372,14 +439,14 @@ HTML;
372
  * If the modal dialog has no confirmation message, that is, it has only one panel, then ensure
373
  * that clicking the deactivate button will actually deactivate the plugin.
374
  */
375
- if ($modal.hasClass('no-confirmation-message')) {
376
- $deactivateButton.addClass('allow-deactivate');
377
 
378
- showPanel('reasons');
379
  } else {
380
- $deactivateButton.removeClass('allow-deactivate');
381
 
382
- showPanel('confirm');
383
  }
384
  }
385
 
@@ -396,30 +463,30 @@ HTML;
396
  }
397
 
398
  function showPanel(panelType) {
399
- $modal.find('.fs-modal-panel').removeClass('active ');
400
- $modal.find('[data-panel-id="' + panelType + '"]').addClass('active');
401
 
402
  updateButtonLabels();
403
  }
404
 
405
  function updateButtonLabels() {
406
- var $deactivateButton = $modal.find('.button-deactivate');
407
-
408
- // Reset the deactivate button's text.
409
- if ('confirm' === getCurrentPanel()) {
410
- $deactivateButton.text('<?php echo esc_js( sprintf(
411
- fs_text_inline( 'Yes - %s', 'deactivation-modal-button-confirm' , $slug ),
412
- $fs->is_plugin() ?
413
- $deactivate_text :
414
- sprintf( $activate_x_text, $theme_text )
415
- ) ) ?>');
416
  } else {
417
- $deactivateButton.html('<?php echo esc_js( sprintf(
418
  fs_text_inline('Skip & %s', 'skip-and-x', $slug ),
419
  $fs->is_plugin() ?
420
  $deactivate_text :
421
  sprintf( $activate_x_text, $theme_text )
422
- ) ) ?>');
423
  }
424
  }
425
 
10
  exit;
11
  }
12
 
13
+ /**
14
+ * @var array $VARS
15
+ */
16
  $fs = freemius( $VARS['id'] );
17
  $slug = $fs->get_slug();
18
 
69
 
70
  fs_enqueue_local_style( 'fs_dialog_boxes', '/admin/dialog-boxes.css' );
71
  ?>
72
+ <?php $fs->_maybe_add_subscription_cancellation_dialog_box() ?>
73
  <script type="text/javascript">
74
  (function ($) {
75
+ var reasonsHtml = <?php echo json_encode( $reasons_list_items_html ) ?>,
76
  modalHtml =
77
  '<div class="fs-modal fs-modal-deactivation-feedback<?php echo empty( $confirmation_message ) ? ' no-confirmation-message' : ''; ?>">'
78
  + ' <div class="fs-modal-dialog">'
79
  + ' <div class="fs-modal-header">'
80
+ + ' <h4><?php fs_esc_attr_echo_inline( 'Quick Feedback', 'quick-feedback' , $slug ) ?></h4>'
81
  + ' </div>'
82
  + ' <div class="fs-modal-body">'
83
  + ' <div class="fs-modal-panel" data-panel-id="confirm"><p><?php echo $confirmation_message; ?></p></div>'
86
  + ' <div class="fs-modal-footer">'
87
  + ' <?php echo $anonymous_feedback_checkbox_html ?>'
88
  + ' <a href="#" class="button button-secondary button-deactivate"></a>'
89
+ + ' <a href="#" class="button button-primary button-close"><?php fs_esc_js_echo_inline( 'Cancel', 'cancel', $slug ) ?></a>'
90
  + ' </div>'
91
  + ' </div>'
92
  + '</div>',
98
  isAnonymous = <?php echo ( $is_anonymous ? 'true' : 'false' ); ?>,
99
  otherReasonID = <?php echo Freemius::REASON_OTHER; ?>,
100
  dontShareDataReasonID = <?php echo Freemius::REASON_DONT_LIKE_TO_SHARE_MY_INFORMATION; ?>,
101
+ deleteThemeUpdateData = <?php echo $fs->is_theme() && $fs->is_premium() && ! $fs->has_any_active_valid_license() ? 'true' : 'false' ?>,
102
+ $subscriptionCancellationModal = $( '.fs-modal-subscription-cancellation-<?php echo $fs->get_id() ?>' );
103
 
104
  $modal.appendTo($('body'));
105
 
106
+ if ( 0 !== $subscriptionCancellationModal.length ) {
107
+ $subscriptionCancellationModal.on( '<?php echo $fs->get_action_tag( 'subscription_cancellation_action' ) ?>', function( evt, cancelSubscription ) {
108
+ if ( false === cancelSubscription ) {
109
+ showModal();
110
+
111
+ $subscriptionCancellationModal.trigger( 'closeModal' );
112
+ } else {
113
+ var $errorMessage = $subscriptionCancellationModal.find( '.notice-error' );
114
+
115
+ <?php
116
+ $subscription_cancellation_context = $fs->is_paid_trial() ?
117
+ fs_text_inline( 'trial', 'trial', $slug ) :
118
+ fs_text_inline( 'subscription', 'subscription', $slug );
119
+ ?>
120
+
121
+ $.ajax({
122
+ url : ajaxurl,
123
+ method : 'POST',
124
+ data : {
125
+ action : '<?php echo $fs->get_ajax_action( 'cancel_subscription_or_trial' ) ?>',
126
+ security : '<?php echo $fs->get_ajax_security( 'cancel_subscription_or_trial' ) ?>',
127
+ module_id: '<?php echo $fs->get_id() ?>'
128
+ },
129
+ beforeSend: function() {
130
+ $errorMessage.hide();
131
+
132
+ $subscriptionCancellationModal.find( '.fs-modal-footer .button' ).addClass( 'disabled' );
133
+ $subscriptionCancellationModal.find( '.fs-modal-footer .button-primary' ).text( '<?php echo esc_js(
134
+ sprintf( fs_text_inline( 'Cancelling %s...', 'cancelling-x' , $slug ), $subscription_cancellation_context )
135
+ ) ?>' );
136
+ },
137
+ success: function( result ) {
138
+ if ( result.success ) {
139
+ $subscriptionCancellationModal.removeClass( 'has-subscription-actions' );
140
+ $subscriptionCancellationModal.find( '.fs-modal-footer .button-primary' ).removeClass( 'warn' );
141
+
142
+ $subscriptionCancellationModal.remove();
143
+ showModal();
144
+ } else {
145
+ $errorMessage.find( '> p' ).html( result.error );
146
+ $errorMessage.show();
147
+
148
+ $subscriptionCancellationModal.find( '.fs-modal-footer .button' ).removeClass( 'disabled' );
149
+ $subscriptionCancellationModal.find( '.fs-modal-footer .button-primary' ).html( <?php echo json_encode( sprintf(
150
+ fs_text_inline( 'Cancel %s & Proceed', 'cancel-x-and-proceed', $slug ),
151
+ ucfirst( $subscription_cancellation_context )
152
+ ) ) ?> );
153
+ }
154
+ }
155
+ });
156
+ }
157
+ });
158
+ }
159
+
160
  registerEventHandlers();
161
 
162
  function registerEventHandlers() {
 
 
163
  $deactivateLink.click(function (evt) {
164
  evt.preventDefault();
165
 
166
+ redirectLink = $(this).attr('href');
167
 
168
+ if ( 0 == $subscriptionCancellationModal.length ) {
169
+ showModal();
170
+ } else {
171
+ $subscriptionCancellationModal.trigger( 'showModal' );
172
+ }
173
  });
174
+
175
  <?php
176
+ if ( ! $fs->is_plugin() ) {
177
  /**
178
  * For "theme" module type, the modal is shown when the current user clicks on
179
  * the "Activate" button of any other theme. The "Activate" button is actually
185
  *
186
  * @since 1.2.2.7 Don't trigger the deactivation feedback form if activating the premium version of the theme.
187
  */
188
+ ?>
189
+ $('body').on('click', '.theme-browser .theme:not([data-slug=<?php echo $fs->get_premium_slug() ?>]) .theme-actions .button.activate', function (evt) {
190
  evt.preventDefault();
191
 
192
  redirectLink = $(this).attr('href');
308
  });
309
 
310
  $modal.on('click', 'input[type="radio"]', function () {
311
+ var $selectedReasonOption = $( this );
312
 
313
  // If the selection has not changed, do not proceed.
314
  if (selectedReasonID === $selectedReasonOption.val())
366
  }
367
 
368
  // If the user has not clicked the close button and the clicked element is inside the modal dialog, just return.
369
+ if (
370
+ ! $target.hasClass( 'button-close' ) &&
371
+ ( $target.parents( '.fs-modal-body' ).length > 0 || $target.parents( '.fs-modal-footer' ).length > 0 )
372
+ ) {
373
  return;
374
  }
375
 
376
  closeModal();
377
+
378
  return false;
379
  });
380
  }
439
  * If the modal dialog has no confirmation message, that is, it has only one panel, then ensure
440
  * that clicking the deactivate button will actually deactivate the plugin.
441
  */
442
+ if ( $modal.hasClass( 'no-confirmation-message' ) ) {
443
+ $deactivateButton.addClass( 'allow-deactivate' );
444
 
445
+ showPanel( 'reasons' );
446
  } else {
447
+ $deactivateButton.removeClass( 'allow-deactivate' );
448
 
449
+ showPanel( 'confirm' );
450
  }
451
  }
452
 
463
  }
464
 
465
  function showPanel(panelType) {
466
+ $modal.find( '.fs-modal-panel' ).removeClass( 'active' );
467
+ $modal.find( '[data-panel-id="' + panelType + '"]' ).addClass( 'active' );
468
 
469
  updateButtonLabels();
470
  }
471
 
472
  function updateButtonLabels() {
473
+ var $deactivateButton = $modal.find( '.button-deactivate' );
474
+
475
+ // Reset the deactivate button's text.
476
+ if ( 'confirm' === getCurrentPanel() ) {
477
+ $deactivateButton.text( <?php echo json_encode( sprintf(
478
+ fs_text_inline( 'Yes - %s', 'deactivation-modal-button-confirm', $slug ),
479
+ $fs->is_plugin() ?
480
+ $deactivate_text :
481
+ sprintf( $activate_x_text, $theme_text )
482
+ ) ) ?> );
483
  } else {
484
+ $deactivateButton.html( <?php echo json_encode( sprintf(
485
  fs_text_inline('Skip & %s', 'skip-and-x', $slug ),
486
  $fs->is_plugin() ?
487
  $deactivate_text :
488
  sprintf( $activate_x_text, $theme_text )
489
+ ) ) ?> );
490
  }
491
  }
492
 
vendor/freemius/templates/forms/premium-versions-upgrade-handler.php CHANGED
@@ -20,12 +20,32 @@
20
  $plugin_name = $plugin_data['Name'];
21
  $plugin_basename = $fs->get_plugin_basename();
22
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
23
  $message = sprintf(
24
  fs_text_inline( 'There is a new version of %s available.', 'new-version-available-message', $slug ) .
25
- fs_text_inline( ' %sRenew your license now%s to access version %s security & feature updates, and support.', 'renew-license-now', $slug ),
26
  '<span id="plugin_name"></span>',
27
- '<a id="pricing_url" href="">',
28
- '</a>',
 
 
 
 
29
  '<span id="new_version"></span>'
30
  );
31
 
@@ -33,7 +53,9 @@
33
 
34
  $header_title = fs_text_inline( 'New Version Available', 'new-version-available', $slug );
35
 
36
- $renew_license_button_text = fs_text_inline( 'Renew license', 'renew-license', $slug );
 
 
37
 
38
  fs_enqueue_local_style( 'fs_dialog_boxes', '/admin/dialog-boxes.css' );
39
  ?>
@@ -56,7 +78,7 @@
56
  + ' <div class="fs-modal-panel active">' + modalContentHtml + '</div>'
57
  + ' </div>'
58
  + ' <div class="fs-modal-footer">'
59
- + ' <a class="button button-primary button-renew-license" tabindex="3" href="<?php echo $fs->pricing_url() ?>"><?php echo esc_js( $renew_license_button_text ) ?></a>'
60
  + ' <button class="button button-secondary button-close" tabindex="4"><?php fs_esc_js_echo_inline( 'Cancel', 'cancel', $slug ) ?></button>'
61
  + ' </div>'
62
  + ' </div>'
20
  $plugin_name = $plugin_data['Name'];
21
  $plugin_basename = $fs->get_plugin_basename();
22
 
23
+ $license = $fs->_get_license();
24
+
25
+ if ( ! is_object( $license ) ) {
26
+ $purchase_url = $fs->pricing_url();
27
+ } else {
28
+ $subscription = $fs->_get_subscription( $license->id );
29
+
30
+ $purchase_url = $fs->checkout_url(
31
+ is_object( $subscription ) ?
32
+ ( 1 == $subscription->billing_cycle ? WP_FS__PERIOD_MONTHLY : WP_FS__PERIOD_ANNUALLY ) :
33
+ WP_FS__PERIOD_LIFETIME,
34
+ false,
35
+ array( 'licenses' => $license->quota )
36
+ );
37
+ }
38
+
39
  $message = sprintf(
40
  fs_text_inline( 'There is a new version of %s available.', 'new-version-available-message', $slug ) .
41
+ fs_text_inline( ' %s to access version %s security & feature updates, and support.', 'x-for-updates-and-support', $slug ),
42
  '<span id="plugin_name"></span>',
43
+ sprintf(
44
+ '<a id="pricing_url" href="">%s</a>',
45
+ is_object( $license ) ?
46
+ fs_text_inline( 'Renew your license now', 'renew-license-now', $slug ) :
47
+ fs_text_inline( 'Buy a license now', 'buy-license-now', $slug )
48
+ ),
49
  '<span id="new_version"></span>'
50
  );
51
 
53
 
54
  $header_title = fs_text_inline( 'New Version Available', 'new-version-available', $slug );
55
 
56
+ $renew_license_button_text = is_object( $license ) ?
57
+ fs_text_inline( 'Renew license', 'renew-license', $slug ) :
58
+ fs_text_inline( 'Buy license', 'buy-license', $slug );
59
 
60
  fs_enqueue_local_style( 'fs_dialog_boxes', '/admin/dialog-boxes.css' );
61
  ?>
78
  + ' <div class="fs-modal-panel active">' + modalContentHtml + '</div>'
79
  + ' </div>'
80
  + ' <div class="fs-modal-footer">'
81
+ + ' <a class="button button-primary button-renew-license" tabindex="3" href="<?php echo $purchase_url ?>"><?php echo esc_js( $renew_license_button_text ) ?></a>'
82
  + ' <button class="button button-secondary button-close" tabindex="4"><?php fs_esc_js_echo_inline( 'Cancel', 'cancel', $slug ) ?></button>'
83
  + ' </div>'
84
  + ' </div>'
vendor/freemius/templates/forms/premium-versions-upgrade-metadata.php CHANGED
@@ -14,6 +14,22 @@
14
  * @var Freemius $fs
15
  */
16
  $fs = freemius( $VARS['id'] );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
17
  ?>
18
  <script type="text/javascript">
19
  (function( $ ) {
@@ -22,7 +38,7 @@
22
 
23
  $premiumVersionCheckbox.addClass( 'license-expired' );
24
  $premiumVersionCheckbox.data( 'plugin-name', <?php echo json_encode( $fs->get_plugin_data()['Name'] ) ?> );
25
- $premiumVersionCheckbox.data( 'pricing-url', <?php echo json_encode( $fs->pricing_url() ) ?> );
26
  $premiumVersionCheckbox.data( 'new-version', <?php echo json_encode( $VARS['new_version'] ) ?> );
27
  });
28
  })( jQuery );
14
  * @var Freemius $fs
15
  */
16
  $fs = freemius( $VARS['id'] );
17
+
18
+ $license = $fs->_get_license();
19
+
20
+ if ( ! is_object( $license ) ) {
21
+ $purchase_url = $fs->pricing_url();
22
+ } else {
23
+ $subscription = $fs->_get_subscription( $license->id );
24
+
25
+ $purchase_url = $fs->checkout_url(
26
+ is_object( $subscription ) ?
27
+ ( 1 == $subscription->billing_cycle ? WP_FS__PERIOD_MONTHLY : WP_FS__PERIOD_ANNUALLY ) :
28
+ WP_FS__PERIOD_LIFETIME,
29
+ false,
30
+ array( 'licenses' => $license->quota )
31
+ );
32
+ }
33
  ?>
34
  <script type="text/javascript">
35
  (function( $ ) {
38
 
39
  $premiumVersionCheckbox.addClass( 'license-expired' );
40
  $premiumVersionCheckbox.data( 'plugin-name', <?php echo json_encode( $fs->get_plugin_data()['Name'] ) ?> );
41
+ $premiumVersionCheckbox.data( 'pricing-url', <?php echo json_encode( $purchase_url ) ?> );
42
  $premiumVersionCheckbox.data( 'new-version', <?php echo json_encode( $VARS['new_version'] ) ?> );
43
  });
44
  })( jQuery );
vendor/freemius/templates/forms/subscription-cancellation.php ADDED
@@ -0,0 +1,277 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /**
3
+ * @package Freemius
4
+ * @copyright Copyright (c) 2015, Freemius, Inc.
5
+ * @license https://www.gnu.org/licenses/gpl-3.0.html GNU General Public License Version 3
6
+ * @since 2.2.1
7
+ */
8
+
9
+ if ( ! defined( 'ABSPATH' ) ) {
10
+ exit;
11
+ }
12
+
13
+ /**
14
+ * @var array $VARS
15
+ */
16
+ $fs = freemius( $VARS['id'] );
17
+ $slug = $fs->get_slug();
18
+
19
+ /**
20
+ * @var FS_Plugin_License $license
21
+ */
22
+ $license = $VARS['license'];
23
+
24
+ $has_trial = $VARS['has_trial'];
25
+
26
+ $subscription_cancellation_context = $has_trial ?
27
+ fs_text_inline( 'trial', 'trial', $slug ) :
28
+ fs_text_inline( 'subscription', 'subscription', $slug );
29
+
30
+ $plan = $fs->get_plan();
31
+ $module_label = $fs->get_module_label( true );
32
+
33
+ if ( $VARS['is_license_deactivation'] ) {
34
+ $subscription_cancellation_text = '';
35
+ } else {
36
+ $subscription_cancellation_text = sprintf(
37
+ fs_text_inline(
38
+ "Deactivating or uninstalling the %s will automatically disable the license, which you'll be able to use on another site.",
39
+ 'deactivation-or-uninstall-message',
40
+ $slug
41
+ ),
42
+ $module_label
43
+ ) . ' ';
44
+ }
45
+
46
+ $subscription_cancellation_text .= sprintf(
47
+ fs_text_inline(
48
+ 'In case you are NOT planning on using this %s on this site (or any other site) - would you like to cancel the %s as well?',
49
+ 'cancel-subscription-message',
50
+ $slug
51
+ ),
52
+ ( $VARS['is_license_deactivation'] ? fs_text_inline( 'license', 'license', $slug ) : $module_label ),
53
+ $subscription_cancellation_context
54
+ );
55
+
56
+ $cancel_subscription_action_label = sprintf(
57
+ fs_esc_html_inline(
58
+ "Cancel %s - I no longer need any security & feature updates, nor support for %s because I'm not planning to use the %s on this, or any other site.",
59
+ 'cancel-x',
60
+ $slug
61
+ ),
62
+ esc_html( $subscription_cancellation_context ),
63
+ sprintf( '<strong>%s</strong>', esc_html( $fs->get_plugin_title() ) ),
64
+ esc_html( $module_label )
65
+ );
66
+
67
+ $keep_subscription_active_action_label = esc_html( sprintf(
68
+ fs_text_inline(
69
+ "Don't cancel %s - I'm still interested in getting security & feature updates, as well as be able to contact support.",
70
+ 'dont-cancel-x',
71
+ $slug
72
+ ),
73
+ $subscription_cancellation_context
74
+ ) );
75
+
76
+ $subscription_cancellation_text = esc_html( $subscription_cancellation_text );
77
+
78
+ $subscription_cancellation_html = <<< HTML
79
+ <div class="notice notice-error inline"><p></p></div><p>{$subscription_cancellation_text}</p>
80
+ <ul class="subscription-actions">
81
+ <li>
82
+ <label>
83
+ <input type="radio" name="cancel-subscription" value="false"/>
84
+ <span>{$keep_subscription_active_action_label}</span>
85
+ </label>
86
+ </li>
87
+ <li>
88
+ <label>
89
+ <input type="radio" name="cancel-subscription" value="true"/>
90
+ <span>{$cancel_subscription_action_label}</span>
91
+ </label>
92
+ </li>
93
+ </ul>
94
+ HTML;
95
+
96
+ $downgrading_plan_text = fs_text_inline( 'Downgrading your plan', 'downgrading-plan', $slug );
97
+ $cancelling_subscription_text = fs_text_inline( 'Cancelling the subscription', 'cancelling-subscription', $slug );
98
+ /* translators: %1s: Either 'Downgrading your plan' or 'Cancelling the subscription' */
99
+ $downgrade_x_confirm_text = fs_text_inline( '%1s will immediately stop all future recurring payments and your %s plan license will expire in %s.', 'downgrade-x-confirm', $slug );
100
+ $prices_increase_text = fs_text_inline( 'Please note that we will not be able to grandfather outdated pricing for renewals/new subscriptions after a cancellation. If you choose to renew the subscription manually in the future, after a price increase, which typically occurs once a year, you will be charged the updated price.', 'pricing-increase-warning', $slug );
101
+ $after_downgrade_non_blocking_text = fs_text_inline( 'You can still enjoy all %s features but you will not have access to %s security & feature updates, nor support.', 'after-downgrade-non-blocking', $slug );
102
+ $after_downgrade_blocking_text = fs_text_inline( 'Once your license expires you can still use the Free version but you will NOT have access to the %s features.', 'after-downgrade-blocking', $slug );
103
+ $after_downgrade_blocking_text_premium_only = fs_text_inline( 'Once your license expires you will no longer be able to use the %s, unless you activate it again with a valid premium license.', 'after-downgrade-blocking-premium-only', $slug );
104
+
105
+ $subscription_cancellation_confirmation_message = $has_trial ?
106
+ fs_text_inline( 'Cancelling the trial will immediately block access to all premium features. Are you sure?', 'cancel-trial-confirm', $slug ) :
107
+ sprintf(
108
+ '%s %s %s %s',
109
+ sprintf(
110
+ $downgrade_x_confirm_text,
111
+ ($fs->is_only_premium() ? $cancelling_subscription_text : $downgrading_plan_text ),
112
+ $plan->title,
113
+ human_time_diff( time(), strtotime( $license->expiration ) )
114
+ ),
115
+ (
116
+ $license->is_block_features ?
117
+ (
118
+ $fs->is_only_premium() ?
119
+ sprintf( $after_downgrade_blocking_text_premium_only, $module_label ) :
120
+ sprintf( $after_downgrade_blocking_text, $plan->title )
121
+ ) :
122
+ sprintf( $after_downgrade_non_blocking_text, $plan->title, $fs->get_module_label( true ) )
123
+ ),
124
+ $prices_increase_text,
125
+ fs_esc_attr_inline( 'Are you sure you want to proceed?', 'proceed-confirmation', $slug )
126
+ );
127
+
128
+ fs_enqueue_local_style( 'fs_dialog_boxes', '/admin/dialog-boxes.css' );
129
+ ?>
130
+ <script type="text/javascript">
131
+ (function( $ ) {
132
+ var modalHtml =
133
+ '<div class="fs-modal fs-modal-subscription-cancellation fs-modal-subscription-cancellation-<?php echo $fs->get_id() ?>">'
134
+ + ' <div class="fs-modal-dialog">'
135
+ + ' <div class="fs-modal-header">'
136
+ + ' <h4><?php echo esc_attr( sprintf( fs_text_inline( 'Cancel %s?', 'cancel-x', $slug ), ucfirst( $subscription_cancellation_context ) ) ) ?></h4>'
137
+ + ' </div>'
138
+ + ' <div class="fs-modal-body">'
139
+ + ' <div class="fs-modal-panel active">' + <?php echo json_encode( $subscription_cancellation_html ) ?> + '<p class="fs-price-increase-warning" style="display: none;">' + <?php echo json_encode( $prices_increase_text ) ?> + '</p></div>'
140
+ + ' </div>'
141
+ + ' <div class="fs-modal-footer">'
142
+ + ' <a href="#" class="button button-secondary button-close"><?php fs_esc_attr_echo( 'cancel', $slug ) ?></a>'
143
+ + ' <a href="#" class="button button-primary button-deactivate disabled"><?php fs_esc_attr_echo_inline( 'Proceed', 'proceed', $slug ) ?></a>'
144
+ + ' </div>'
145
+ + ' </div>'
146
+ + '</div>',
147
+ $modal = $(modalHtml);
148
+
149
+ $modal.appendTo($('body'));
150
+
151
+ registerEventHandlers();
152
+
153
+ function registerEventHandlers() {
154
+ $modal.on( 'showModal', function() {
155
+ showModal();
156
+ });
157
+
158
+ $modal.on( 'closeModal', function() {
159
+ closeModal();
160
+ });
161
+
162
+ $modal.on('click', '.fs-modal-footer .button', function (evt) {
163
+ evt.preventDefault();
164
+
165
+ if ($(this).hasClass('disabled')) {
166
+ return;
167
+ }
168
+
169
+ var _this = $(this),
170
+ subscriptionCancellationActionEventName = <?php echo json_encode( $fs->get_action_tag( 'subscription_cancellation_action' ) ) ?>;
171
+
172
+ if ( _this.hasClass( 'button-primary' ) ) {
173
+ if ( 'true' !== $( 'input[name="cancel-subscription"]:checked' ).val() ) {
174
+ $modal.trigger( subscriptionCancellationActionEventName, false );
175
+ } else {
176
+ if ( confirm( <?php echo json_encode( $subscription_cancellation_confirmation_message ) ?> ) ) {
177
+ $modal.trigger( subscriptionCancellationActionEventName, true );
178
+ }
179
+ }
180
+ }
181
+ });
182
+
183
+ $modal.on('click', 'input[type="radio"]', function () {
184
+ var
185
+ $selectedOption = $( this ),
186
+ $primaryButton = $modal.find( '.button-primary' ),
187
+ isSelected = ( 'true' === $selectedOption.val() );
188
+
189
+ if ( isSelected ) {
190
+ $primaryButton.html( <?php echo json_encode( sprintf(
191
+ fs_text_inline( 'Cancel %s & Proceed', 'cancel-x-and-proceed', $slug ),
192
+ ucfirst( $subscription_cancellation_context )
193
+ ) ) ?> );
194
+
195
+ $modal.find('.fs-price-increase-warning').show();
196
+ } else {
197
+ $primaryButton.html( <?php echo fs_json_encode_echo_inline( 'Proceed', 'proceed', $slug ) ?> );
198
+ $modal.find('.fs-price-increase-warning').hide();
199
+ }
200
+
201
+ $primaryButton.toggleClass( 'warn', isSelected );
202
+ $primaryButton.removeClass( 'disabled' );
203
+ });
204
+
205
+ // If the user has clicked outside the window, cancel it.
206
+ $modal.on('click', function (evt) {
207
+ var $target = $(evt.target);
208
+
209
+ // If the user has clicked anywhere in the modal dialog, just return.
210
+ if ($target.hasClass('fs-modal-body') || $target.hasClass('fs-modal-footer')) {
211
+ return;
212
+ }
213
+
214
+ // If the user has not clicked the close button and the clicked element is inside the modal dialog, just return.
215
+ if (
216
+ ( ! $target.hasClass( 'button-close' ) ) &&
217
+ ( $target.parents( '.fs-modal-body' ).length > 0 || $target.parents( '.fs-modal-footer' ).length > 0 )
218
+ ) {
219
+ return;
220
+ }
221
+
222
+ closeModal();
223
+
224
+ return false;
225
+ });
226
+ }
227
+
228
+ function showModal() {
229
+ resetModal();
230
+
231
+ // Display the dialog box.
232
+ $modal.addClass('active');
233
+
234
+ $('body').addClass('has-fs-modal');
235
+ }
236
+
237
+ function closeModal() {
238
+ var activeModalsCount = $( '.fs-modal.active' ).length;
239
+
240
+ $modal.removeClass('active');
241
+
242
+ // If child modal, do not remove the "has-fs-modal" class of the <body> element to keep its scrollbars hidden.
243
+ if ( activeModalsCount > 1 ) {
244
+ return;
245
+ }
246
+
247
+ $('body').removeClass('has-fs-modal');
248
+ }
249
+
250
+ function resetModal() {
251
+ updateButtonLabels();
252
+
253
+ if ( 0 === $modal.find( '.subscription-actions' ).length ) {
254
+ $modal.find('.button-deactivate').removeClass('disabled');
255
+ } else {
256
+ $modal.find('.button-deactivate').addClass('disabled');
257
+ }
258
+
259
+ $modal.find('.fs-price-increase-warning').hide();
260
+
261
+ // Uncheck all radio buttons.
262
+ $modal.find('input[type="radio"]').prop('checked', false);
263
+
264
+ $modal.find('.message').hide();
265
+ }
266
+
267
+ function showMessage(message) {
268
+ $modal.find('.message').text(message).show();
269
+ }
270
+
271
+ function updateButtonLabels() {
272
+ $modal.find('.button-primary').text( <?php fs_json_encode_echo_inline( 'Proceed', 'proceed', $slug ) ?> );
273
+
274
+ $modal.find('.button-secondary').text( <?php fs_json_encode_echo( 'cancel', $slug ) ?> );
275
+ }
276
+ })( jQuery );
277
+ </script>
vendor/freemius/templates/pricing.php CHANGED
@@ -105,7 +105,7 @@
105
  }
106
  ?>
107
  <div id="fs_pricing" class="wrap fs-section fs-full-size-wrapper">
108
- <div id="frame"></div>
109
  <form action="" method="POST">
110
  <input type="hidden" name="user_id"/>
111
  <input type="hidden" name="user_email"/>
@@ -128,7 +128,7 @@
128
 
129
  // Append the I-frame into the DOM.
130
  frame = $('<i' + 'frame " src="' + src + '" width="100%" height="' + frame_height + 'px" scrolling="no" frameborder="0" style="background: transparent; width: 1px; min-width: 100%;"><\/i' + 'frame>')
131
- .appendTo('#frame');
132
 
133
  FS.PostMessage.init(base_url, [frame[0]]);
134
 
105
  }
106
  ?>
107
  <div id="fs_pricing" class="wrap fs-section fs-full-size-wrapper">
108
+ <div id="fs_frame"></div>
109
  <form action="" method="POST">
110
  <input type="hidden" name="user_id"/>
111
  <input type="hidden" name="user_email"/>
128
 
129
  // Append the I-frame into the DOM.
130
  frame = $('<i' + 'frame " src="' + src + '" width="100%" height="' + frame_height + 'px" scrolling="no" frameborder="0" style="background: transparent; width: 1px; min-width: 100%;"><\/i' + 'frame>')
131
+ .appendTo('#fs_frame');
132
 
133
  FS.PostMessage.init(base_url, [frame[0]]);
134
 
vendor/freemius/templates/tabs.php CHANGED
@@ -30,6 +30,10 @@
30
  'support' :
31
  $item['menu_slug'];
32
 
 
 
 
 
33
  if ( ! $is_free_wp_org_theme || ! $fs->is_submenu_item_visible( $submenu_name, true ) ) {
34
  continue;
35
  }
30
  'support' :
31
  $item['menu_slug'];
32
 
33
+ if ( 'pricing' === $submenu_name && ! $fs->is_pricing_page_visible() ) {
34
+ continue;
35
+ }
36
+
37
  if ( ! $is_free_wp_org_theme || ! $fs->is_submenu_item_visible( $submenu_name, true ) ) {
38
  continue;
39
  }