first commit

This commit is contained in:
2024-07-15 11:28:08 +02:00
commit f52d538ea5
21891 changed files with 6161164 additions and 0 deletions

View File

@@ -0,0 +1,5 @@
*.log
node_modules
.sass-cache
.idea
package-lock.json

View File

@@ -0,0 +1,97 @@
# JetTabs For Elementor
JetTabs is a plugin that allows adding stylish tabs and accordion widgets with vertical and horizontal layouts and building content inside them using Elementor live page builder widgets.
The plugin makes it simple to create a template with Elementor and add it to the Accordion or Tabs widget. It helps organize content and style it up according to ones needs and preferences.
# ChangeLog
## [2.1.0](https://github.com/ZemezLab/jet-tabs/releases/tag/2.1.0) - 02.12.2019
* Added: Jet Dashboard
## [2.0.6](https://github.com/ZemezLab/jet-tabs/releases/tag/2.0.6) - 29.11.2019
* Added: better compatibility with JetPopup plugin
* Fixed: prevent php error on update DB
## [2.0.5](https://github.com/ZemezLab/jet-tabs/releases/tag/2.0.5) - 15.10.2019
* Added: compatibility with WPML and Polylang plugins
* Added: multiple performance improvements
## [2.0.4](https://github.com/ZemezLab/jet-tabs/releases/tag/2.0.4) - 02.10.2019
* Added: compatibility for the upcoming release of JetStylesManager plugin
* Added: better accessibility in the Tabs and Accordion widgets
* Fixed: ajax loading in the Tabs widget
## [2.0.3](https://github.com/ZemezLab/jet-tabs/releases/tag/2.0.3) - 22.08.2019
* Fixed: prevent PHP errors
## [2.0.2](https://github.com/ZemezLab/jet-tabs/releases/tag/2.0.2) - 16.07.2019
* Fixed: animation of elements in the templates
## [2.0.1](https://github.com/ZemezLab/jet-tabs/releases/tag/2.0.1) - 15.07.2019
* Fixed: minimize frontend scripts file
## [2.0.0](https://github.com/ZemezLab/jet-tabs/releases/tag/2.0.0) - 11.07.2019
* Added: Ajax template loading for tabs and accoddion widgets
* Added: Editor Load Level Option
* Fixed: minor issues
## [1.1.9](https://github.com/ZemezLab/jet-tabs/releases/tag/1.1.9) - 15.06.2019
* Added: no active tabs option
* Added: tabs bottom position
* Added: draft template is not avaliable for frontend now
## [1.1.8](https://github.com/ZemezLab/jet-tabs/releases/tag/1.1.8) - 30.05.2019
* Added: Screen Reader Compliance ([#288](https://github.com/CrocoBlock/suggestions/issues/288))
* Fixed: minor issue in the Accordion Widget
## [1.1.7](https://github.com/ZemezLab/jet-tabs/releases/tag/1.1.7) - 24.04.2019
* Added: the ability to change the tab by clicking on the anchor link
## [1.1.6](https://github.com/ZemezLab/jet-tabs/releases/tag/1.1.6)
* Added: typography and text color controls for tabs content
* Added: js triggers
* Fixed: missing the close button for embedded editor
* Fixed: RTL compatibility in the Switcher Widget
## [1.1.5](https://github.com/ZemezLab/jet-tabs/releases/tag/1.1.5)
* Added: location hash in the Tabs&Accordion widgets
## [1.1.4](https://github.com/ZemezLab/jet-tabs/releases/tag/1.1.4)
* Added: RU localization
* Added: ability using dynamic tags in widgets
* Added: responsive tab controls position in the Tabs Widget
* Added: multiple performance improvements and bug fixes
## [1.1.3](https://github.com/ZemezLab/jet-tabs/releases/tag/1.1.2)
* Added: multiple performance improvements and bug fixes
## [1.1.1](https://github.com/ZemezLab/jet-tabs/releases/tag/1.1.1)
* Added: Elementor 2.1 compatibility
## [1.1.0](https://github.com/ZemezLab/jet-tabs/releases/tag/1.1.0)
* Added: Switcher Widget(NEW)
* Added: JetTabs widget / auto tab switching option
## [1.0.5](https://github.com/ZemezLab/jet-tabs/releases/tag/1.0.5)
* Added: toggle icon position control in Accordion widget
* Updated: edit mode ui styles
## [1.0.4](https://github.com/ZemezLab/jet-tabs/releases/tag/1.0.4)
* Added: multiple performance improvements and bug fixes
* Added: toggle icon position control in Accordion widget
* Updated: animation for better compatibility from third-party js scripts
## [1.0.3](https://github.com/ZemezLab/jet-tabs/releases/tag/1.0.3)
* Added: multiple performance improvements and bug fixes
## [1.0.2](https://github.com/ZemezLab/jet-tabs/releases/tag/1.0.2)
* Fixed: Template edit mode
## [1.0.1](https://github.com/ZemezLab/jet-tabs/releases/tag/1.0.1)
* Fixed: image accordion item url
## [1.0.0](https://github.com/ZemezLab/jet-tabs/releases/tag/1.0.0)
* Init

View File

@@ -0,0 +1 @@
#jet-tabs-settings-page{visibility:hidden}#jet-tabs-settings-page.is-mounted{visibility:visible}.jet-tabs-settings-page{margin:25px 15px 0 15px}.jet-tabs-settings-page .cx-vui-tabs-panel>.cx-vui-subtitle{padding:20px;margin-top:20px}.jet-tabs-settings-page .cx-vui-tabs-panel>.cx-vui-subtitle:first-child{margin-top:0}.jet-tabs-settings-page .jet-tabs-avaliable-widgets-control .cx-vui-checkgroup{display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-box-orient:horizontal;-webkit-box-direction:normal;-webkit-flex-flow:row wrap;-ms-flex-flow:row wrap;flex-flow:row wrap}.jet-tabs-settings-page .jet-tabs-avaliable-widgets-control .cx-vui-checkgroup .cx-vui-checkbox-wrap{width:25%}@media screen and (max-width: 1200px){.jet-tabs-settings-page .jet-tabs-avaliable-widgets-control .cx-vui-checkgroup .cx-vui-checkbox-wrap{width:50%}}@media screen and (max-width: 782px){.jet-tabs-settings-page .jet-tabs-avaliable-widgets-control .cx-vui-checkgroup .cx-vui-checkbox-wrap{width:100%}}.jet-tabs-settings-page__avaliable-controls{display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-box-orient:horizontal;-webkit-box-direction:normal;-webkit-flex-flow:row wrap;-ms-flex-flow:row wrap;flex-flow:row wrap}.jet-tabs-settings-page__avaliable-control{width:33.3333%}@media screen and (max-width: 1200px){.jet-tabs-settings-page__avaliable-control{width:50%}}@media screen and (max-width: 782px){.jet-tabs-settings-page__avaliable-control{width:100%}}.jet-tabs-settings-page__avaliable-control .cx-vui-component{padding:10px 0}.jet-tabs-settings-page__disable-all-widgets{display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-box-pack:start;-webkit-justify-content:flex-start;-ms-flex-pack:start;justify-content:flex-start;-webkit-box-align:center;-webkit-align-items:center;-ms-flex-align:center;align-items:center;border-bottom:1px solid #ECECEC;padding-bottom:20px;margin:20px 0}.jet-tabs-settings-page__disable-all-widgets .cx-vui-component__label{margin-right:10px}

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

Binary file not shown.

After

Width:  |  Height:  |  Size: 24 KiB

View File

@@ -0,0 +1 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?><svg xmlns:svg="http://www.w3.org/2000/svg" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.0" width="32px" height="32px" viewBox="0 0 128 128" xml:space="preserve"><g><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="1"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.67" transform="rotate(45,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.42" transform="rotate(90,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.2" transform="rotate(135,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.12" transform="rotate(180,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.12" transform="rotate(225,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.12" transform="rotate(270,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.12" transform="rotate(315,64,64)"/><animateTransform attributeName="transform" type="rotate" values="0 64 64;315 64 64;270 64 64;225 64 64;180 64 64;135 64 64;90 64 64;45 64 64" calcMode="discrete" dur="800ms" repeatCount="indefinite"></animateTransform></g></svg>

After

Width:  |  Height:  |  Size: 1.2 KiB

View File

@@ -0,0 +1 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?><svg xmlns:svg="http://www.w3.org/2000/svg" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.0" width="64px" height="64px" viewBox="0 0 128 128" xml:space="preserve"><g><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="1"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.67" transform="rotate(45,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.42" transform="rotate(90,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.2" transform="rotate(135,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.12" transform="rotate(180,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.12" transform="rotate(225,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.12" transform="rotate(270,64,64)"/><circle cx="16" cy="64" r="16" fill="#ffffff" fill-opacity="0.12" transform="rotate(315,64,64)"/><animateTransform attributeName="transform" type="rotate" values="0 64 64;315 64 64;270 64 64;225 64 64;180 64 64;135 64 64;90 64 64;45 64 64" calcMode="discrete" dur="800ms" repeatCount="indefinite"></animateTransform></g></svg>

After

Width:  |  Height:  |  Size: 1.2 KiB

View File

@@ -0,0 +1,107 @@
(function( $, settingsPageConfig ) {
'use strict';
Vue.config.devtools = true;
window.JetTabsSettingsPage = new Vue( {
el: '#jet-tabs-settings-page',
data: {
pageOptions: settingsPageConfig.settingsData,
preparedOptions: {},
savingStatus: false,
ajaxSaveHandler: null,
disableAllWidgets: false
},
mounted: function() {
for ( var slug in this.pageOptions['avaliable_widgets']['value'] ) {
if ( 'true' === this.pageOptions['avaliable_widgets']['value'][slug] ) {
this.disableAllWidgets = true;
break;
}
}
this.$el.className = 'is-mounted';
},
watch: {
pageOptions: {
handler( options ) {
let prepared = {};
for ( let option in options ) {
if ( options.hasOwnProperty( option ) ) {
prepared[ option ] = options[option]['value'];
}
}
this.preparedOptions = prepared;
this.saveOptions();
},
deep: true
}
},
methods: {
disableAllWidgetsEvent: function( state ) {
if ( state ) {
for ( var slug in this.pageOptions['avaliable_widgets']['value'] ) {
this.pageOptions['avaliable_widgets']['value'][slug] = 'true';
}
} else {
for ( var slug in this.pageOptions['avaliable_widgets']['value'] ) {
this.pageOptions['avaliable_widgets']['value'][slug] = 'false';
}
}
},
saveOptions: function() {
var self = this;
self.savingStatus = true;
self.ajaxSaveHandler = $.ajax( {
type: 'POST',
url: settingsPageConfig.settingsApiUrl,
dataType: 'json',
data: self.preparedOptions,
beforeSend: function( jqXHR, ajaxSettings ) {
if ( null !== self.ajaxSaveHandler ) {
self.ajaxSaveHandler.abort();
}
},
success: function( responce, textStatus, jqXHR ) {
self.savingStatus = false;
if ( 'success' === responce.status ) {
self.$CXNotice.add( {
message: responce.message,
type: 'success',
duration: 3000,
} );
}
if ( 'error' === responce.status ) {
self.$CXNotice.add( {
message: responce.message,
type: 'error',
duration: 3000,
} );
}
}
} );
},
}
} );
})( jQuery, window.JetTabsSettingsPageConfig );

View File

@@ -0,0 +1,89 @@
(function( $ ) {
'use strict';
var JetTabsEditor,
JetTabsData = window.JetTabsData || {};
JetTabsEditor = {
modal: false,
init: function() {
window.elementor.on( 'preview:loaded', JetTabsEditor.onPreviewLoaded );
},
onPreviewLoaded: function() {
var $previewContents = window.elementor.$previewContents,
elementorFrontend = $('#elementor-preview-iframe')[0].contentWindow.elementorFrontend;
elementorFrontend.hooks.addAction( 'frontend/element_ready/jet-tabs.default', function( $scope ){
$scope.find( '.jet-tabs__edit-cover' ).on( 'click', JetTabsEditor.showTemplatesModal );
$scope.find( '.jet-tabs-new-template-link' ).on( 'click', function( event ) {
window.location.href = $( this ).attr( 'href' );
} );
} );
elementorFrontend.hooks.addAction( 'frontend/element_ready/jet-accordion.default', function( $scope ){
$scope.find( '.jet-toggle__edit-cover' ).on( 'click', JetTabsEditor.showTemplatesModal );
$scope.find( '.jet-toogle-new-template-link' ).on( 'click', function( event ) {
window.location.href = $( this ).attr( 'href' );
} );
} );
elementorFrontend.hooks.addAction( 'frontend/element_ready/jet-switcher.default', function( $scope ){
$scope.find( '.jet-switcher__edit-cover' ).on( 'click', JetTabsEditor.showTemplatesModal );
$scope.find( '.jet-switcher-new-template-link' ).on( 'click', function( event ) {
window.location.href = $( this ).attr( 'href' );
} );
} );
JetTabsEditor.getModal().on( 'hide', function() {
window.elementor.reloadPreview();
});
},
showTemplatesModal: function() {
var editLink = $( this ).data( 'template-edit-link' );
JetTabsEditor.showModal( editLink );
},
showModal: function( link ) {
var $iframe,
$loader;
JetTabsEditor.getModal().show();
$( '#jet-tabs-template-edit-modal .dialog-message').html( '<iframe src="' + link + '" id="jet-tabs-edit-frame" width="100%" height="100%"></iframe>' );
$( '#jet-tabs-template-edit-modal .dialog-message').append( '<div id="jet-tabs-loading"><div class="elementor-loader-wrapper"><div class="elementor-loader"><div class="elementor-loader-boxes"><div class="elementor-loader-box"></div><div class="elementor-loader-box"></div><div class="elementor-loader-box"></div><div class="elementor-loader-box"></div></div></div><div class="elementor-loading-title">Loading</div></div></div>' );
$iframe = $( '#jet-tabs-edit-frame');
$loader = $( '#jet-tabs-loading');
$iframe.on( 'load', function() {
$loader.fadeOut( 300 );
} );
},
getModal: function() {
if ( ! JetTabsEditor.modal ) {
this.modal = elementor.dialogsManager.createWidget( 'lightbox', {
id: 'jet-tabs-template-edit-modal',
closeButton: true,
closeButtonClass: 'eicon-close',
hide: {
onBackgroundClick: false
}
} );
}
return JetTabsEditor.modal;
}
};
$( window ).on( 'elementor:init', JetTabsEditor.init );
})( jQuery );

View File

@@ -0,0 +1 @@
!function(e){"use strict";var t;window.JetTabsData;t={modal:!1,init:function(){window.elementor.on("preview:loaded",t.onPreviewLoaded)},onPreviewLoaded:function(){window.elementor.$previewContents;var o=e("#elementor-preview-iframe")[0].contentWindow.elementorFrontend;o.hooks.addAction("frontend/element_ready/jet-tabs.default",function(o){o.find(".jet-tabs__edit-cover").on("click",t.showTemplatesModal),o.find(".jet-tabs-new-template-link").on("click",function(t){window.location.href=e(this).attr("href")})}),o.hooks.addAction("frontend/element_ready/jet-accordion.default",function(o){o.find(".jet-toggle__edit-cover").on("click",t.showTemplatesModal),o.find(".jet-toogle-new-template-link").on("click",function(t){window.location.href=e(this).attr("href")})}),o.hooks.addAction("frontend/element_ready/jet-switcher.default",function(o){o.find(".jet-switcher__edit-cover").on("click",t.showTemplatesModal),o.find(".jet-switcher-new-template-link").on("click",function(t){window.location.href=e(this).attr("href")})}),t.getModal().on("hide",function(){window.elementor.reloadPreview()})},showTemplatesModal:function(){var o=e(this).data("template-edit-link");t.showModal(o)},showModal:function(o){var i,n;t.getModal().show(),e("#jet-tabs-template-edit-modal .dialog-message").html('<iframe src="'+o+'" id="jet-tabs-edit-frame" width="100%" height="100%"></iframe>'),e("#jet-tabs-template-edit-modal .dialog-message").append('<div id="jet-tabs-loading"><div class="elementor-loader-wrapper"><div class="elementor-loader"><div class="elementor-loader-boxes"><div class="elementor-loader-box"></div><div class="elementor-loader-box"></div><div class="elementor-loader-box"></div><div class="elementor-loader-box"></div></div></div><div class="elementor-loading-title">Loading</div></div></div>'),i=e("#jet-tabs-edit-frame"),n=e("#jet-tabs-loading"),i.on("load",function(){n.fadeOut(300)})},getModal:function(){return t.modal||(this.modal=elementor.dialogsManager.createWidget("lightbox",{id:"jet-tabs-template-edit-modal",closeButton:!0,closeButtonClass:"eicon-close",hide:{onBackgroundClick:!1}})),t.modal}},e(window).on("elementor:init",t.init)}(jQuery);

View File

@@ -0,0 +1,837 @@
// Promise polyfill
!function(e,n){"object"==typeof exports&&"undefined"!=typeof module?n():"function"==typeof define&&define.amd?define(n):n()}(0,function(){"use strict";function e(e){var n=this.constructor;return this.then(function(t){return n.resolve(e()).then(function(){return t})},function(t){return n.resolve(e()).then(function(){return n.reject(t)})})}function n(e){return!(!e||"undefined"==typeof e.length)}function t(){}function o(e){if(!(this instanceof o))throw new TypeError("Promises must be constructed via new");if("function"!=typeof e)throw new TypeError("not a function");this._state=0,this._handled=!1,this._value=undefined,this._deferreds=[],c(e,this)}function r(e,n){for(;3===e._state;)e=e._value;0!==e._state?(e._handled=!0,o._immediateFn(function(){var t=1===e._state?n.onFulfilled:n.onRejected;if(null!==t){var o;try{o=t(e._value)}catch(r){return void f(n.promise,r)}i(n.promise,o)}else(1===e._state?i:f)(n.promise,e._value)})):e._deferreds.push(n)}function i(e,n){try{if(n===e)throw new TypeError("A promise cannot be resolved with itself.");if(n&&("object"==typeof n||"function"==typeof n)){var t=n.then;if(n instanceof o)return e._state=3,e._value=n,void u(e);if("function"==typeof t)return void c(function(e,n){return function(){e.apply(n,arguments)}}(t,n),e)}e._state=1,e._value=n,u(e)}catch(r){f(e,r)}}function f(e,n){e._state=2,e._value=n,u(e)}function u(e){2===e._state&&0===e._deferreds.length&&o._immediateFn(function(){e._handled||o._unhandledRejectionFn(e._value)});for(var n=0,t=e._deferreds.length;t>n;n++)r(e,e._deferreds[n]);e._deferreds=null}function c(e,n){var t=!1;try{e(function(e){t||(t=!0,i(n,e))},function(e){t||(t=!0,f(n,e))})}catch(o){if(t)return;t=!0,f(n,o)}}var a=setTimeout;o.prototype["catch"]=function(e){return this.then(null,e)},o.prototype.then=function(e,n){var o=new this.constructor(t);return r(this,new function(e,n,t){this.onFulfilled="function"==typeof e?e:null,this.onRejected="function"==typeof n?n:null,this.promise=t}(e,n,o)),o},o.prototype["finally"]=e,o.all=function(e){return new o(function(t,o){function r(e,n){try{if(n&&("object"==typeof n||"function"==typeof n)){var u=n.then;if("function"==typeof u)return void u.call(n,function(n){r(e,n)},o)}i[e]=n,0==--f&&t(i)}catch(c){o(c)}}if(!n(e))return o(new TypeError("Promise.all accepts an array"));var i=Array.prototype.slice.call(e);if(0===i.length)return t([]);for(var f=i.length,u=0;i.length>u;u++)r(u,i[u])})},o.resolve=function(e){return e&&"object"==typeof e&&e.constructor===o?e:new o(function(n){n(e)})},o.reject=function(e){return new o(function(n,t){t(e)})},o.race=function(e){return new o(function(t,r){if(!n(e))return r(new TypeError("Promise.race accepts an array"));for(var i=0,f=e.length;f>i;i++)o.resolve(e[i]).then(t,r)})},o._immediateFn="function"==typeof setImmediate&&function(e){setImmediate(e)}||function(e){a(e,0)},o._unhandledRejectionFn=function(e){void 0!==console&&console&&console.warn("Possible Unhandled Promise Rejection:",e)};var l=function(){if("undefined"!=typeof self)return self;if("undefined"!=typeof window)return window;if("undefined"!=typeof global)return global;throw Error("unable to locate global object")}();"Promise"in l?l.Promise.prototype["finally"]||(l.Promise.prototype["finally"]=e):l.Promise=o});
( function( $, elementor, settings ) {
'use strict';
var JetTabs = {
addedScripts: {},
addedStyles: {},
addedAssetsPromises: [],
devMode: JetTabsSettings.devMode || 'false',
init: function() {
var widgets = {
'jet-tabs.default': JetTabs.tabsInit,
'jet-accordion.default': JetTabs.accordionInit,
'jet-image-accordion.default': JetTabs.imageAccordionInit,
'jet-switcher.default': JetTabs.switcherInit,
};
$.each( widgets, function( widget, callback ) {
elementor.hooks.addAction( 'frontend/element_ready/' + widget, callback );
});
},
tabsInit: function( $scope ) {
var $target = $( '.jet-tabs', $scope ).first(),
$widgetId = $target.data( 'id' ),
$window = $( window ),
$controlWrapper = $( '.jet-tabs__control-wrapper', $target ).first(),
$contentWrapper = $( '.jet-tabs__content-wrapper', $target ).first(),
$controlList = $( '> .jet-tabs__control', $controlWrapper ),
$contentList = $( '> .jet-tabs__content', $contentWrapper ),
settings = $target.data( 'settings' ) || {},
toogleEvents = 'mouseenter mouseleave',
scrollOffset,
autoSwitchInterval = null,
curentHash = window.location.hash || false,
tabsArray = curentHash ? curentHash.replace( '#', '' ).split( '&' ) : false;
if ( 'click' === settings['event'] ) {
addClickEvent();
} else {
addMouseEvent();
}
if ( settings['autoSwitch'] ) {
var startIndex = settings['activeIndex'],
currentIndex = startIndex,
controlListLength = $controlList.length;
autoSwitchInterval = setInterval( function() {
if ( currentIndex < controlListLength - 1 ) {
currentIndex++;
} else {
currentIndex = 0;
}
if ( settings['ajaxTemplate'] ) {
ajaxLoadTemplate( currentIndex );
}
switchTab( currentIndex );
}, +settings['autoSwitchDelay'] );
}
if ( settings['ajaxTemplate'] ) {
ajaxLoadTemplate( settings['activeIndex'] );
}
$( window ).on( 'resize.jetTabs orientationchange.jetTabs', function() {
$contentWrapper.css( { 'height': 'auto' } );
} );
/**
* [addClickEvent description]
*/
function addClickEvent() {
$controlList.on( 'click.jetTabs', function() {
var $this = $( this ),
tabId = +$this.data( 'tab' ) - 1,
templateId = $this.data( 'template-id' );
clearInterval( autoSwitchInterval );
if ( settings['ajaxTemplate'] && templateId ) {
ajaxLoadTemplate( tabId );
}
switchTab( tabId );
});
}
/**
* [addMouseEvent description]
*/
function addMouseEvent() {
if ( 'ontouchend' in window || 'ontouchstart' in window ) {
$controlList.on( 'touchstart', function( event ) {
scrollOffset = $( window ).scrollTop();
} );
$controlList.on( 'touchend', function( event ) {
var $this = $( this ),
tabId = +$this.data( 'tab' ) - 1,
templateId = $this.data( 'template-id' );
if ( scrollOffset !== $( window ).scrollTop() ) {
return false;
}
clearInterval( autoSwitchInterval );
if ( settings['ajaxTemplate'] && templateId ) {
ajaxLoadTemplate( tabId );
}
switchTab( tabId );
} );
} else {
$controlList.on( 'mouseenter', function( event ) {
var $this = $( this ),
tabId = +$this.data( 'tab' ) - 1,
templateId = $this.data( 'template-id' );
clearInterval( autoSwitchInterval );
if ( settings['ajaxTemplate'] && templateId ) {
ajaxLoadTemplate( tabId );
}
switchTab( tabId );
} );
}
}
/**
* [switchTab description]
* @param {[type]} curentIndex [description]
* @return {[type]} [description]
*/
function switchTab( curentIndex ) {
var $activeControl = $controlList.eq( curentIndex ),
$activeContent = $contentList.eq( curentIndex ),
activeContentHeight = 'auto',
timer;
$contentWrapper.css( { 'height': $contentWrapper.outerHeight( true ) } );
$controlList.removeClass( 'active-tab' );
$activeControl.addClass( 'active-tab' );
$controlList.attr( 'aria-expanded', 'false' );
$activeControl.attr( 'aria-expanded', 'true' );
$contentList.removeClass( 'active-content' );
activeContentHeight = $activeContent.outerHeight( true );
activeContentHeight += parseInt( $contentWrapper.css( 'border-top-width' ) ) + parseInt( $contentWrapper.css( 'border-bottom-width' ) );
$activeContent.addClass( 'active-content' );
$contentList.attr( 'aria-hidden', 'true' );
$activeContent.attr( 'aria-hidden', 'false' );
$contentWrapper.css( { 'height': activeContentHeight } );
$window.trigger( 'jet-tabs/tabs/show-tab-event/before', {
widgetId: $widgetId,
tabIndex: curentIndex,
} );
if ( timer ) {
clearTimeout( timer );
}
timer = setTimeout( function() {
$window.trigger( 'jet-tabs/tabs/show-tab-event/after', {
widgetId: $widgetId,
tabIndex: curentIndex,
} );
$contentWrapper.css( { 'height': 'auto' } );
}, 500 );
}
/**
* [ajaxLoadTemplate description]
* @param {[type]} $index [description]
* @return {[type]} [description]
*/
function ajaxLoadTemplate( $index ) {
var $contentHolder = $contentList.eq( $index ),
templateLoaded = $contentHolder.data( 'template-loaded' ) || false,
templateId = $contentHolder.data( 'template-id' ),
loader = $( '.jet-tabs-loader', $contentHolder );
if ( templateLoaded ) {
return false;
}
$contentHolder.data( 'template-loaded', true );
$.ajax( {
type: 'GET',
url: window.JetTabsSettings.templateApiUrl,
dataType: 'json',
data: {
'id': templateId,
'dev': window.JetTabsSettings.devMode
},
success: function( responce, textStatus, jqXHR ) {
var templateContent = responce['template_content'],
templateScripts = responce['template_scripts'],
templateStyles = responce['template_styles'];
for ( var scriptHandler in templateScripts ) {
JetTabs.addedAssetsPromises.push( JetTabs.loadScriptAsync( scriptHandler, templateScripts[ scriptHandler ] ) );
}
for ( var styleHandler in templateStyles ) {
JetTabs.addedAssetsPromises.push( JetTabs.loadStyle( styleHandler, templateStyles[ styleHandler ] ) );
}
Promise.all( JetTabs.addedAssetsPromises ).then( value => {
loader.remove();
$contentHolder.append( templateContent );
JetTabs.elementorFrontendInit( $contentHolder );
}, reason => {
console.log( 'Script Loaded Error' );
});
}
} );//end
}
// Hash Watch Handler
if ( tabsArray ) {
$controlList.each( function( index ) {
var $this = $( this ),
id = $this.attr( 'id' ),
templateId = $this.data( 'template-id' ),
tabIndex = index;
tabsArray.forEach( function( itemHash, i ) {
if ( itemHash === id ) {
if ( settings['ajaxTemplate'] && templateId ) {
ajaxLoadTemplate( tabIndex );
}
switchTab( tabIndex );
}
} );
} );
}
$( document ).on( 'click.jetTabAnchor', 'a[href*="#jet-tabs-control-"]', function( event ) {
var $hash = $( this.hash );
if ( ! $hash.closest( $scope )[0] ) {
return;
}
var tabInx = $hash.data( 'tab' ) - 1;
if ( settings['ajaxTemplate'] ) {
ajaxLoadTemplate( tabInx );
}
switchTab( tabInx );
} );
},// tabsInit end
switcherInit: function( $scope ) {
var $target = $( '.jet-switcher', $scope ).first(),
$widgetId = $target.data( 'id' ),
$window = $( window ),
$controlWrapper = $( '.jet-switcher__control-wrapper', $target ).first(),
$contentWrapper = $( '.jet-switcher__content-wrapper', $target ).first(),
$controlInstance = $( '> .jet-switcher__control-instance', $controlWrapper ),
$controlList = $( '> .jet-switcher__control-instance > .jet-switcher__control, > .jet-switcher__control', $controlWrapper ),
$contentList = $( '> .jet-switcher__content', $contentWrapper ),
$disableContent = $( '> .jet-switcher__content--disable', $contentWrapper ),
$enableContent = $( '> .jet-switcher__content--enable', $contentWrapper ),
state = $target.hasClass( 'jet-switcher--disable' ),
settings = $target.data( 'settings' ) || {},
toogleEvents = 'mouseenter mouseleave',
scrollOffset;
if ( 'ontouchend' in window || 'ontouchstart' in window ) {
addTouchEvent();
} else {
addClickEvent();
}
$( window ).on( 'resize.jetSwitcher orientationchange.jetSwitcher', function() {
$contentWrapper.css( { 'height': 'auto' } );
} );
function addClickEvent() {
$controlInstance.on( 'click.jetSwitcher', function() {
switchTab();
});
}
function addTouchEvent() {
$controlInstance.on( 'touchstart', function( event ) {
scrollOffset = $( window ).scrollTop();
} );
$controlInstance.on( 'touchend', function( event ) {
if ( scrollOffset !== $( window ).scrollTop() ) {
return false;
}
switchTab();
} );
}
function switchTab( curentIndex ) {
var $activeControl, $activeContent,
activeContentHeight = 'auto',
timer;
$contentWrapper.css( { 'height': $contentWrapper.outerHeight( true ) } );
$target.toggleClass( 'jet-switcher--disable jet-switcher--enable' );
if ( $target.hasClass( 'jet-switcher--disable' ) ) {
state = false;
} else {
state = true;
}
$activeControl = ! state ? $controlList.eq(0) : $controlList.eq(1);
$activeContent = ! state ? $contentList.eq(0) : $contentList.eq(1);
$contentList.removeClass( 'active-content' );
activeContentHeight = $activeContent.outerHeight( true );
activeContentHeight += parseInt( $contentWrapper.css( 'border-top-width' ) ) + parseInt( $contentWrapper.css( 'border-bottom-width' ) );
$activeContent.addClass( 'active-content' );
$controlList.attr( 'aria-expanded', 'false' );
$activeControl.attr( 'aria-expanded', 'true' );
$contentList.attr( 'aria-hidden', 'true' );
$activeContent.attr( 'aria-hidden', 'false' );
$contentWrapper.css( { 'height': activeContentHeight } );
$window.trigger( 'jet-tabs/switcher/show-case-event/before', {
widgetId: $widgetId,
caseIndex: curentIndex,
} );
if ( timer ) {
clearTimeout( timer );
}
timer = setTimeout( function() {
$window.trigger( 'jet-tabs/switcher/show-case-event/after', {
widgetId: $widgetId,
caseIndex: curentIndex,
} );
$contentWrapper.css( { 'height': 'auto' } );
}, 500 );
}
},
accordionInit: function( $scope ) {
var $target = $( '.jet-accordion', $scope ).first(),
$widgetId = $target.data( 'id' ),
$window = $( window ),
$controlsList = $( '> .jet-accordion__inner > .jet-toggle > .jet-toggle__control', $target ),
settings = $target.data( 'settings' ),
$toggleList = $( '> .jet-accordion__inner > .jet-toggle', $target ),
timer, timer2,
curentHash = window.location.hash || false,
togglesArray = curentHash ? curentHash.replace( '#', '' ).split( '&' ) : false;
$( window ).on( 'resize.jetAccordion orientationchange.jetAccordion', function() {
var activeToggle = $( '> .jet-accordion__inner > .active-toggle', $target ),
activeToggleContent = $( '> .jet-toggle__content', activeToggle );
activeToggleContent.css( { 'height': 'auto' } );
} );
$controlsList.on( 'click.jetAccordion', function() {
var $this = $( this ),
$toggle = $this.closest( '.jet-toggle' ),
toggleIndex = +$this.data( 'toggle' ) - 1;
if ( settings['collapsible'] ) {
if ( ! $toggle.hasClass( 'active-toggle' ) ) {
$toggleList.each( function( index ) {
var $this = $( this ),
$toggleControl = $( '> .jet-toggle__control', $this ),
$toggleContent = $( '> .jet-toggle__content', $this ),
$toggleContentHeight = $( '> .jet-toggle__content > .jet-toggle__content-inner', $this ).outerHeight();
$toggleContentHeight += parseInt( $toggleContent.css( 'border-top-width' ) ) + parseInt( $toggleContent.css( 'border-bottom-width' ) );
if ( index === toggleIndex ) {
$this.addClass( 'active-toggle' );
$toggleContent.css( { 'height': $toggleContentHeight } );
$toggleControl.attr( 'aria-expanded', 'true' );
$toggleContent.attr( 'aria-hidden', 'false' );
if ( settings['ajaxTemplate'] ) {
ajaxLoadTemplate( toggleIndex );
}
$window.trigger( 'jet-tabs/accordion/show-toggle-event/before', {
widgetId: $widgetId,
toggleIndex: toggleIndex,
} );
if ( timer ) {
clearTimeout( timer );
}
timer = setTimeout( function() {
$window.trigger( 'jet-tabs/accordion/show-toggle-event/after', {
widgetId: $widgetId,
toggleIndex: toggleIndex,
} );
$toggleContent.css( { 'height': 'auto' } );
}, 300 );
} else {
if ( $this.hasClass( 'active-toggle' ) ) {
$toggleContent.css( { 'height': $toggleContent.outerHeight() } );
$this.removeClass( 'active-toggle' );
$toggleControl.attr( 'aria-expanded', 'false' );
$toggleContent.attr( 'aria-hidden', 'true' );
if ( timer2 ) {
clearTimeout( timer2 );
}
timer2 = setTimeout( function() {
$toggleContent.css( { 'height': 0 } );
}, 5 );
}
}
} );
}
} else {
var $toggleContent = $( '> .jet-toggle__content', $toggle ),
$toggleContentHeight = $( '> .jet-toggle__content > .jet-toggle__content-inner', $toggle ).outerHeight();
$toggleContentHeight += parseInt( $toggleContent.css( 'border-top-width' ) ) + parseInt( $toggleContent.css( 'border-bottom-width' ) );
$toggle.toggleClass( 'active-toggle' );
if ( $toggle.hasClass( 'active-toggle') ) {
$toggleContent.css( { 'height': $toggleContentHeight } );
$this.attr( 'aria-expanded', 'true' );
$toggleContent.attr( 'aria-hidden', 'false' );
if ( settings['ajaxTemplate'] ) {
ajaxLoadTemplate( toggleIndex );
}
$window.trigger( 'jet-tabs/accordion/show-toggle-event/before', {
widgetId: $widgetId,
toggleIndex: toggleIndex,
} );
if ( timer ) {
clearTimeout( timer );
}
timer = setTimeout( function() {
$window.trigger( 'jet-tabs/accordion/show-toggle-event/after', {
widgetId: $widgetId,
toggleIndex: toggleIndex,
} );
$toggleContent.css( { 'height': 'auto' } );
}, 300 );
} else {
$toggleContent.css( { 'height': $toggleContent.outerHeight() } );
$this.attr( 'aria-expanded', 'false' );
$toggleContent.attr( 'aria-hidden', 'true' );
if ( timer2 ) {
clearTimeout( timer2 );
}
timer2 = setTimeout( function() {
$toggleContent.css( { 'height': 0 } );
}, 5 );
}
}
});
/**
* [ajaxLoadTemplate description]
* @param {[type]} $index [description]
* @return {[type]} [description]
*/
function ajaxLoadTemplate( $index ) {
var $toggle = $toggleList.eq( $index ),
$contentHolder = $( '> .jet-toggle__content', $toggle ),
$contentHolderInner = $( '> .jet-toggle__content > .jet-toggle__content-inner', $toggle ),
templateLoaded = $contentHolder.data( 'template-loaded' ) || false,
templateId = $contentHolder.data( 'template-id' ),
loader = $( '.jet-tabs-loader', $contentHolderInner );
if ( templateLoaded ) {
return false;
}
$contentHolder.data( 'template-loaded', true );
$.ajax( {
type: 'GET',
url: window.JetTabsSettings.templateApiUrl,
dataType: 'json',
data: {
'id': templateId,
'dev': window.JetTabsSettings.devMode
},
success: function( responce, textStatus, jqXHR ) {
var templateContent = responce['template_content'],
templateScripts = responce['template_scripts'],
templateStyles = responce['template_styles'];
for ( var scriptHandler in templateScripts ) {
JetTabs.addedAssetsPromises.push( JetTabs.loadScriptAsync( scriptHandler, templateScripts[ scriptHandler ] ) );
}
for ( var styleHandler in templateStyles ) {
JetTabs.addedAssetsPromises.push( JetTabs.loadStyle( styleHandler, templateStyles[ styleHandler ] ) );
}
Promise.all( JetTabs.addedAssetsPromises ).then( value => {
loader.remove();
$contentHolderInner.append( templateContent );
JetTabs.elementorFrontendInit( $contentHolderInner );
}, reason => {
console.log( 'Script Loaded Error' );
});
}
} );//end
}
// Hash Watch Handler
if ( togglesArray ) {
$controlsList.each( function( index ) {
var $this = $( this ),
id = $this.attr( 'id' ),
toggleIndex = index;
togglesArray.forEach( function( itemHash, i ) {
if ( itemHash === id ) {
$this.trigger('click.jetAccordion');
}
} );
} );
}
$( document ).on( 'click.jetAccordionAnchor', 'a[href*="#jet-toggle-control-"]', function( event ) {
var $hash = $( this.hash );
if ( ! $hash.closest( $scope )[0] ) {
return;
}
$hash.trigger( 'click.jetAccordion' );
} );
},// accordionInit end
imageAccordionInit: function( $scope) {
var $target = $( '.jet-image-accordion', $scope ),
instance = null,
settings = {};
if ( ! $target.length ) {
return;
}
settings = $target.data( 'settings' );
instance = new jetImageAccordion( $target, settings );
instance.init();
},// imageAccordionInit end
loadScriptAsync: function( script, uri ) {
if ( JetTabs.addedScripts.hasOwnProperty( script ) ) {
return script;
}
JetTabs.addedScripts[ script ] = uri;
return new Promise( ( resolve, reject ) => {
var tag = document.createElement( 'script' );
tag.src = uri;
tag.async = true;
tag.onload = () => {
resolve( script );
};
document.head.appendChild( tag );
});
},
loadStyle: function( style, uri ) {
if ( JetTabs.addedStyles.hasOwnProperty( style ) && JetTabs.addedStyles[ style ] === uri) {
return style;
}
JetTabs.addedStyles[ style ] = uri;
return new Promise( ( resolve, reject ) => {
var tag = document.createElement( 'link' );
tag.id = style;
tag.rel = 'stylesheet';
tag.href = uri;
tag.type = 'text/css';
tag.media = 'all';
tag.onload = () => {
resolve( style );
};
document.head.appendChild( tag );
});
},
elementorFrontendInit: function( $container ) {
$container.find( 'div[data-element_type]' ).each( function() {
var $this = $( this ),
elementType = $this.data( 'element_type' );
if ( ! elementType ) {
return;
}
try {
if ( 'widget' === elementType ) {
elementType = $this.data( 'widget_type' );
window.elementorFrontend.hooks.doAction( 'frontend/element_ready/widget', $this, $ );
}
window.elementorFrontend.hooks.doAction( 'frontend/element_ready/global', $this, $ );
window.elementorFrontend.hooks.doAction( 'frontend/element_ready/' + elementType, $this, $ );
} catch ( err ) {
console.log(err);
$this.remove();
return false;
}
} );
}
};
/**
* jetImageAccordion Class
*
* @return {void}
*/
window.jetImageAccordion = function( $selector, settings ) {
var self = this,
$instance = $selector,
$itemsList = $( '.jet-image-accordion__item', $instance ),
itemslength = $itemsList.length,
defaultSettings = {
orientation: 'vertical',
activeSize: {
size: 50,
unit: '%'
},
duration: 500,
activeItem: -1
},
settings = settings || {},
activeItem = -1;
/**
* Checking options, settings and options merging
*/
settings = $.extend( defaultSettings, settings );
activeItem = settings['activeItem'];
/**
* Layout Build
*/
this.layoutBuild = function( ) {
$itemsList.css( {
'transition-duration': settings.duration + 'ms'
} );
$itemsList.each( function( index ) {
if ( index === activeItem ) {
$( this ).addClass( 'active-accordion' );
self.layoutRender();
}
} );
$( '.jet-image-accordion__image-instance', $itemsList ).imagesLoaded().progress( function( instance, image ) {
var $image = $( image.img ),
$parentItem = $image.closest( '.jet-image-accordion__item' ),
$loader = $( '.jet-image-accordion__item-loader', $parentItem );
$image.addClass( 'loaded' );
$loader.fadeTo( 250, 0, function() {
$( this ).remove();
} );
});
self.layoutRender();
self.addEvents();
}
/**
* Layout Render
*/
this.layoutRender = function( $accordionItem ) {
var $accordionItem = $accordionItem || false,
activeSize = settings.activeSize.size,
basis = ( 100 / itemslength ).toFixed(2),
grow = activeSize / ( ( 100 - activeSize ) / ( itemslength - 1 ) );
$( '.jet-image-accordion__item:not(.active-accordion)', $instance ).css( {
'flex-grow': 1
} );
$( '.active-accordion', $instance ).css( {
'flex-grow': grow
} );
}
this.addEvents = function() {
var toogleEvents = 'mouseenter',
scrollOffset = $( window ).scrollTop();
if ( 'ontouchend' in window || 'ontouchstart' in window ) {
$itemsList.on( 'touchstart.jetImageAccordion', function( event ) {
scrollOffset = $( window ).scrollTop();
} );
$itemsList.on( 'touchend.jetImageAccordion', function( event ) {
event.stopPropagation();
var $this = $( this );
if ( scrollOffset !== $( window ).scrollTop() ) {
return false;
}
if ( ! $this.hasClass( 'active-accordion' ) ) {
$itemsList.removeClass( 'active-accordion' );
$this.addClass( 'active-accordion' );
} else {
$itemsList.removeClass( 'active-accordion' );
}
self.layoutRender();
} );
} else {
$itemsList.on( 'mouseenter', function( event ) {
var $this = $( this );
if ( ! $this.hasClass( 'active-accordion' ) ) {
$itemsList.removeClass( 'active-accordion' );
$this.addClass( 'active-accordion' );
}
self.layoutRender();
} );
}
$instance.on( 'mouseleave.jetImageAccordion', function( event ) {
$itemsList.removeClass( 'active-accordion' );
if ( -1 !== activeItem ) {
$itemsList.eq( activeItem ).addClass( 'active-accordion' );
}
self.layoutRender();
} );
/*$( document ).on( 'touchend.jetImageAccordion', function( event ) {
$itemsList.removeClass( 'active-accordion' );
self.layoutRender();
} );*/
}
/**
* Init
*/
this.init = function() {
self.layoutBuild();
}
}
$( window ).on( 'elementor/frontend/init', JetTabs.init );
}( jQuery, window.elementorFrontend, window.JetTabsSettings ) );

File diff suppressed because one or more lines are too long

View File

@@ -0,0 +1,229 @@
.jet-accordion {
&__inner {
display: flex;
flex-flow: column;
align-items: stretch;
}
}
.jet-toggle {
display: flex;
flex-flow: column;
align-items: stretch;
//overflow: hidden; // @since 1.1.8 Disabled this property to prevent cut box-shadow
border: 1px solid #e8e8f6;
border-radius: 5px;
margin-bottom: 20px;
background-color: white;
&:first-child {
margin-top: 0 !important;
}
&:last-child {
margin-bottom: 0 !important;
}
&.active-toggle {
> .jet-toggle__control {
.jet-toggle__label-icon {
.icon-normal {
display: none;
}
.icon-active {
display: flex;
}
}
}
> .jet-toggle__content {
height: auto;
}
}
&__control {
padding: 15px 20px;
display: flex;
flex-flow: row nowrap;
justify-content: flex-start;
align-items: center;
cursor: pointer;
&:hover {}
}
&__label-icon {
margin-right: 10px;
&.jet-toggle-icon-position-right {
margin-left: 10px;
margin-right: 0;
order: 3;
}
.icon-active {
display: none;
}
i {
display: flex;
}
}
&__icon {
display: flex;
justify-content: center;
align-items: center;
font-size: 15px;
width: 25px;
height: 25px;
border-radius: 50%;
color: white;
background-color: #6ec1e4;
}
&__label-text {
font-weight: 600;
color: #7a7a7a;
user-select: none;
}
&__content {
height: 0;
overflow: hidden;
transition: height 0.5s ease;
.jet-toggle:not(.active-toggle) > & {
padding: 0 !important;
margin: 0 !important;
border: none !important;
box-shadow: none !important;
}
> .elementor {
> .elementor-inner {
margin: 0;
}
}
}
&__content-inner {
position: relative;
padding: 30px;
}
&-fade-effect {
&.active-toggle {
.jet-toggle__content {
.jet-toggle__content-inner {
animation-name: fade;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
}
&-zoom-in-effect {
&.active-toggle {
.jet-toggle__content {
.jet-toggle__content-inner {
animation-name: zoomIn;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
}
&-zoom-out-effect {
&.active-toggle {
.jet-toggle__content {
.jet-toggle__content-inner {
animation-name: zoomOut;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
}
&-move-up-effect {
&.active-toggle {
.jet-toggle__content {
.jet-toggle__content-inner {
animation-name: moveUp;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
}
&-fall-perspective-effect {
&.active-toggle {
.jet-toggle__content {
.jet-toggle__content-inner {
animation-name: fallPerspective;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
}
}
.jet-toggle__edit-cover {
display: flex;
justify-content: center;
align-items: center;
position: absolute;
box-sizing: border-box;
height: 30px;
padding: 5px 10px;
right: 15px;
top: 15px;
border-radius: 3px;
background-color: #b7084e;
z-index: 99;
cursor: pointer;
transition: opacity 0.3s ease;
box-shadow: 0 0 0 0 rgba( 183, 8, 78, 0.6);
animation: edit-button-pulse 5s infinite;
i {
font-size: 14px;
color: white;
margin-right: 5px;
}
span{
font-family: Roboto, Arial, Helvetica, Verdana, sans-serif;
font-size: 13px;
color: white;
}
&:hover {
background-color: #840739;
animation: none;
}
}
.jet-toggle-no-template-message {
text-align: center;
padding: 10px;
}
.jet-toggle-new-template-link {
color: #6ec1e4;
text-decoration: underline;
}

View File

@@ -0,0 +1,194 @@
.jet-image-accordion {
&__list {
display: flex;
flex-wrap: nowrap;
position: relative;
width: 100%;
height: 600px;
overflow: hidden;
z-index: 1;
}
&__item {
display: flex;
align-items: stretch;
overflow: hidden;
flex-shrink: 0;
flex-basis: auto;
transition-property: all;
transition-duration: 500ms;
transition-timing-function: cubic-bezier(.83,.08,.16,.97);
backface-visibility: hidden;
transform: translateZ(0);
&.active-accordion {
flex-grow: 2;
.jet-image-accordion__content {
opacity: 1;
transition-delay: 500ms;
}
}
&:before {
position: absolute;
width: 100%;
height: 100%;
display: block;
top: 0;
left: 0;
z-index: 1;
content: '';
}
}
&__image-instance {
position: absolute;
top: 0;
left: 0;
object-fit: cover;
width: 100%;
height: 100% !important;
opacity: 0;
transition: opacity 300ms ease;
&.loaded {
opacity: 1;
}
}
&__content {
position: absolute;
display: flex;
flex-flow: column;
top: 0;
left: 0;
width: 100%;
height: 100%;
padding: 20px;
overflow: hidden;
opacity: 0;
z-index: 2;
background-color: rgba( 0,0,0, 0.5 );
transition: opacity 300ms ease;
&:empty {
display: none;
}
}
&__title {
align-self: stretch;
text-align: left;
color: white;
font-size: 20px;
}
&__desc {
align-self: stretch;
text-align: left;
color: white;
font-size: 16px;
margin-bottom: 20px;
}
&__button {
font-weight: 500;
background-color: #6ec1e4;
}
&__item-loader {
position: absolute;
display: none;
justify-content: center;
align-items: center;
width: 100%;
height: 100%;
left: 0;
top: 0;
background-color: rgba( 0,0,0, 0.5 );
z-index: 1;
.jet-image-accordion__image-instance ~ & {
display: flex;
}
span {
width: 32px;
height: 32px;
display: block;
background: url( '../images/spinner-32.svg' ) no-repeat;
}
}
&.jet-image-accordion-vertical-orientation {
.jet-image-accordion__list {
flex-direction: row;
align-items: stretch;
}
.jet-image-accordion__item {
margin-top: 0 !important;
margin-bottom: 0 !important;
&:first-child {
margin-left: 0 !important;
}
&:last-child {
margin-right: 0 !important;
}
}
}
&.jet-image-accordion-horizontal-orientation {
.jet-image-accordion__list {
flex-direction: column;
align-items: stretch;
}
.jet-image-accordion__item {
margin-left: 0 !important;
margin-right: 0 !important;
&:first-child {
margin-top: 0 !important;
}
&:last-child {
margin-bottom: 0 !important;
}
}
}
&.jet-image-accordion-sine-ease {
.jet-image-accordion__item {
transition-timing-function: cubic-bezier(0.390, 0.575, 0.565, 1.000);
}
}
&.jet-image-accordion-quint-ease {
.jet-image-accordion__item {
transition-timing-function: cubic-bezier(0.230, 1.000, 0.320, 1.000);
}
}
&.jet-image-accordion-cubic-ease {
.jet-image-accordion__item {
transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
}
}
&.jet-image-accordion-expo-ease {
.jet-image-accordion__item {
transition-timing-function: cubic-bezier(0.190, 1.000, 0.220, 1.000);
}
}
&.jet-image-accordion-back-ease {
.jet-image-accordion__item {
transition-timing-function: cubic-bezier(0.175, 0.885, 0.320, 1.275);
}
}
}

View File

@@ -0,0 +1,304 @@
.jet-switcher {
display: flex;
flex-flow: column;
justify-content: flex-start;
align-items: stretch;
&__control-wrapper {
display: flex;
justify-content: center;
align-items: center;
}
&__control-instance {
display: flex;
align-items: center;
position: relative;
cursor: pointer;
background-color: #f7f7fb;
border-radius: 50px;
transition: background-color 0.3s cubic-bezier(.44,.95,.57,.97);
}
&__control-handler {
position: absolute;
border-radius: inherit;
display: flex;
align-items: stretch;
top: 0;
z-index: 1;
span {
flex: 0 1 100%;
margin: 3px;
transition: all 0.3s cubic-bezier(.44,.95,.57,.97);
border-radius: inherit;
}
}
&__control {
display: flex;
justify-content: center;
align-items: center;
cursor: pointer;
outline: none;
pointer-events: none;
z-index: 2;
text-align: center;
transition: all 0.3s cubic-bezier(.44,.95,.57,.97);
&--disable {
}
&--enable {
}
}
&__label-text {
user-select: none;
}
&__content-wrapper {
width: 100%;
position: relative;
transition: height 0.25s cubic-bezier(.44,.96,.5,.98);
overflow: hidden;
}
&__content {
width: 100%;
top: 0;
left: 0;
position: absolute;
opacity: 0;
pointer-events: none;
> .elementor {
> .elementor-inner {
margin: 0;
}
}
&.active-content {
position: relative;
pointer-events: auto;
opacity: 1;
}
}
}
.jet-switcher--preset-1 {
&.jet-switcher--disable {
.jet-switcher__control-handler {
transform: translateX(0);
span {
background-color: #c3c3c3;
}
}
.jet-switcher__control--disable {
color: #fff;
}
}
&.jet-switcher--enable {
.jet-switcher__control-handler {
transform: translateX(100%);
.rtl & {
transform: translateX(-100%);
}
span {
background-color: #61ce70;
}
}
.jet-switcher__control--enable {
color: #fff;
}
}
.jet-switcher__control-instance {
width: 160px;
height: 50px;
justify-content: flex-start;
}
.jet-switcher__control {
max-width: 50%;
}
.jet-switcher__control-handler {
width: 50%;
height: 100%;
transition: transform 0.3s cubic-bezier(.44,.95,.57,.97);
}
.jet-switcher__control--disable {
width: 50%;
height: 100%;
}
.jet-switcher__control--enable {
width: 50%;
height: 100%;
}
}
.jet-switcher--preset-2 {
&.jet-switcher--disable {
.jet-switcher__control-handler {
left: 0;
span {
background-color: #c3c3c3;
}
}
}
&.jet-switcher--enable {
.jet-switcher__control-handler {
left: calc(100% - 30px);
span {
background-color: #61ce70;
}
}
}
.jet-switcher__control-instance {
width: 80px;
height: 40px;
}
.jet-switcher__control-handler {
width: 60px;
height: 100%;
transition: left 0.3s cubic-bezier(.44,.95,.57,.97);
}
.jet-switcher__control--disable {
margin-right: 15px;
.rtl & {
margin-left: 15px;
}
}
.jet-switcher__control--enable {
margin-left: 15px;
.rtl & {
margin-right: 15px;
}
}
}
.jet-switcher {
&-fade-effect {
.jet-tabs__content {
&.active-content {
animation-name: fade;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
&-zoom-in-effect {
.jet-switcher__content {
&.active-content {
animation-name: zoomIn;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
&-zoom-out-effect {
.jet-switcher__content {
&.active-content {
animation-name: zoomOut;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
&-move-up-effect {
.jet-switcher__content {
&.active-content {
animation-name: moveUp;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
&-fall-perspective-effect {
.jet-switcher__content {
&.active-content {
animation-name: fallPerspective;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
}
.jet-switcher__edit-cover {
display: flex;
justify-content: center;
align-items: center;
position: absolute;
box-sizing: border-box;
height: 30px;
padding: 5px 10px;
right: 15px;
top: 15px;
border-radius: 3px;
background-color: #b7084e;
z-index: 99;
cursor: pointer;
transition: opacity 0.3s ease;
box-shadow: 0 0 0 0 rgba( 183, 8, 78, 0.6);
animation: edit-button-pulse 5s infinite;
i {
font-size: 14px;
color: white;
margin-right: 5px;
}
span {
font-family: Roboto, Arial, Helvetica, Verdana, sans-serif;
font-size: 13px;
color: white;
}
&:hover {
background-color: #840739;
animation: none;
}
}
.jet-switcher-no-template-message {
text-align: center;
padding: 10px;
}
.jet-switcher-new-template-link {
color: #6ec1e4;
text-decoration: underline;
}

View File

@@ -0,0 +1,475 @@
.jet-tabs {
display: flex;
&__control-wrapper {
display: flex;
background-color: white;
overflow: hidden;
z-index: 1;
}
&__content-wrapper {
position: relative;
overflow: hidden;
background-color: white;
transition: height 0.25s cubic-bezier(.44,.96,.5,.98);
}
&__control {
cursor: pointer;
outline: none;
&.jet-tabs__control-icon-left {
.jet-tabs__control-inner {
flex-flow: row nowrap;
}
}
&.jet-tabs__control-icon-top {
.jet-tabs__control-inner {
flex-flow: column nowrap;
}
}
}
&__control-inner {
padding: 10px 20px;
display: flex;
justify-content: center;
align-items: center;
}
&__label-icon {
margin-right: 5px;
line-height: 1;
.active-tab & {
color: #6ec1e4;
}
}
&__label-image {
width: 25px;
}
&__label-text {
.active-tab & {
color: #6ec1e4;
}
}
&__content {
width: 100%;
top: 0;
left: 0;
position: absolute;
opacity: 0;
pointer-events: none;
padding: 10px;
> .elementor {
> .elementor-inner {
margin: 0;
}
}
&.active-content {
position: relative;
pointer-events: auto;
opacity: 1;
.jet-popup--hide-state & {
pointer-events: none;
}
}
}
&-position-top {
flex-flow: column nowrap;
align-items: stretch;
.jet-tabs__control-wrapper {
align-self: flex-start;
flex-flow: row wrap;
justify-content: flex-start;
align-items: center;
border-width: 1px 1px 0 1px;
order: 1;
}
.jet-tabs__content-wrapper {
order: 2;
border-top-width: 1px;
}
}
&-position-bottom {
flex-flow: column nowrap;
align-items: stretch;
.jet-tabs__control-wrapper {
align-self: flex-start;
flex-flow: row wrap;
justify-content: flex-start;
align-items: center;
border-width: 0 1px 1px 1px;
order: 2;
}
.jet-tabs__content-wrapper {
order: 1;
}
}
&-position-left {
flex-flow: row nowrap;
.jet-tabs__control-wrapper {
flex: 0 1 auto;
min-width: 200px;
order: 1;
display: flex;
flex-flow: column nowrap;
align-items: stretch;
}
.jet-tabs__content-wrapper{
flex: 1 1 auto;
order: 2;
border-left-width: 2px;
align-self: stretch;
}
}
&-position-right {
flex-flow: row nowrap;
.jet-tabs__control-wrapper {
flex: 0 1 auto;
min-width: 100px;
width: 200px;
order: 2;
display: flex;
flex-flow: column nowrap;
align-items: stretch;
}
.jet-tabs__content-wrapper{
flex: 1 1 auto;
order: 1;
}
}
&-ajax-template {
.jet-tabs__content {
min-height: 30px;
}
}
@media (max-width: 1024px) {
&.jet-tabs-position-tablet-top {
flex-flow: column nowrap;
align-items: stretch;
.jet-tabs__control-wrapper {
width: auto;
min-width: inherit;
align-self: flex-start;
flex-flow: row wrap;
justify-content: flex-start;
align-items: center;
order: 1;
}
.jet-tabs__content-wrapper {
order: 2;
}
}
&.jet-tabs-position-tablet-bottom {
flex-flow: column nowrap;
align-items: stretch;
.jet-tabs__control-wrapper {
align-self: flex-start;
flex-flow: row wrap;
justify-content: flex-start;
align-items: center;
order: 2;
}
.jet-tabs__content-wrapper {
order: 1;
}
}
&.jet-tabs-position-tablet-left {
flex-flow: row nowrap;
.jet-tabs__control-wrapper {
flex: 0 1 auto;
min-width: 200px;
order: 1;
display: flex;
flex-flow: column nowrap;
align-items: stretch;
}
.jet-tabs__content-wrapper{
flex: 1 1 auto;
order: 2;
border-left-width: 2px;
align-self: stretch;
}
}
&.jet-tabs-position-tablet-right {
flex-flow: row nowrap;
.jet-tabs__control-wrapper {
flex: 0 1 auto;
min-width: 100px;
width: 200px;
order: 2;
display: flex;
flex-flow: column nowrap;
align-items: stretch;
}
.jet-tabs__content-wrapper{
flex: 1 1 auto;
order: 1;
}
}
}
@media (max-width: 767px) {
&.jet-tabs-position-mobile-top {
flex-flow: column nowrap;
align-items: stretch;
.jet-tabs__control-wrapper {
width: auto;
min-width: inherit;
align-self: flex-start;
flex-flow: row wrap;
justify-content: flex-start;
align-items: center;
order: 1;
}
.jet-tabs__content-wrapper {
order: 2;
}
}
&.jet-tabs-position-mobile-bottom {
flex-flow: column nowrap;
align-items: stretch;
.jet-tabs__control-wrapper {
align-self: flex-start;
flex-flow: row wrap;
justify-content: flex-start;
align-items: center;
order: 2;
}
.jet-tabs__content-wrapper {
order: 1;
}
}
&.jet-tabs-position-mobile-left {
flex-flow: row nowrap;
.jet-tabs__control-wrapper {
flex: 0 1 auto;
min-width: 200px;
order: 1;
display: flex;
flex-flow: column nowrap;
align-items: stretch;
}
.jet-tabs__content-wrapper{
flex: 1 1 auto;
order: 2;
align-self: stretch;
}
}
&.jet-tabs-position-mobile-right {
flex-flow: row nowrap;
.jet-tabs__control-wrapper {
flex: 0 1 auto;
min-width: 100px;
width: 200px;
order: 2;
display: flex;
flex-flow: column nowrap;
align-items: stretch;
}
.jet-tabs__content-wrapper{
flex: 1 1 auto;
order: 1;
}
}
}
&-fade-effect {
.jet-tabs__content {
&.active-content {
animation-name: fade;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
&-column-fade-effect {
.jet-tabs__content {
//display: none;
.elementor-top-column {
animation-name: fade;
animation-fill-mode: backwards;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
}
&.active-content {
//display: block;
.elementor-top-column {
@for $i from 1 through 4 {
&:nth-child(#{$i}) {
animation-delay: #{$i*100}ms;
}
}
}
}
}
}
&-zoom-in-effect {
.jet-tabs__content {
&.active-content {
animation-name: zoomIn;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
&-zoom-out-effect {
.jet-tabs__content {
&.active-content {
animation-name: zoomOut;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
&-move-up-effect {
.jet-tabs__content {
&.active-content {
animation-name: moveUp;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
&-column-move-up-effect {
.jet-tabs__content {
//display: none;
.elementor-top-column {
animation-name: moveUp;
animation-fill-mode: backwards;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
}
&.active-content {
//display: block;
.elementor-top-column {
@for $i from 1 through 4 {
&:nth-child(#{$i}) {
animation-delay: #{$i*100}ms;
}
}
}
}
}
}
&-fall-perspective-effect {
.jet-tabs__content {
&.active-content {
animation-name: fallPerspective;
animation-duration: 500ms;
animation-timing-function: cubic-bezier(.26,.69,.37,.96);
animation-play-state: running;
}
}
}
}
.jet-tabs__edit-cover {
display: flex;
justify-content: center;
align-items: center;
position: absolute;
box-sizing: border-box;
height: 30px;
padding: 5px 10px;
right: 15px;
top: 15px;
border-radius: 3px;
background-color: #b7084e;
z-index: 99;
cursor: pointer;
transition: opacity 0.3s ease;
box-shadow: 0 0 0 0 rgba( 183, 8, 78, 0.6);
animation: edit-button-pulse 5s infinite;
i {
font-size: 14px;
color: white;
margin-right: 5px;
}
span {
font-family: Roboto, Arial, Helvetica, Verdana, sans-serif;
font-size: 13px;
color: white;
}
&:hover {
background-color: #840739;
animation: none;
}
}
.jet-tabs-no-template-message {
text-align: center;
padding: 10px;
}
.jet-tabs-new-template-link {
color: #6ec1e4;
text-decoration: underline;
}

View File

@@ -0,0 +1,76 @@
#jet-tabs-settings-page {
visibility: hidden;
&.is-mounted {
visibility: visible;
}
}
.jet-tabs-settings-page {
margin: 25px 15px 0 15px;
.cx-vui-tabs-panel {
> .cx-vui-subtitle {
padding: 20px;
margin-top: 20px;
&:first-child {
margin-top: 0;
}
}
}
.jet-tabs-avaliable-widgets-control {
.cx-vui-checkgroup {
display: flex;
flex-flow: row wrap;
.cx-vui-checkbox-wrap {
width: 25%;
@media screen and (max-width: 1200px) {
width: 50%;
}
@media screen and (max-width: 782px) {
width: 100%;
}
}
}
}
&__avaliable-controls {
display: flex;
flex-flow: row wrap;
}
&__avaliable-control {
width: 33.3333%;
@media screen and (max-width: 1200px) {
width: 50%;
}
@media screen and (max-width: 782px) {
width: 100%;
}
.cx-vui-component {
padding: 10px 0;
}
}
&__disable-all-widgets {
display: flex;
justify-content: flex-start;
align-items: center;
border-bottom: 1px solid #ECECEC;
padding-bottom: 20px;
margin: 20px 0;
.cx-vui-component__label {
margin-right: 10px;
}
}
}

View File

@@ -0,0 +1,73 @@
@import "jet-tabs-icons";
#jet-tabs-template-edit-modal {
.dialog-widget-content {
width: 100%;
height: 90vh;
min-height: 700px;
background-color: #f1f3f5;
@media (min-width: 1440px) {
max-width: 90vw;
}
}
.dialog-close-button {
font-size: 25px;
}
.dialog-header {
display: none;
}
.dialog-message {
padding: 0;
height: 100%;
iframe {
height: 100%;
}
}
#jet-tabs-loading {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: #f1f3f5;
z-index: 9999;
transform: translateZ(0);
display: flex;
justify-content: center;
align-items: center;
.elementor-loader-wrapper {
top: auto;
left: auto;
transform: none;
}
}
}
#elementor-widget-template-empty-templates {
margin-top: 15px;
text-align: center;
.elementor-widget-template-empty-templates {
&-title {
padding: 25px 0 25px;
}
&-icon {
font-size: 96px;
color: #d5dadf;
}
&-footer {
font-style: italic;
margin-bottom: 15px;
}
}
}

View File

@@ -0,0 +1,27 @@
@import "utils/jet-tabs-effects";
@import "addons/jet-tabs";
@import "addons/jet-accordion";
@import "addons/jet-image-accordion";
@import "addons/jet-switcher";
.jet-tabs-loader {
position: absolute;
left: 50%;
top: 50%;
width: 24px;
height: 24px;
margin-top: -12px;
margin-left: -12px;
border: 4px rgba( #000,0.15 ) solid;
border-top-width: 4px;
border-top-style: solid;
border-top-color: #fff;
border-radius: 50%;
animation: spCircRot .6s infinite linear;
}
@keyframes spCircRot {
from { transform: rotate(0deg); }
to { transform: rotate(359deg); }
}

View File

@@ -0,0 +1,40 @@
[class*="jet-tabs-icon-"] {
display: block;
.elementor-panel &,
.elementor-sortable-helper & {
font-size: 38px;
margin-bottom: calc( 28px - 1em );
}
.elementor-navigator__item & {
font-size: 16px;
}
&:before {
content: '';
display: block;
width: 1em;
height: 1em;
margin: 0 auto;
background-position: center;
background-repeat: no-repeat;
background-size: contain;
}
}
.jet-tabs-icon-tabs:before {
background-image: url("data:image/svg+xml,%3Csvg width='64' height='40' viewBox='0 0 64 40' fill='none' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath d='M1 9H60C61.6569 9 63 10.3431 63 12V36C63 37.6569 61.6569 39 60 39H4C2.34315 39 1 37.6569 1 36V9Z' fill='white' stroke='%23162B40' stroke-width='2'/%3E%3Crect x='7' y='16' width='50' height='2' rx='1' fill='%23162B40'/%3E%3Crect x='7' y='20' width='50' height='2' rx='1' fill='%23162B40'/%3E%3Cpath d='M7 25C7 24.4477 7.44772 24 8 24H31C31.5523 24 32 24.4477 32 25C32 25.5523 31.5523 26 31 26H8C7.44772 26 7 25.5523 7 25Z' fill='%23162B40'/%3E%3Cpath d='M1 4C1 2.34315 2.34315 1 4 1H17V9H1V4Z' fill='%236F8BFF' stroke='%23162B40' stroke-width='2'/%3E%3Cpath d='M17 1H33V9H17V1Z' fill='white' stroke='%23162B40' stroke-width='2'/%3E%3Cpath d='M33 1H46C47.6569 1 49 2.34315 49 4V9H33V1Z' fill='white' stroke='%23162B40' stroke-width='2'/%3E%3C/svg%3E%0A");
}
.jet-tabs-icon-accordion:before {
background-image: url("data:image/svg+xml,%3Csvg width='64' height='42' viewBox='0 0 64 42' fill='none' xmlns='http://www.w3.org/2000/svg'%3E%3Crect x='1' y='1' width='62' height='10' rx='3' fill='%236F8BFF' stroke='%23162B40' stroke-width='2'/%3E%3Cpath d='M53 7L55 5L57 7' stroke='%23162B40' stroke-width='2' stroke-linecap='round'/%3E%3Crect x='1' y='31' width='62' height='10' rx='3' fill='white' stroke='%23162B40' stroke-width='2'/%3E%3Cpath d='M53 35L55 37L57 35' stroke='%23162B40' stroke-width='2' stroke-linecap='round'/%3E%3Crect x='2' y='16' width='60' height='2' rx='1' fill='%23162B40'/%3E%3Crect x='2' y='20' width='60' height='2' rx='1' fill='%23162B40'/%3E%3Cpath d='M2 25C2 24.4477 2.44772 24 3 24H31C31.5523 24 32 24.4477 32 25C32 25.5523 31.5523 26 31 26H3C2.44772 26 2 25.5523 2 25Z' fill='%23162B40'/%3E%3C/svg%3E%0A");
}
.jet-tabs-icon-switcher:before {
background-image: url("data:image/svg+xml,%3Csvg width='49' height='28' viewBox='0 0 49 28' fill='none' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath d='M1 14C1 6.8203 6.8203 1 14 1H35C42.1797 1 48 6.8203 48 14C48 21.1797 42.1797 27 35 27H14C6.8203 27 1 21.1797 1 14Z' fill='white' stroke='%23162B40' stroke-width='2'/%3E%3Cpath d='M22 14C22 18.4183 18.4183 22 14 22C9.58172 22 6 18.4183 6 14C6 9.58172 9.58172 6 14 6C18.4183 6 22 9.58172 22 14Z' fill='%234AF3BA' stroke='%23162B40' stroke-width='2'/%3E%3C/svg%3E%0A");
}
.jet-tabs-icon-image-accordion:before {
background-image: url("data:image/svg+xml,%3Csvg width='64' height='50' viewBox='0 0 64 50' fill='none' xmlns='http://www.w3.org/2000/svg'%3E%3Crect x='1' y='1' width='10' height='48' rx='3' fill='%234AF3BA' stroke='%23162B40' stroke-width='2'/%3E%3Cpath d='M5 7L7 9L5 11' stroke='%23162B40' stroke-width='2' stroke-linecap='round'/%3E%3Crect x='15' y='1' width='34' height='48' rx='3' fill='white' stroke='%23162B40' stroke-width='2'/%3E%3Cpath d='M24 33L27.5789 29.3636L31.1579 33L36.0789 28L41 33' stroke='%23162B40' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'/%3E%3Ccircle cx='31.5' cy='21.5' r='2.5' fill='white' stroke='%23162B40' stroke-width='2'/%3E%3Cpath d='M21 7L19 9L21 11' stroke='%23162B40' stroke-width='2' stroke-linecap='round'/%3E%3Crect x='53' y='1' width='10' height='48' rx='3' fill='%234AF3BA' stroke='%23162B40' stroke-width='2'/%3E%3Cpath d='M57 7L59 9L57 11' stroke='%23162B40' stroke-width='2' stroke-linecap='round'/%3E%3C/svg%3E%0A");
}

View File

@@ -0,0 +1,82 @@
@keyframes fade {
0% {
opacity: 0;
}
100% {
opacity: 1;
}
}
@keyframes zoomIn {
0% {
opacity: 0;
transform: scale(0.75);
}
100% {
opacity: 1;
transform: scale(1);
}
}
@keyframes zoomOut {
0% {
opacity: 0;
transform: scale(1.1);
}
100% {
opacity: 1;
transform: scale(1);
}
}
@keyframes moveUp {
0% {
opacity: 0;
transform: translateY(25px);
}
100% {
opacity: 1;
transform: translateY(0);
}
}
@keyframes columnMoveUp {
0% {
opacity: 0;
transform: translateY(25px);
}
100% {
opacity: 1;
transform: translateY(0);
}
}
@keyframes fallPerspective {
0% {
opacity: 0;
transform: perspective(1000px) translateY(50px) translateZ(-300px) rotateX(-35deg);
}
100% {
opacity: 1;
transform: perspective(1000px) translateY(0) translateZ(0) rotateX(0deg);
}
}
@keyframes edit-button-pulse {
0% {
box-shadow: 0 0 2px 0 rgba( 183, 8, 78, 0.6);
}
30% {
box-shadow: 0 0 2px 10px rgba( 183, 8, 78, 0);
}
100% {
box-shadow: 0 0 2px 0 rgba( 183, 8, 78, 0);
}
}

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@@ -0,0 +1,126 @@
'use strict';
let gulp = require('gulp'),
rename = require('gulp-rename'),
notify = require('gulp-notify'),
autoprefixer = require('gulp-autoprefixer'),
sass = require('gulp-sass'),
uglify = require('gulp-uglify-es').default,
plumber = require('gulp-plumber'),
checktextdomain = require('gulp-checktextdomain');
//frontend
gulp.task('jet-tabs-frontend', () => {
return gulp.src('./assets/scss/jet-tabs-frontend.scss')
.pipe(
plumber( {
errorHandler: function ( error ) {
console.log('=================ERROR=================');
console.log(error.message);
this.emit( 'end' );
}
})
)
.pipe(sass( { outputStyle: 'compressed' } ))
.pipe(autoprefixer({
browsers: ['last 10 versions'],
cascade: false
}))
.pipe(rename('jet-tabs-frontend.css'))
.pipe(gulp.dest('./assets/css/'))
.pipe(notify('Compile Sass Done!'));
});
gulp.task('jet-tabs-admin', () => {
return gulp.src('./assets/scss/jet-tabs-admin.scss')
.pipe(
plumber( {
errorHandler: function ( error ) {
console.log('=================ERROR=================');
console.log(error.message);
this.emit( 'end' );
}
})
)
.pipe(sass( { outputStyle: 'compressed' } ))
.pipe(autoprefixer({
browsers: ['last 10 versions'],
cascade: false
}))
.pipe(rename('jet-tabs-admin.css'))
.pipe(gulp.dest('./assets/css/'))
.pipe(notify('Compile Sass Done!'));
});
gulp.task('jet-tabs-editor', () => {
return gulp.src('./assets/scss/jet-tabs-editor.scss')
.pipe(
plumber( {
errorHandler: function ( error ) {
console.log('=================ERROR=================');
console.log(error.message);
this.emit( 'end' );
}
})
)
.pipe(sass( { outputStyle: 'compressed' } ))
.pipe(autoprefixer({
browsers: ['last 10 versions'],
cascade: false
}))
.pipe(rename('jet-tabs-editor.css'))
.pipe(gulp.dest('./assets/css/'))
.pipe(notify('Compile Sass Done!'));
});
gulp.task( 'js-editor-minify', () => {
return gulp.src( './assets/js/jet-tabs-editor.js' )
.pipe( uglify() )
.pipe( rename({ extname: '.min.js' }) )
.pipe( gulp.dest( './assets/js/') )
.pipe( notify('js Minify Done!') );
});
gulp.task( 'js-frontend-minify', () => {
return gulp.src( './assets/js/jet-tabs-frontend.js' )
.pipe( uglify() )
.pipe( rename({ extname: '.min.js' }) )
.pipe( gulp.dest( './assets/js/') )
.pipe( notify('js Minify Done!') );
});
//watch
gulp.task('watch', () => {
gulp.watch('./assets/scss/*.scss', gulp.series('jet-tabs-frontend') );
gulp.watch('./assets/scss/*.scss', gulp.series('jet-tabs-admin') );
gulp.watch('./assets/scss/*.scss', gulp.series('jet-tabs-editor') );
gulp.watch('./assets/js/jet-tabs-editor.js', gulp.series('js-editor-minify') );
gulp.watch('./assets/js/jet-tabs-frontend.js', gulp.series('js-frontend-minify') );
});
gulp.task( 'checktextdomain', () => {
return gulp.src( ['**/*.php', '!framework/**/*.php'] )
.pipe( checktextdomain( {
text_domain: 'jet-tabs',
keywords: [
'__:1,2d',
'_e:1,2d',
'_x:1,2c,3d',
'esc_html__:1,2d',
'esc_html_e:1,2d',
'esc_html_x:1,2c,3d',
'esc_attr__:1,2d',
'esc_attr_e:1,2d',
'esc_attr_x:1,2c,3d',
'_ex:1,2c,3d',
'_n:1,2,4d',
'_nx:1,2,4c,5d',
'_n_noop:1,2,3d',
'_nx_noop:1,2,3c,4d',
'translate_nooped_plural:1,2c,3d'
]
} ) );
} );

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,819 @@
<?php
/**
* Class: Jet_Switcher_Widget
* Name: Jet Switcher
* Slug: jet-switcher
*/
namespace Elementor;
use Elementor\Controls_Manager;
use Elementor\Group_Control_Border;
use Elementor\Group_Control_Box_Shadow;
use Elementor\Group_Control_Typography;
use Elementor\Repeater;
use Elementor\Scheme_Color;
use Elementor\Scheme_Typography;
use Elementor\Widget_Base;
if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly
class Jet_Switcher_Widget extends Jet_Tabs_Base {
public function get_name() {
return 'jet-switcher';
}
public function get_title() {
return esc_html__( 'Switcher', 'jet-tabs' );
}
public function get_help_url() {
return 'https://crocoblock.com/knowledge-base/articles/jettabs-switcher-widget-for-elementor-a-tool-to-switch-between-section-templates-within-one-block?utm_source=jettabs&utm_medium=jet-switcher&utm_campaign=need-help';
}
public function get_icon() {
return 'jet-tabs-icon-switcher';
}
public function get_categories() {
return array( 'cherry' );
}
protected function _register_controls() {
$css_scheme = apply_filters(
'jet-tabs/switcher/css-scheme',
array(
'instance' => '> .elementor-widget-container > .jet-switcher',
'control_wrapper' => '> .elementor-widget-container > .jet-switcher > .jet-switcher__control-wrapper',
'control' => '> .elementor-widget-container > .jet-switcher > .jet-switcher__control-wrapper > .jet-switcher__control-instance',
'disable_control' => '> .elementor-widget-container > .jet-switcher.jet-switcher--disable > .jet-switcher__control-wrapper',
'enable_control' => '> .elementor-widget-container > .jet-switcher.jet-switcher--enable > .jet-switcher__control-wrapper',
'content_wrapper' => '> .elementor-widget-container > .jet-switcher > .jet-switcher__content-wrapper',
'content' => '> .elementor-widget-container > .jet-switcher > .jet-switcher__content-wrapper > .jet-switcher__content',
)
);
$this->start_controls_section(
'section_items_data',
array(
'label' => esc_html__( 'Items', 'jet-tabs' ),
)
);
$templates = jet_tabs()->elementor()->templates_manager->get_source( 'local' )->get_items();
$options = [
'0' => '— ' . esc_html__( 'Select', 'jet-tabs' ) . ' —',
];
$types = [];
foreach ( $templates as $template ) {
$options[ $template['template_id'] ] = $template['title'] . ' (' . $template['type'] . ')';
$types[ $template['template_id'] ] = $template['type'];
}
$this->start_controls_tabs( 'swither_content_tabs' );
$this->start_controls_tab(
'swither_content_tabs_disable_state',
array(
'label' => esc_html__( 'Disable', 'jet-tabs' ),
)
);
$this->add_control(
'disable_label',
array(
'label' => esc_html__( 'Label', 'jet-tabs' ),
'type' => Controls_Manager::TEXT,
'default' => esc_html__( 'Disable', 'jet-tabs' ),
'dynamic' => [
'active' => true,
],
)
);
$this->add_control(
'disable_content_type',
[
'label' => esc_html__( 'Content Type', 'jet-tabs' ),
'type' => Controls_Manager::SELECT,
'default' => 'template',
'options' => [
'template' => esc_html__( 'Template', 'jet-tabs' ),
'editor' => esc_html__( 'Editor', 'jet-tabs' ),
],
'label_block' => 'true',
]
);
$this->add_control(
'disable_template_id',
array(
'label' => esc_html__( 'Template', 'jet-tabs' ),
'type' => Controls_Manager::SELECT,
'default' => '0',
'options' => $options,
'types' => $types,
'label_block' => 'true',
'condition' => [
'disable_content_type' => 'template',
]
)
);
$this->add_control(
'disable_item_editor_content',
[
'label' => __( 'Content', 'jet-tabs' ),
'type' => Controls_Manager::WYSIWYG,
'default' => __( 'Tab Item Content', 'jet-tabs' ),
'dynamic' => [
'active' => true,
],
'condition' => [
'disable_content_type' => 'editor',
]
]
);
$this->end_controls_tab();
$this->start_controls_tab(
'swither_content_tabs_enable_state',
array(
'label' => esc_html__( 'Enable', 'jet-tabs' ),
)
);
$this->add_control(
'enable_label',
array(
'label' => esc_html__( 'Label', 'jet-tabs' ),
'type' => Controls_Manager::TEXT,
'default' => esc_html__( 'Enable', 'jet-tabs' ),
'dynamic' => [
'active' => true,
],
)
);
$this->add_control(
'enable_content_type',
[
'label' => esc_html__( 'Content Type', 'jet-tabs' ),
'type' => Controls_Manager::SELECT,
'default' => 'template',
'options' => [
'template' => esc_html__( 'Template', 'jet-tabs' ),
'editor' => esc_html__( 'Editor', 'jet-tabs' ),
],
'label_block' => 'true',
]
);
$this->add_control(
'enable_template_id',
array(
'label' => esc_html__( 'Template', 'jet-tabs' ),
'type' => Controls_Manager::SELECT,
'default' => '0',
'options' => $options,
'types' => $types,
'label_block' => 'true',
'condition' => [
'enable_content_type' => 'template',
]
)
);
$this->add_control(
'enable_item_editor_content',
[
'label' => __( 'Content', 'jet-tabs' ),
'type' => Controls_Manager::WYSIWYG,
'default' => __( 'Tab Item Content', 'jet-tabs' ),
'dynamic' => [
'active' => true,
],
'condition' => [
'enable_content_type' => 'editor',
]
]
);
$this->end_controls_tab();
$this->end_controls_tabs();
$this->end_controls_section();
$this->start_controls_section(
'section_settings_data',
array(
'label' => esc_html__( 'Settings', 'jet-tabs' ),
)
);
$this->add_control(
'initial_state',
array(
'label' => esc_html__( 'Initial State', 'jet-tabs' ),
'type' => Controls_Manager::SWITCHER,
'label_on' => esc_html__( 'Enable', 'jet-tabs' ),
'label_off' => esc_html__( 'Disable', 'jet-tabs' ),
'return_value' => 'yes',
'default' => 'false',
)
);
$this->add_control(
'switcher_preset',
array(
'label' => esc_html__( 'Switcher Preset', 'jet-tabs' ),
'type' => Controls_Manager::SELECT,
'default' => 'preset-1',
'options' => array(
'preset-1' => esc_html__( 'Preset-1', 'jet-tabs' ),
'preset-2' => esc_html__( 'Preset-2', 'jet-tabs' ),
),
)
);
$this->add_control(
'show_effect',
array(
'label' => esc_html__( 'Show Effect', 'jet-tabs' ),
'type' => Controls_Manager::SELECT,
'default' => 'move-up',
'options' => array(
'none' => esc_html__( 'None', 'jet-tabs' ),
'fade' => esc_html__( 'Fade', 'jet-tabs' ),
'zoom-in' => esc_html__( 'Zoom In', 'jet-tabs' ),
'zoom-out' => esc_html__( 'Zoom Out', 'jet-tabs' ),
'move-up' => esc_html__( 'Move Up', 'jet-tabs' ),
'fall-perspective' => esc_html__( 'Fall Perspective', 'jet-tabs' ),
),
)
);
$this->end_controls_section();
$this->__start_controls_section(
'section_swither_control_style',
array(
'label' => esc_html__( 'Switcher Control', 'jet-tabs' ),
'tab' => Controls_Manager::TAB_STYLE,
'show_label' => false,
)
);
$this->__add_responsive_control(
'swither_control_width',
array(
'label' => esc_html__( 'Width', 'jet-tabs' ),
'type' => Controls_Manager::NUMBER,
'default' => 180,
'min' => 20,
'max' => 300,
'step' => 1,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['control'] => 'width: {{VALUE}}px',
),
),
25
);
$this->__add_responsive_control(
'swither_control_height',
array(
'label' => esc_html__( 'Height', 'jet-tabs' ),
'type' => Controls_Manager::NUMBER,
'default' => 60,
'min' => 10,
'max' => 100,
'step' => 1,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['control'] => 'height: {{VALUE}}px',
),
),
25
);
$this->__add_responsive_control(
'swither_handler_width',
array(
'label' => esc_html__( 'Handler Width', 'jet-tabs' ),
'type' => Controls_Manager::NUMBER,
'default' => 60,
'min' => 1,
'max' => 300,
'step' => 1,
'condition' => array(
'switcher_preset' => 'preset-2',
),
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['control'] . ' .jet-switcher__control-handler' => 'width: {{VALUE}}px',
'{{WRAPPER}} ' . $css_scheme['enable_control'] . ' .jet-switcher__control-handler' => 'left: calc(100% - {{VALUE}}px)',
),
)
);
$this->__add_responsive_control(
'swither_container_margin',
array(
'label' => __( 'Margin', 'jet-tabs' ),
'type' => Controls_Manager::DIMENSIONS,
'size_units' => array( 'px', '%' ),
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['control_wrapper'] => 'margin: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}};',
),
),
75
);
$this->__add_group_control(
Group_Control_Border::get_type(),
array(
'name' => 'swither_container_border',
'label' => esc_html__( 'Border', 'jet-tabs' ),
'placeholder' => '1px',
'default' => '1px',
'selector' => '{{WRAPPER}} ' . $css_scheme['control'],
),
50
);
$this->__add_responsive_control(
'swither_container_border_radius',
array(
'label' => __( 'Border Radius', 'jet-tabs' ),
'type' => Controls_Manager::DIMENSIONS,
'size_units' => array( 'px', '%' ),
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['control'] => 'border-radius: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}};',
),
),
75
);
$this->__add_group_control(
Group_Control_Box_Shadow::get_type(),
array(
'name' => 'swither_container_box_shadow',
'selector' => '{{WRAPPER}} ' . $css_scheme['control'],
),
100
);
$this->__add_control(
'handler_style_heading',
array(
'label' => esc_html__( 'Handler', 'jet-tabs' ),
'type' => Controls_Manager::HEADING,
'separator' => 'before',
),
75
);
$this->__add_responsive_control(
'swither_handler_offset',
array(
'label' => esc_html__( 'Handler Offset', 'jet-tabs' ),
'type' => Controls_Manager::NUMBER,
'default' => 3,
'min' => 0,
'max' => 20,
'step' => 1,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['control'] . ' .jet-switcher__control-handler span' => 'margin: {{VALUE}}px',
),
),
75
);
$this->__add_control(
'labels_style_heading',
array(
'label' => esc_html__( 'Typography', 'jet-tabs' ),
'type' => Controls_Manager::HEADING,
'separator' => 'before',
),
50
);
$this->__add_group_control(
Group_Control_Typography::get_type(),
array(
'label' => esc_html__( 'Labels', 'jet-tabs' ),
'name' => 'swither_control_labels_typography',
'selector' => '{{WRAPPER}} '. $css_scheme['control_wrapper'] . ' .jet-switcher__label-text',
),
50
);
$this->__add_control(
'control_state_style_heading',
array(
'label' => esc_html__( 'States', 'jet-tabs' ),
'type' => Controls_Manager::HEADING,
'separator' => 'before',
)
);
$this->__start_controls_tabs( 'swither_control_styles_tabs' );
$this->__start_controls_tab(
'swither_control_styles_disable_tab',
array(
'label' => esc_html__( 'Disable', 'jet-tabs' ),
)
);
$this->__add_control(
'control_disable_background_color',
array(
'label' => esc_html__( 'Control Color', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['disable_control'] . ' .jet-switcher__control-instance' => 'background-color: {{VALUE}}',
),
),
25
);
$this->__add_control(
'control_handler_disable_background_color',
array(
'label' => esc_html__( 'Handler Color', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['disable_control'] . ' .jet-switcher__control-handler span' => 'background-color: {{VALUE}}',
),
),
25
);
$this->__add_control(
'control_disable_state_disable_label_color',
array(
'label' => esc_html__( 'Disable Label Color', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['disable_control'] . ' .jet-switcher__control--disable' => 'color: {{VALUE}}',
),
),
25
);
$this->__add_control(
'control_disable_state_enable_label_color',
array(
'label' => esc_html__( 'Enable Label Color', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['disable_control'] . ' .jet-switcher__control--enable' => 'color: {{VALUE}}',
),
),
25
);
$this->__end_controls_tab();
$this->__start_controls_tab(
'swither_control_styles_enable_tab',
array(
'label' => esc_html__( 'Enable', 'jet-tabs' ),
)
);
$this->__add_control(
'control_enable_background_color',
array(
'label' => esc_html__( 'Control Color', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['enable_control'] . ' .jet-switcher__control-instance' => 'background-color: {{VALUE}}',
),
),
25
);
$this->__add_control(
'control_handler_enable_background_color',
array(
'label' => esc_html__( 'Handler Color', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['enable_control'] . ' .jet-switcher__control-handler span' => 'background-color: {{VALUE}}',
),
),
25
);
$this->__add_control(
'control_enable_state_disable_label_color',
array(
'label' => esc_html__( 'Disable Label Color', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['enable_control'] . ' .jet-switcher__control--disable' => 'color: {{VALUE}}',
),
),
25
);
$this->__add_control(
'control_enable_state_enable_label_color',
array(
'label' => esc_html__( 'Enable Label Color', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['enable_control'] . ' .jet-switcher__control--enable' => 'color: {{VALUE}}',
),
),
25
);
$this->__end_controls_tab();
$this->__end_controls_tabs();
$this->__end_controls_section();
/**
* Swither Content Style Section
*/
$this->__start_controls_section(
'section_swither_content_style',
array(
'label' => esc_html__( 'Switcher Content', 'jet-tabs' ),
'tab' => Controls_Manager::TAB_STYLE,
'show_label' => false,
)
);
$this->__add_group_control(
Group_Control_Typography::get_type(),
array(
'name' => 'tabs_content_typography',
'selector' => '{{WRAPPER}} ' . $css_scheme['content'],
),
50
);
$this->__add_control(
'tabs_content_text_color',
array(
'label' => esc_html__( 'Text color', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['content'] => 'color: {{VALUE}};',
),
),
25
);
$this->__add_group_control(
Group_Control_Background::get_type(),
array(
'name' => 'swither_content_background',
'selector' => '{{WRAPPER}} ' . $css_scheme['content_wrapper'],
),
25
);
$this->__add_responsive_control(
'swither_content_padding',
array(
'label' => __( 'Padding', 'jet-tabs' ),
'type' => Controls_Manager::DIMENSIONS,
'size_units' => array( 'px', '%' ),
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['content'] => 'padding: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}};',
),
),
50
);
$this->__add_group_control(
Group_Control_Border::get_type(),
array(
'name' => 'swither_content_border',
'label' => esc_html__( 'Border', 'jet-tabs' ),
'placeholder' => '1px',
'default' => '1px',
'selector' => '{{WRAPPER}} ' . $css_scheme['content_wrapper'],
),
50
);
$this->__add_responsive_control(
'swither_content_radius',
array(
'label' => __( 'Border Radius', 'jet-tabs' ),
'type' => Controls_Manager::DIMENSIONS,
'size_units' => array( 'px', '%' ),
'selectors' => array(
'{{WRAPPER}} ' . $css_scheme['content_wrapper'] => 'border-radius: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}};',
),
),
75
);
$this->__add_group_control(
Group_Control_Box_Shadow::get_type(),
array(
'name' => 'tabs_content_box_shadow',
'selector' => '{{WRAPPER}} ' . $css_scheme['content_wrapper'],
),
100
);
$this->__end_controls_section();
}
/**
* [render description]
* @return [type] [description]
*/
protected function render() {
$this->__context = 'render';
$widget_settings = $this->get_settings_for_display();
$show_effect = $widget_settings[ 'show_effect' ];
$switcher_preset = $widget_settings[ 'switcher_preset' ];
$initial_state = filter_var( $widget_settings[ 'initial_state' ], FILTER_VALIDATE_BOOLEAN );
$settings = array(
'effect' => $widget_settings[ 'show_effect' ],
);
$this->add_render_attribute( 'instance', array(
'class' => array(
'jet-switcher',
'jet-switcher--' . $switcher_preset,
'jet-switcher-' . $show_effect . '-effect',
$initial_state ? 'jet-switcher--enable' : 'jet-switcher--disable',
),
'data-settings' => json_encode( $settings ),
) );
?><div <?php echo $this->get_render_attribute_string( 'instance' ); ?>>
<div class="jet-switcher__control-wrapper"><?php
include jet_tabs()->get_template( $this->get_name() . '/global/' . $switcher_preset . '.php' );
?></div>
<div class="jet-switcher__content-wrapper"><?php
$this->add_render_attribute( 'jet_switcher_content_disable', array(
'id' => 'jet-switcher-content-disable-' . $this->get_id(),
'class' => array(
'jet-switcher__content',
'jet-switcher__content--disable',
! $initial_state ? 'active-content' : '',
),
'aria-hidden' => ! $initial_state ? 'false' : 'true',
) );
switch ( $widget_settings['disable_content_type'] ) {
case 'template':
$disable_content_html = $this->get_template_content_by_id( $widget_settings['disable_template_id'] );
break;
case 'editor':
$disable_content_html = $this->parse_text_editor( $widget_settings['disable_item_editor_content'] );
break;
}
echo sprintf( '<div %1$s>%2$s</div>', $this->get_render_attribute_string( 'jet_switcher_content_disable' ), $disable_content_html );
$this->add_render_attribute( 'jet_switcher_content_enable', array(
'id' => 'jet-switcher-content-enable-' . $this->get_id(),
'class' => array(
'jet-switcher__content',
'jet-switcher__content--enable',
$initial_state ? 'active-content' : '',
),
'aria-hidden' => $initial_state ? 'false' : 'true',
) );
switch ( $widget_settings['enable_content_type'] ) {
case 'template':
$enable_content_html = $this->get_template_content_by_id( $widget_settings['enable_template_id'] );
break;
case 'editor':
$enable_content_html = $this->parse_text_editor( $widget_settings['enable_item_editor_content'] );
break;
}
echo sprintf( '<div %1$s>%2$s</div>', $this->get_render_attribute_string( 'jet_switcher_content_enable' ), $enable_content_html );?></div>
</div>
<?php
}
/**
* [get_template_content_by_id description]
* @param [type] $template_id [description]
* @return [type] [description]
*/
public function get_template_content_by_id( $template_id ) {
if ( '0' !== $template_id ) {
$content_html = '';
// for multi-language plugins
$template_id = apply_filters( 'jet-tabs/widgets/template_id', $template_id, $this );
$template_content = jet_tabs()->elementor()->frontend->get_builder_content_for_display( $template_id );
if ( ! empty( $template_content ) ) {
$content_html .= $template_content;
if ( jet_tabs_integration()->is_edit_mode() ) {
$link = add_query_arg(
array(
'elementor' => '',
),
get_permalink( $template_id )
);
$content_html .= sprintf( '<div class="jet-switcher__edit-cover" data-template-edit-link="%s"><i class="fa fa-pencil"></i><span>%s</span></div>', $link, esc_html__( 'Edit Template', 'jet-tabs' ) );
}
} else {
$content_html = $this->no_template_content_message();
}
} else {
$content_html = $this->no_templates_message();
}
return $content_html;
}
/**
* [empty_templates_message description]
* @return [type] [description]
*/
public function empty_templates_message() {
return '<div id="elementor-widget-template-empty-templates">
<div class="elementor-widget-template-empty-templates-icon"><i class="eicon-nerd"></i></div>
<div class="elementor-widget-template-empty-templates-title">' . esc_html__( 'You Havent Saved Templates Yet.', 'jet-tabs' ) . '</div>
<div class="elementor-widget-template-empty-templates-footer">' . esc_html__( 'What is Library?', 'jet-tabs' ) . ' <a class="elementor-widget-template-empty-templates-footer-url" href="https://go.elementor.com/docs-library/" target="_blank">' . esc_html__( 'Read our tutorial on using Library templates.', 'jet-tabs' ) . '</a></div>
</div>';
}
/**
* [no_templates_message description]
* @return [type] [description]
*/
public function no_templates_message() {
$message = '<span>' . esc_html__( 'Template is not defined. ', 'jet-tabs' ) . '</span>';
$link = add_query_arg(
array(
'post_type' => 'elementor_library',
'action' => 'elementor_new_post',
'_wpnonce' => wp_create_nonce( 'elementor_action_new_post' ),
'template_type' => 'section',
),
esc_url( admin_url( '/edit.php' ) )
);
$new_link = '<span>' . esc_html__( 'Select an existing template or create a ', 'jet-tabs' ) . '</span><a class="jet-switcher-new-template-link elementor-clickable" target="_blank" href="' . $link . '">' . esc_html__( 'new one', 'jet-tabs' ) . '</a>' ;
return sprintf(
'<div class="jet-switcher-no-template-message">%1$s%2$s</div>',
$message,
jet_tabs_integration()->in_elementor() ? $new_link : ''
);
}
/**
* [no_template_content_message description]
* @return [type] [description]
*/
public function no_template_content_message() {
$message = '<span>' . esc_html__( 'The switcher are working. Please, note, that you have to add a template to the library in order to be able to display it inside the switcher.', 'jet-tabs' ) . '</span>';
return sprintf( '<div class="jet-toogle-no-template-message">%1$s</div>', $message );
}
/**
* [get_template_edit_link description]
* @param [type] $template_id [description]
* @return [type] [description]
*/
public function get_template_edit_link( $template_id ) {
$link = add_query_arg( 'elementor', '', get_permalink( $template_id ) );
return '<a target="_blank" class="elementor-edit-template elementor-clickable" href="' . $link .'"><i class="fa fa-pencil"></i> ' . esc_html__( 'Edit Template', 'jet-tabs' ) . '</a>';
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,160 @@
<?php
/**
* Class description
*
* @package package_name
* @author Cherry Team
* @license GPL-2.0+
*/
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
if ( ! class_exists( 'Jet_Tabs_Assets' ) ) {
/**
* Define Jet_Tabs_Assets class
*/
class Jet_Tabs_Assets {
/**
* A reference to an instance of this class.
*
* @since 1.0.0
* @var object
*/
private static $instance = null;
/**
* Constructor for the class
*/
public function init() {
add_action( 'elementor/editor/after_enqueue_styles', array( $this, 'editor_styles' ) );
add_action( 'elementor/editor/before_enqueue_scripts', array( $this, 'editor_scripts' ) );
add_action( 'elementor/frontend/after_enqueue_styles', array( $this, 'enqueue_styles' ) );
add_action( 'elementor/frontend/before_enqueue_scripts', array( $this, 'enqueue_scripts' ) );
}
/**
* Enqueue public-facing stylesheets.
*
* @since 1.0.0
* @access public
* @return void
*/
public function enqueue_styles() {
wp_enqueue_style(
'jet-tabs-frontend',
jet_tabs()->plugin_url( 'assets/css/jet-tabs-frontend.css' ),
false,
jet_tabs()->get_version()
);
}
/**
* Enqueue plugin scripts only with elementor scripts
*
* @return void
*/
public function enqueue_scripts() {
$suffix = defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ? '' : '.min';
wp_enqueue_script(
'jet-tabs-frontend',
jet_tabs()->plugin_url( 'assets/js/jet-tabs-frontend' . $suffix . '.js' ),
array( 'jquery', 'elementor-frontend' ),
jet_tabs()->get_version(),
true
);
$rest_api_url = apply_filters( 'jet-tabs/rest/url', get_rest_url() );
wp_localize_script( 'jet-tabs-frontend', 'JetTabsSettings', array(
'ajaxurl' => esc_url( admin_url( 'admin-ajax.php' ) ),
'isMobile' => filter_var( wp_is_mobile(), FILTER_VALIDATE_BOOLEAN ) ? 'true' : 'false',
'templateApiUrl' => $rest_api_url . 'jet-tabs-api/v1/elementor-template',
'devMode' => is_user_logged_in() ? 'true' : 'false',
) );
}
/**
* Enqueue elemnetor editor-related styles
*
* @return void
*/
public function editor_styles() {
wp_enqueue_style(
'jet-tabs-editor',
jet_tabs()->plugin_url( 'assets/css/jet-tabs-editor.css' ),
array(),
jet_tabs()->get_version()
);
}
/**
* Enqueue elemnetor editor scripts
*
* @return void
*/
public function editor_scripts() {
$suffix = defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ? '' : '.min';
wp_enqueue_script(
'jet-tabs-editor',
jet_tabs()->plugin_url( 'assets/js/jet-tabs-editor' . $suffix . '.js' ),
array( 'jquery', 'underscore', 'backbone-marionette' ),
jet_tabs()->get_version(),
true
);
}
/**
* Prints editor templates
*
* @return void
*/
public function print_templates() {
/*foreach ( glob( jet_theme_core()->plugin_path( 'templates/editor/*.php' ) ) as $file ) {
$name = basename( $file, '.php' );
ob_start();
include $file;
printf( '<script type="text/html" id="tmpl-jet-%1$s">%2$s</script>', $name, ob_get_clean() );
}*/
}
/**
* Returns the instance.
*
* @since 1.0.0
* @return object
*/
public static function get_instance() {
// If the single instance hasn't been set, set it now.
if ( null == self::$instance ) {
self::$instance = new self;
}
return self::$instance;
}
}
}
/**
* Returns instance of Jet_Tabs_Registration
*
* @return object
*/
function jet_tabs_assets() {
return Jet_Tabs_Assets::get_instance();
}

View File

@@ -0,0 +1,578 @@
<?php
namespace Elementor;
if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly
abstract class Jet_Tabs_Base extends Widget_Base {
public $__context = 'render';
public $__processed_item = false;
public $__processed_index = 0;
public $__query = array();
public $__load_level = 100;
public $__include_controls = [];
public $__exclude_controls = [];
/**
* [__construct description]
* @param array $data [description]
* @param [type] $args [description]
*/
public function __construct( $data = [], $args = null ) {
parent::__construct( $data, $args );
$this->__load_level = (int)jet_tabs_settings()->get( 'widgets_load_level', 100 );
$widget_name = $this->get_name();
$this->__include_controls = apply_filters( "jet-tabs/editor/{$widget_name}/include-controls", [], $widget_name, $this );
$this->__exclude_controls = apply_filters( "jet-tabs/editor/{$widget_name}/exclude-controls", [], $widget_name, $this );
}
/**
* Get globaly affected template
*
* @param [type] $name [description]
* @return [type] [description]
*/
public function __get_global_template( $name = null ) {
$template = call_user_func( array( $this, sprintf( '__get_%s_template', $this->__context ) ) );
if ( ! $template ) {
$template = jet_tabs()->get_template( $this->get_name() . '/global/' . $name . '.php' );
}
return $template;
}
/**
* Get front-end template
* @param [type] $name [description]
* @return [type] [description]
*/
public function __get_render_template( $name = null ) {
return jet_tabs()->get_template( $this->get_name() . '/render/' . $name . '.php' );
}
/**
* Get editor template
* @param [type] $name [description]
* @return [type] [description]
*/
public function __get_edit_template( $name = null ) {
return jet_tabs()->get_template( $this->get_name() . '/edit/' . $name . '.php' );
}
/**
* Get global looped template for settings
* Required only to process repeater settings.
*
* @param string $name Base template name.
* @param string $setting Repeater setting that provide data for template.
* @return void
*/
public function __get_global_looped_template( $name = null, $setting = null ) {
$templates = array(
'start' => $this->__get_global_template( $name . '-loop-start' ),
'loop' => $this->__get_global_template( $name . '-loop-item' ),
'end' => $this->__get_global_template( $name . '-loop-end' ),
);
call_user_func(
array( $this, sprintf( '__get_%s_looped_template', $this->__context ) ), $templates, $setting
);
}
/**
* Get render mode looped template
*
* @param array $templates [description]
* @param [type] $setting [description]
* @return [type] [description]
*/
public function __get_render_looped_template( $templates = array(), $setting = null ) {
$loop = $this->get_settings_for_display( $setting );
if ( empty( $loop ) ) {
return;
}
if ( ! empty( $templates['start'] ) ) {
include $templates['start'];
}
foreach ( $loop as $item ) {
$this->__processed_item = $item;
if ( ! empty( $templates['start'] ) ) {
include $templates['loop'];
}
$this->__processed_index++;
}
$this->__processed_item = false;
$this->__processed_index = 0;
if ( ! empty( $templates['end'] ) ) {
include $templates['end'];
}
}
/**
* Get edit mode looped template
*
* @param array $templates [description]
* @param [type] $setting [description]
* @return [type] [description]
*/
public function __get_edit_looped_template( $templates = array(), $setting = null ) {
?>
<# if ( settings.<?php echo $setting; ?> ) { #>
<?php
if ( ! empty( $templates['start'] ) ) {
include $templates['start'];
}
?>
<# _.each( settings.<?php echo $setting; ?>, function( item ) { #>
<?php
if ( ! empty( $templates['loop'] ) ) {
include $templates['loop'];
}
?>
<# } ); #>
<?php
if ( ! empty( $templates['end'] ) ) {
include $templates['end'];
}
?>
<# } #>
<?php
}
/**
* Get current looped item dependends from context.
*
* @param string $key Key to get from processed item
* @return mixed
*/
public function __loop_item( $keys = array(), $format = '%s' ) {
return call_user_func( array( $this, sprintf( '__%s_loop_item', $this->__context ) ), $keys, $format );
}
/**
* Loop edit item
*
* @param [type] $keys [description]
* @param string $format [description]
* @param boolean $nested_key [description]
* @return [type] [description]
*/
public function __edit_loop_item( $keys = array(), $format = '%s' ) {
$settings = $keys[0];
if ( isset( $keys[1] ) ) {
$settings .= '.' . $keys[1];
}
ob_start();
echo '<# if ( item.' . $settings . ' ) { #>';
printf( $format, '{{{ item.' . $settings . ' }}}' );
echo '<# } #>';
return ob_get_clean();
}
/**
* Loop render item
*
* @param string $format [description]
* @param [type] $key [description]
* @param boolean $nested_key [description]
* @return [type] [description]
*/
public function __render_loop_item( $keys = array(), $format = '%s' ) {
$item = $this->__processed_item;
$key = $keys[0];
$nested_key = isset( $keys[1] ) ? $keys[1] : false;
if ( empty( $item ) || ! isset( $item[ $key ] ) ) {
return false;
}
if ( false === $nested_key || ! is_array( $item[ $key ] ) ) {
$value = $item[ $key ];
} else {
$value = isset( $item[ $key ][ $nested_key ] ) ? $item[ $key ][ $nested_key ] : false;
}
if ( ! empty( $value ) ) {
return sprintf( $format, $value );
}
}
/**
* Include global template if any of passed settings is defined
*
* @param [type] $name [description]
* @param [type] $settings [description]
* @return [type] [description]
*/
public function __glob_inc_if( $name = null, $settings = array() ) {
$template = $this->__get_global_template( $name );
call_user_func( array( $this, sprintf( '__%s_inc_if', $this->__context ) ), $template, $settings );
}
/**
* Include render template if any of passed setting is not empty
*
* @param [type] $file [description]
* @param [type] $settings [description]
* @return [type] [description]
*/
public function __render_inc_if( $file = null, $settings = array() ) {
foreach ( $settings as $setting ) {
$val = $this->get_settings_for_display( $setting );
if ( ! empty( $val ) ) {
include $file;
return;
}
}
}
/**
* Include render template if any of passed setting is not empty
*
* @param [type] $file [description]
* @param [type] $settings [description]
* @return [type] [description]
*/
public function __edit_inc_if( $file = null, $settings = array() ) {
$condition = null;
$sep = null;
foreach ( $settings as $setting ) {
$condition .= $sep . 'settings.' . $setting;
$sep = ' || ';
}
?>
<# if ( <?php echo $condition; ?> ) { #>
<?php include $file; ?>
<# } #>
<?php
}
/**
* Open standard wrapper
*
* @return void
*/
public function __open_wrap() {
printf( '<div class="elementor-%s jet-tabs-addons">', $this->get_name() );
}
/**
* Close standard wrapper
*
* @return void
*/
public function __close_wrap() {
echo '</div>';
}
/**
* Print HTML markup if passed setting not empty.
*
* @param string $setting Passed setting.
* @param string $format Required markup.
* @param array $args Additional variables to pass into format string.
* @param bool $echo Echo or return.
* @return string|void
*/
public function __html( $setting = null, $format = '%s' ) {
call_user_func( array( $this, sprintf( '__%s_html', $this->__context ) ), $setting, $format );
}
/**
* Returns HTML markup if passed setting not empty.
*
* @param string $setting Passed setting.
* @param string $format Required markup.
* @param array $args Additional variables to pass into format string.
* @param bool $echo Echo or return.
* @return string|void
*/
public function __get_html( $setting = null, $format = '%s' ) {
ob_start();
$this->__html( $setting, $format );
return ob_get_clean();
}
/**
* Print HTML template
*
* @param [type] $setting [description]
* @param [type] $format [description]
* @return [type] [description]
*/
public function __render_html( $setting = null, $format = '%s' ) {
if ( is_array( $setting ) ) {
$key = $setting[1];
$setting = $setting[0];
}
$val = $this->get_settings_for_display( $setting );
if ( ! is_array( $val ) && '0' === $val ) {
printf( $format, $val );
}
if ( is_array( $val ) && empty( $val[ $key ] ) ) {
return '';
}
if ( ! is_array( $val ) && empty( $val ) ) {
return '';
}
if ( is_array( $val ) ) {
printf( $format, $val[ $key ] );
} else {
printf( $format, $val );
}
}
/**
* Print underscore template
*
* @param [type] $setting [description]
* @param [type] $format [description]
* @return [type] [description]
*/
public function __edit_html( $setting = null, $format = '%s' ) {
if ( is_array( $setting ) ) {
$setting = $setting[0] . '.' . $setting[1];
}
echo '<# if ( settings.' . $setting . ' ) { #>';
printf( $format, '{{{ settings.' . $setting . ' }}}' );
echo '<# } #>';
}
/**
* Set posts query results
*/
public function __set_query( $posts ) {
$this->__query = $posts;
}
/**
* Return posts query results
*/
public function __get_query() {
return $this->__query;
}
/**
* [__add_control description]
* @param boolean $control_id [description]
* @param array $control_args [description]
* @param integer $load_level [description]
* @return [type] [description]
*/
public function __add_control( $control_id = false, $control_args = [], $load_level = 100 ) {
if (
( $this->__load_level < $load_level
|| 0 === $this->__load_level
|| in_array( $control_id, $this->__exclude_controls )
) && !in_array( $control_id, $this->__include_controls )
) {
return false;
}
if ( function_exists( 'jet_styles_manager' ) && jet_styles_manager()->compatibility ) {
$control_args = jet_styles_manager()->compatibility->set_control_args(
$control_args,
$load_level,
'jet-tabs'
);
}
$this->add_control( $control_id, $control_args );
}
/**
* [__add_responsive_control description]
* @param boolean $control_id [description]
* @param array $control_args [description]
* @param integer $load_level [description]
* @return [type] [description]
*/
public function __add_responsive_control( $control_id = false, $control_args = [], $load_level = 100 ) {
if (
( $this->__load_level < $load_level
|| 0 === $this->__load_level
|| in_array( $control_id, $this->__exclude_controls )
) && !in_array( $control_id, $this->__include_controls )
) {
return false;
}
if ( function_exists( 'jet_styles_manager' ) && jet_styles_manager()->compatibility ) {
$control_args = jet_styles_manager()->compatibility->set_control_args(
$control_args,
$load_level,
'jet-tabs'
);
}
$this->add_responsive_control( $control_id, $control_args );
}
/**
* [__add_group_control description]
* @param boolean $group_control_type [description]
* @param array $group_control_args [description]
* @param integer $load_level [description]
* @return [type] [description]
*/
public function __add_group_control( $group_control_type = false, $group_control_args = [], $load_level = 100 ) {
if (
( $this->__load_level < $load_level
|| 0 === $this->__load_level
|| in_array( $group_control_args['name'], $this->__exclude_controls )
) && !in_array( $group_control_args['name'], $this->__include_controls )
) {
return false;
}
if ( function_exists( 'jet_styles_manager' ) && jet_styles_manager()->compatibility ) {
$group_control_args = jet_styles_manager()->compatibility->set_group_control_args(
$group_control_type,
$group_control_args,
$load_level,
'jet-tabs'
);
}
$this->add_group_control( $group_control_type, $group_control_args );
}
/**
* [__start_controls_section description]
* @param boolean $controls_section_id [description]
* @param array $controls_section_args [description]
* @param integer $load_level [description]
* @return [type] [description]
*/
public function __start_controls_section( $controls_section_id = false, $controls_section_args = [], $load_level = 25 ) {
if ( ! $controls_section_id || $this->__load_level < $load_level || 0 === $this->__load_level ) {
return false;
}
$this->start_controls_section( $controls_section_id, $controls_section_args );
}
/**
* [__end_controls_section description]
* @param integer $load_level [description]
* @return [type] [description]
*/
public function __end_controls_section( $load_level = 25 ) {
if ( $this->__load_level < $load_level || 0 === $this->__load_level ) {
return false;
}
$this->end_controls_section();
}
/**
* [__start_controls_tabs description]
* @param boolean $tabs_id [description]
* @param integer $load_level [description]
* @return [type] [description]
*/
public function __start_controls_tabs( $tabs_id = false, $load_level = 25 ) {
if ( ! $tabs_id || $this->__load_level < $load_level || 0 === $this->__load_level ) {
return false;
}
$this->start_controls_tabs( $tabs_id );
}
/**
* [__end_controls_tabs description]
* @param integer $load_level [description]
* @return [type] [description]
*/
public function __end_controls_tabs( $load_level = 25 ) {
if ( $this->__load_level < $load_level || 0 === $this->__load_level ) {
return false;
}
$this->end_controls_tabs();
}
/**
* [__start_controls_tab description]
* @param boolean $tab_id [description]
* @param array $tab_args [description]
* @param integer $load_level [description]
* @return [type] [description]
*/
public function __start_controls_tab( $tab_id = false, $tab_args = [], $load_level = 25 ) {
if ( ! $tab_id || $this->__load_level < $load_level || 0 === $this->__load_level ) {
return false;
}
$this->start_controls_tab( $tab_id, $tab_args );
}
/**
* [__end_controls_tab description]
* @param integer $load_level [description]
* @return [type] [description]
*/
public function __end_controls_tab( $load_level = 25 ) {
if ( $this->__load_level < $load_level || 0 === $this->__load_level ) {
return false;
}
$this->end_controls_tab();
}
}

View File

@@ -0,0 +1,178 @@
<?php
/**
* Jet_Tabs_Compatibility class
*/
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
if ( ! class_exists( 'Jet_Tabs_Compatibility' ) ) {
/**
* Define Jet_Tabs_Compatibility class
*/
class Jet_Tabs_Compatibility {
/**
* A reference to an instance of this class.
*
* @since 1.0.0
* @var Jet_Tabs_Compatibility
*/
private static $instance = null;
/**
* Constructor for the class
*/
public function init() {
// WPML Compatibility
if ( defined( 'WPML_ST_VERSION' ) ) {
if ( class_exists( 'WPML_Elementor_Module_With_Items' ) ) {
$this->load_wpml_modules();
}
add_filter( 'wpml_elementor_widgets_to_translate', array( $this, 'add_wpml_translatable_nodes' ) );
add_filter( 'jet-tabs/widgets/template_id', array( $this, 'set_wpml_translated_template_id' ) );
}
// Polylang compatibility
if ( class_exists( 'Polylang' ) ) {
add_filter( 'jet-tabs/widgets/template_id', array( $this, 'set_pll_translated_template_id' ) );
}
}
/**
* Load wpml required files.
*
* @return void
*/
public function load_wpml_modules() {
require jet_tabs()->plugin_path( 'includes/compatibility/wpml-modules/jet-wpml-accordion.php' );
require jet_tabs()->plugin_path( 'includes/compatibility/wpml-modules/jet-wpml-image-accordion.php' );
require jet_tabs()->plugin_path( 'includes/compatibility/wpml-modules/jet-wpml-tabs.php' );
}
/**
* Add wpml translation nodes
*
* @param array $nodes_to_translate
*
* @return array
*/
public function add_wpml_translatable_nodes( $nodes_to_translate ) {
$nodes_to_translate['jet-accordion'] = array(
'conditions' => array( 'widgetType' => 'jet-accordion' ),
'integration-class' => 'Jet_Tabs_WPML_Accordion',
);
$nodes_to_translate['jet-image-accordion'] = array(
'conditions' => array( 'widgetType' => 'jet-image-accordion' ),
'integration-class' => 'Jet_Tabs_WPML_Image_Accordion',
);
$nodes_to_translate['jet-switcher'] = array(
'conditions' => array( 'widgetType' => 'jet-switcher' ),
'fields' => array(
array(
'field' => 'disable_label',
'type' => esc_html__( 'Jet Switcher: Disable Label', 'jet-tabs' ),
'editor_type' => 'LINE',
),
array(
'field' => 'disable_item_editor_content',
'type' => esc_html__( 'Jet Switcher: Disable Editor Content', 'jet-tabs' ),
'editor_type' => 'VISUAL',
),
array(
'field' => 'enable_label',
'type' => esc_html__( 'Jet Switcher: Enable Label', 'jet-tabs' ),
'editor_type' => 'LINE',
),
array(
'field' => 'enable_item_editor_content',
'type' => esc_html__( 'Jet Switcher: Enable Editor Content', 'jet-tabs' ),
'editor_type' => 'VISUAL',
),
),
);
$nodes_to_translate['jet-tabs'] = array(
'conditions' => array( 'widgetType' => 'jet-tabs' ),
'integration-class' => 'Jet_Tabs_WPML_Tabs',
);
return $nodes_to_translate;
}
/**
* Set WPML translated template.
*
* @param $template_id
*
* @return mixed|void
*/
public function set_wpml_translated_template_id( $template_id ) {
$post_type = get_post_type( $template_id );
return apply_filters( 'wpml_object_id', $template_id, $post_type, true );
}
/**
* Set Polylang translated template.
*
* @param $template_id
*
* @return false|int|null
*/
public function set_pll_translated_template_id( $template_id ) {
if ( function_exists( 'pll_get_post' ) ) {
$translation_template_id = pll_get_post( $template_id );
if ( null === $translation_template_id ) {
// the current language is not defined yet
return $template_id;
} elseif ( false === $translation_template_id ) {
//no translation yet
return $template_id;
} elseif ( $translation_template_id > 0 ) {
// return translated post id
return $translation_template_id;
}
}
return $template_id;
}
/**
* Returns the instance.
*
* @since 1.0.0
* @return Jet_Tabs_Compatibility
*/
public static function get_instance() {
// If the single instance hasn't been set, set it now.
if ( null == self::$instance ) {
self::$instance = new self;
}
return self::$instance;
}
}
}
/**
* Returns instance of Jet_Tabs_Compatibility
*
* @return Jet_Tabs_Compatibility
*/
function jet_tabs_compatibility() {
return Jet_Tabs_Compatibility::get_instance();
}

View File

@@ -0,0 +1,41 @@
<?php
/**
* Class Jet_Tabs_WPML_Accordion
*/
class Jet_Tabs_WPML_Accordion extends WPML_Elementor_Module_With_Items {
public function get_items_field() {
return 'toggles';
}
public function get_fields() {
return array( 'item_label', 'item_editor_content' );
}
protected function get_title( $field ) {
switch( $field ) {
case 'item_label':
return esc_html__( 'Jet Accordion: Item Label', 'jet-tabs' );
case 'item_editor_content':
return esc_html__( 'Jet Accordion: Item Editor Content', 'jet-tabs' );
default:
return '';
}
}
protected function get_editor_type( $field ) {
switch( $field ) {
case 'item_label':
return 'LINE';
case 'item_editor_content':
return 'VISUAL';
default:
return '';
}
}
}

View File

@@ -0,0 +1,53 @@
<?php
/**
* Class Jet_Tabs_WPML_Image_Accordion
*/
class Jet_Tabs_WPML_Image_Accordion extends WPML_Elementor_Module_With_Items {
public function get_items_field() {
return 'item_list';
}
public function get_fields() {
return array( 'item_title', 'item_desc', 'item_link_text', 'item_link' );
}
protected function get_title( $field ) {
switch( $field ) {
case 'item_title':
return esc_html__( 'Jet Image Accordion: Item Label', 'jet-tabs' );
case 'item_desc':
return esc_html__( 'Jet Image Accordion: Item Description', 'jet-tabs' );
case 'item_link_text':
return esc_html__( 'Jet Image Accordion: Item Button text', 'jet-tabs' );
case 'item_link':
return esc_html__( 'Jet Image Accordion: Item Link', 'jet-tabs' );
default:
return '';
}
}
protected function get_editor_type( $field ) {
switch( $field ) {
case 'item_title':
return 'LINE';
case 'item_desc':
return 'AREA';
case 'item_link_text':
return 'LINE';
case 'item_link':
return 'LINK';
default:
return '';
}
}
}

View File

@@ -0,0 +1,41 @@
<?php
/**
* Class Jet_Tabs_WPML_Tabs
*/
class Jet_Tabs_WPML_Tabs extends WPML_Elementor_Module_With_Items {
public function get_items_field() {
return 'tabs';
}
public function get_fields() {
return array( 'item_label', 'item_editor_content' );
}
protected function get_title( $field ) {
switch( $field ) {
case 'item_label':
return esc_html__( 'Jet Tabs: Item Label', 'jet-tabs' );
case 'item_editor_content':
return esc_html__( 'Jet Tabs: Item Editor Content', 'jet-tabs' );
default:
return '';
}
}
protected function get_editor_type( $field ) {
switch( $field ) {
case 'item_label':
return 'LINE';
case 'item_editor_content':
return 'VISUAL';
default:
return '';
}
}
}

View File

@@ -0,0 +1,309 @@
<?php
use Elementor\Controls_Manager;
use Elementor\Group_Control_Border;
use Elementor\Group_Control_Box_Shadow;
use Elementor\Group_Control_Typography;
use Elementor\Repeater;
use Elementor\Scheme_Color;
use Elementor\Scheme_Typography;
use Elementor\Widget_Base;
if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly
class Jet_Tabs_Group_Control_Box_Style extends Elementor\Group_Control_Base {
protected static $fields;
public static function get_type() {
return 'jet-tabs-box-style';
}
protected function init_fields() {
$fields = [];
$fields['box_font_color'] = array(
'label' => esc_html__( 'Color', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'selectors' => array(
'{{SELECTOR}}' => 'color: {{VALUE}}',
),
);
$fields['background'] = array(
'label' => _x( 'Background Type', 'Background Control', 'jet-tabs' ),
'type' => Controls_Manager::CHOOSE,
'options' => array(
'color' => array(
'title' => _x( 'Classic', 'Background Control', 'jet-tabs' ),
'icon' => 'fa fa-paint-brush',
),
'gradient' => array(
'title' => _x( 'Gradient', 'Background Control', 'jet-tabs' ),
'icon' => 'fa fa-barcode',
),
),
'label_block' => false,
'render_type' => 'ui',
);
$fields['color'] = array(
'label' => _x( 'Color', 'Background Control', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'default' => '',
'title' => _x( 'Background Color', 'Background Control', 'jet-tabs' ),
'selectors' => array(
'{{SELECTOR}}' => 'background-color: {{VALUE}};',
),
'condition' => array(
'background' => array( 'color', 'gradient' ),
),
);
$fields['color_stop'] = array(
'label' => _x( 'Location', 'Background Control', 'jet-tabs' ),
'type' => Controls_Manager::SLIDER,
'size_units' => array( '%' ),
'default' => array(
'unit' => '%',
'size' => 0,
),
'render_type' => 'ui',
'condition' => array(
'background' => array( 'gradient' ),
),
'of_type' => 'gradient',
);
$fields['color_b'] = array(
'label' => _x( 'Second Color', 'Background Control', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'default' => '#f2295b',
'render_type' => 'ui',
'condition' => array(
'background' => array( 'gradient' ),
),
'of_type' => 'gradient',
);
$fields['color_b_stop'] = array(
'label' => _x( 'Location', 'Background Control', 'jet-tabs' ),
'type' => Controls_Manager::SLIDER,
'size_units' => array( '%' ),
'default' => array(
'unit' => '%',
'size' => 100,
),
'render_type' => 'ui',
'condition' => array(
'background' => array( 'gradient' ),
),
'of_type' => 'gradient',
);
$fields['gradient_type'] = array(
'label' => _x( 'Type', 'Background Control', 'jet-tabs' ),
'type' => Controls_Manager::SELECT,
'options' => array(
'linear' => _x( 'Linear', 'Background Control', 'jet-tabs' ),
'radial' => _x( 'Radial', 'Background Control', 'jet-tabs' ),
),
'default' => 'linear',
'render_type' => 'ui',
'condition' => array(
'background' => array( 'gradient' ),
),
'of_type' => 'gradient',
);
$fields['gradient_angle'] = array(
'label' => _x( 'Angle', 'Background Control', 'jet-tabs' ),
'type' => Controls_Manager::SLIDER,
'size_units' => array( 'deg' ),
'default' => array(
'unit' => 'deg',
'size' => 180,
),
'range' => array(
'deg' => array(
'step' => 10,
),
),
'selectors' => array(
'{{SELECTOR}}' => 'background-color: transparent; background-image: linear-gradient({{SIZE}}{{UNIT}}, {{color.VALUE}} {{color_stop.SIZE}}{{color_stop.UNIT}}, {{color_b.VALUE}} {{color_b_stop.SIZE}}{{color_b_stop.UNIT}})',
),
'condition' => array(
'background' => array( 'gradient' ),
'gradient_type' => 'linear',
),
'of_type' => 'gradient',
);
$fields['gradient_position'] = array(
'label' => _x( 'Position', 'Background Control', 'jet-tabs' ),
'type' => Controls_Manager::SELECT,
'options' => array(
'center center' => _x( 'Center Center', 'Background Control', 'jet-tabs' ),
'center left' => _x( 'Center Left', 'Background Control', 'jet-tabs' ),
'center right' => _x( 'Center Right', 'Background Control', 'jet-tabs' ),
'top center' => _x( 'Top Center', 'Background Control', 'jet-tabs' ),
'top left' => _x( 'Top Left', 'Background Control', 'jet-tabs' ),
'top right' => _x( 'Top Right', 'Background Control', 'jet-tabs' ),
'bottom center' => _x( 'Bottom Center', 'Background Control', 'jet-tabs' ),
'bottom left' => _x( 'Bottom Left', 'Background Control', 'jet-tabs' ),
'bottom right' => _x( 'Bottom Right', 'Background Control', 'jet-tabs' ),
),
'default' => 'center center',
'selectors' => array(
'{{SELECTOR}}' => 'background-color: transparent; background-image: radial-gradient(at {{VALUE}}, {{color.VALUE}} {{color_stop.SIZE}}{{color_stop.UNIT}}, {{color_b.VALUE}} {{color_b_stop.SIZE}}{{color_b_stop.UNIT}})',
),
'condition' => array(
'background' => array( 'gradient' ),
'gradient_type' => 'radial',
),
'of_type' => 'gradient',
);
$fields['box_font_size'] = array(
'label' => esc_html__( 'Icon Size', 'jet-tabs' ),
'type' => Controls_Manager::SLIDER,
'size_units' => array(
'px', 'em', 'rem',
),
'responsive' => true,
'range' => array(
'px' => array(
'min' => 5,
'max' => 500,
),
),
'selectors' => array(
'{{SELECTOR}}:before' => 'font-size: {{SIZE}}{{UNIT}}',
'{{SELECTOR}}' => 'font-size: {{SIZE}}{{UNIT}}',
),
);
$fields['box_size'] = array(
'label' => esc_html__( 'Box Size', 'jet-tabs' ),
'type' => Controls_Manager::SLIDER,
'size_units' => array(
'px', 'em', '%',
),
'range' => array(
'px' => array(
'min' => 5,
'max' => 500,
),
),
'responsive' => true,
'selectors' => array(
'{{SELECTOR}}' => 'width: {{SIZE}}{{UNIT}}; height: {{SIZE}}{{UNIT}};',
),
);
$fields['box_border'] = array(
'label' => _x( 'Border Type', 'Border Control', 'jet-tabs' ),
'type' => Controls_Manager::SELECT,
'options' => array(
'' => __( 'None', 'jet-tabs' ),
'solid' => _x( 'Solid', 'Border Control', 'jet-tabs' ),
'double' => _x( 'Double', 'Border Control', 'jet-tabs' ),
'dotted' => _x( 'Dotted', 'Border Control', 'jet-tabs' ),
'dashed' => _x( 'Dashed', 'Border Control', 'jet-tabs' ),
),
'selectors' => array(
'{{SELECTOR}}' => 'border-style: {{VALUE}};',
),
);
$fields['box_border_width'] = array(
'label' => _x( 'Width', 'Border Control', 'jet-tabs' ),
'type' => Controls_Manager::DIMENSIONS,
'selectors' => array(
'{{SELECTOR}}' => 'border-width: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}};',
),
'condition' => array(
'box_border!' => '',
),
);
$fields['box_border_color'] = array(
'label' => _x( 'Color', 'Border Control', 'jet-tabs' ),
'type' => Controls_Manager::COLOR,
'default' => '',
'selectors' => array(
'{{SELECTOR}}' => 'border-color: {{VALUE}};',
),
'condition' => array(
'box_border!' => '',
),
);
$fields['box_border_radius'] = array(
'label' => esc_html__( 'Border Radius', 'jet-tabs' ),
'type' => Controls_Manager::DIMENSIONS,
'size_units' => array( 'px', '%' ),
'selectors' => array(
'{{SELECTOR}}' => 'border-radius: {{TOP}}{{UNIT}} {{RIGHT}}{{UNIT}} {{BOTTOM}}{{UNIT}} {{LEFT}}{{UNIT}};',
),
);
$fields['allow_box_shadow'] = array(
'label' => _x( 'Box Shadow', 'Box Shadow Control', 'jet-tabs' ),
'type' => Controls_Manager::SWITCHER,
'label_on' => esc_html__( 'Yes', 'jet-tabs' ),
'label_off' => esc_html__( 'No', 'jet-tabs' ),
'return_value' => 'yes',
'separator' => 'before',
'render_type' => 'ui',
);
$fields['box_shadow'] = array(
'label' => _x( 'Box Shadow', 'Box Shadow Control', 'jet-tabs' ),
'type' => Controls_Manager::BOX_SHADOW,
'condition' => array(
'allow_box_shadow!' => '',
),
'selectors' => array(
'{{SELECTOR}}' => 'box-shadow: {{HORIZONTAL}}px {{VERTICAL}}px {{BLUR}}px {{SPREAD}}px {{COLOR}} {{box_shadow_position.VALUE}};',
),
);
$fields['box_shadow_position'] = array(
'label' => _x( 'Position', 'Box Shadow Control', 'jet-tabs' ),
'type' => Controls_Manager::SELECT,
'options' => array(
' ' => _x( 'Outline', 'Box Shadow Control', 'jet-tabs' ),
'inset' => _x( 'Inset', 'Box Shadow Control', 'jet-tabs' ),
),
'condition' => array(
'allow_box_shadow!' => '',
),
'default' => ' ',
'render_type' => 'ui',
);
return $fields;
}
protected function prepare_fields( $fields ) {
array_walk( $fields, function ( &$field, $field_name ) {
if ( in_array( $field_name, array( 'popover_toggle' ) ) ) {
return;
}
$condition = array(
'popover_toggle!' => '',
);
if( isset( $field['condition'] ) ) {
$field['condition'] = array_merge( $field['condition'], $condition );
} else {
$field['condition'] = $condition;
}
} );
return parent::prepare_fields( $fields );
}
}

View File

@@ -0,0 +1,83 @@
<?php
/**
* DB upgrader class
*/
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
if ( ! class_exists( 'Jet_Tabs_DB_Upgrader' ) ) {
/**
* Define Jet_Tabs_DB_Upgrader class
*/
class Jet_Tabs_DB_Upgrader {
/**
* Setting key
*
* @var string
*/
public $key = null;
/**
* Constructor for the class
*/
public function __construct() {
/**
* Plugin initialized on new Jet_Tabs_DB_Upgrader call.
* Please ensure, that it called only on admin context
*/
$this->init_upgrader();
}
/**
* Initialize upgrader module
*
* @return void
*/
public function init_upgrader() {
$db_updater_data = jet_tabs()->module_loader->get_included_module_data( 'cx-db-updater.php' );
new CX_DB_Updater(
array(
'path' => $db_updater_data['path'],
'url' => $db_updater_data['url'],
'slug' => 'jet-tabs',
'version' => jet_tabs()->get_version(),
'callbacks' => array(
'1.1.8' => array(
array( $this, 'update_db_1_1_8' ),
),
),
'labels' => array(
'start_update' => esc_html__( 'Start Update', 'jet-tabs' ),
'data_update' => esc_html__( 'Data Update', 'jet-tabs' ),
'messages' => array(
'error' => esc_html__( 'Module DB Updater init error in %s - version and slug is required arguments', 'jet-tabs' ),
'update' => esc_html__( 'We need to update your database to the latest version.', 'jet-tabs' ),
'updated' => esc_html__( 'Update complete, thank you for updating to the latest version!', 'jet-tabs' ),
),
),
)
);
}
/**
* Update db updater 1.1.8
*
* @return void
*/
public function update_db_1_1_8() {
if ( class_exists( 'Elementor\Plugin' ) ) {
jet_tabs()->elementor()->files_manager->clear_cache();
}
}
}
}

View File

@@ -0,0 +1,312 @@
<?php
/**
* Class description
*
* @package package_name
* @author Cherry Team
* @license GPL-2.0+
*/
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
use Elementor\Utils;
if ( ! class_exists( 'Jet_Tabs_Integration' ) ) {
/**
* Define Jet_Tabs_Integration class
*/
class Jet_Tabs_Integration {
/**
* A reference to an instance of this class.
*
* @since 1.0.0
* @var object
*/
private static $instance = null;
/**
* Check if processing elementor widget
*
* @var boolean
*/
private $is_elementor_ajax = false;
/**
* Initalize integration hooks
*
* @return void
*/
public function init() {
add_action( 'elementor/init', array( $this, 'register_category' ) );
add_action( 'elementor/widgets/widgets_registered', array( $this, 'register_addons' ), 10 );
add_action( 'elementor/controls/controls_registered', array( $this, 'add_controls' ), 10 );
add_action( 'wp_ajax_elementor_render_widget', array( $this, 'set_elementor_ajax' ), 10, -1 );
add_action( 'template_include', array( $this, 'set_post_type_template' ), 9999 );
add_filter( 'elementor/editor/localize_settings', array( $this, 'elementor_editor_localize_settings' ), 10, 2 );
}
/**
* Set $this->is_elementor_ajax to true on Elementor AJAX processing
*
* @return void
*/
public function set_elementor_ajax() {
$this->is_elementor_ajax = true;
}
/**
* Check if we currently in Elementor mode
*
* @return void
*/
public function in_elementor() {
$result = false;
if ( wp_doing_ajax() ) {
$result = $this->is_elementor_ajax;
} elseif ( Elementor\Plugin::instance()->editor->is_edit_mode()
|| Elementor\Plugin::instance()->preview->is_preview_mode() ) {
$result = true;
}
/**
* Allow to filter result before return
*
* @var bool $result
*/
return apply_filters( 'jet-tabs/in-elementor', $result );
}
/**
* Check if we currently in Elementor editor mode
*
* @return void
*/
public function is_edit_mode() {
$result = false;
if ( Elementor\Plugin::instance()->editor->is_edit_mode() ) {
$result = true;
}
/**
* Allow to filter result before return
*
* @var bool $result
*/
return apply_filters( 'jet-tabs/is-edit-mode', $result );
}
/**
* Add new controls.
*
* @param object $controls_manager Controls manager instance.
* @return void
*/
public function add_controls( $controls_manager ) {
$grouped = array(
'jet-tabs-box-style' => 'Jet_Tabs_Group_Control_Box_Style',
);
foreach ( $grouped as $control_id => $class_name ) {
if ( $this->include_control( $class_name, true ) ) {
$controls_manager->add_group_control( $control_id, new $class_name() );
}
}
}
/**
* Include control file by class name.
*
* @param [type] $class_name [description]
* @return [type] [description]
*/
public function include_control( $class_name, $grouped = false ) {
$filename = sprintf(
'includes/controls/%2$sclass-%1$s.php',
str_replace( '_', '-', strtolower( $class_name ) ),
( true === $grouped ? 'groups/' : '' )
);
if ( ! file_exists( jet_tabs()->plugin_path( $filename ) ) ) {
return false;
}
require jet_tabs()->plugin_path( $filename );
return true;
}
/**
* Register plugin addons
*
* @param object $widgets_manager Elementor widgets manager instance.
* @return void
*/
public function register_addons( $widgets_manager ) {
$avaliable_widgets = jet_tabs_settings()->get( 'avaliable_widgets' );
require jet_tabs()->plugin_path( 'includes/base/class-jet-tabs-base.php' );
foreach ( glob( jet_tabs()->plugin_path( 'includes/addons/' ) . '*.php' ) as $file ) {
$slug = basename( $file, '.php' );
$enabled = isset( $avaliable_widgets[ $slug ] ) ? $avaliable_widgets[ $slug ] : '';
if ( filter_var( $enabled, FILTER_VALIDATE_BOOLEAN ) || ! $avaliable_widgets ) {
$this->register_addon( $file, $widgets_manager );
}
}
}
/**
* Rewrite core controls.
*
* @param object $controls_manager Controls manager instance.
* @return void
*/
public function rewrite_controls( $controls_manager ) {
$controls = array(
$controls_manager::ICON => 'Jet_Tabs_Control_Icon',
);
foreach ( $controls as $control_id => $class_name ) {
if ( $this->include_control( $class_name ) ) {
$controls_manager->unregister_control( $control_id );
$controls_manager->register_control( $control_id, new $class_name() );
}
}
}
/**
* Register addon by file name
*
* @param string $file File name.
* @param object $widgets_manager Widgets manager instance.
* @return void
*/
public function register_addon( $file, $widgets_manager ) {
$base = basename( str_replace( '.php', '', $file ) );
$class = ucwords( str_replace( '-', ' ', $base ) );
$class = str_replace( ' ', '_', $class );
$class = sprintf( 'Elementor\%s', $class );
require $file;
if ( class_exists( $class ) ) {
$widgets_manager->register_widget_type( new $class );
}
}
/**
* Register cherry category for elementor if not exists
*
* @return void
*/
public function register_category() {
$elements_manager = Elementor\Plugin::instance()->elements_manager;
$cherry_cat = 'cherry';
$elements_manager->add_category(
$cherry_cat,
array(
'title' => esc_html__( 'JetElements', 'jet-tabs' ),
'icon' => 'font',
),
1
);
}
/**
* Set blank template for editor
*/
public function set_post_type_template( $template ) {
if ( ! isset( $_REQUEST['jet-tabs-canvas'] ) ) {
return $template;
}
$found = false;
if ( is_singular( 'elementor_library' ) ) {
$found = true;
$template = jet_tabs()->plugin_path( 'templates/blank.php' );
}
if ( $found ) {
do_action( 'jet-tabs/template-include/found' );
}
return $template;
}
/**
* Elementor editor localize settings
*
* @param array $settings
* @param int $id post id
*
* @return array
*/
public function elementor_editor_localize_settings( $settings, $id ) { // todo: check if need
if ( version_compare( ELEMENTOR_VERSION, '2.0.0', '<' ) ) {
$preview_url = Utils::get_preview_url( $id );
} else {
$preview_url = Elementor\Plugin::$instance->documents->get( $id )->get_preview_url();
}
return array(
'preview_link' => $preview_url . '&jet-tabs-canvas',
);
}
/**
* Returns the instance.
*
* @since 1.0.0
* @return object
*/
public static function get_instance( $shortcodes = array() ) {
// If the single instance hasn't been set, set it now.
if ( null == self::$instance ) {
self::$instance = new self( $shortcodes );
}
return self::$instance;
}
}
}
/**
* Returns instance of Jet_Tabs_Integration
*
* @return object
*/
function jet_tabs_integration() {
return Jet_Tabs_Integration::get_instance();
}

View File

@@ -0,0 +1,357 @@
<?php
/**
* DB Updater module
*
* Version: 1.0.0
*/
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
if ( ! class_exists( 'CX_DB_Updater' ) ) {
/**
* Class CX_DB_Updater.
*
* @since 1.0.0
*/
class CX_DB_Updater {
/**
* Module arguments.
*
* @since 1.0.0
* @var array
*/
private $args = array(
'path' => '',
'url' => '',
'callbacks' => array(),
'slug' => null,
'version' => null,
'labels' => array(
'start_update' => 'Start Update',
'data_update' => 'Data Update',
'messages' => array(
'error' => 'Module DB Updater init error in %s - version and slug is required arguments',
'update' => 'We need to update your database to the latest version.',
'updated' => 'Update complete, thank you for updating to the latest version!',
),
),
);
/**
* Option key for DB version.
*
* @since 1.0.0
* @var string
*/
protected $version_key = '%s-db-version';
/**
* Nonce format.
*
* @since 1.0.0
* @var string
*/
protected $nonce = '_%s-db-update-nonce';
/**
* Messages array.
*
* @since 1.0.0
* @var array
*/
protected $messages = array();
/**
* Update done trigger.
*
* @since 1.0.0
* @var bool
*/
protected $updated = false;
/**
* Cherry_Db_Updater constructor.
*
* @since 1.0.0
* @param array $args Module arguments.
* @return void
*/
public function __construct( $args = array() ) {
$this->args = wp_parse_args( $args, $this->args );
if ( ! is_admin() || ! current_user_can( 'update_plugins' ) ) {
return;
}
add_action( 'admin_notices', array( $this, 'init_notices' ) );
add_action( 'admin_init', array( $this, 'do_update' ) );
$this->messages = $this->args['labels']['messages'];
}
/**
* Process DB update.
*
* @since 1.0.0
*/
public function do_update() {
if ( ! $this->is_current_update() ) {
return;
}
$callbacks = $this->prepare_callbacks();
if ( ! empty( $callbacks ) ) {
foreach ( $callbacks as $callback ) {
if ( is_callable( $callback ) ) {
call_user_func( $callback );
}
}
}
$this->set_updated();
}
/**
* Finalize update.
*
* @since 1.0.0
*/
public function set_updated() {
$this->updated = true;
$option = sprintf( $this->version_key, esc_attr( $this->args['slug'] ) );
update_option( $option, esc_attr( $this->args['version'] ) );
}
/**
* Prepare callbacks array.
*
* @since 1.0.0
* @return array
*/
private function prepare_callbacks() {
$callbacks = array();
if ( empty( $this->args['callbacks'] ) ) {
return $callbacks;
}
ksort( $this->args['callbacks'] );
foreach ( $this->args['callbacks'] as $ver => $ver_cb ) {
if ( version_compare( $this->get_current_version(), $ver, '<' ) ) {
$callbacks = array_merge( $callbacks, $ver_cb );
}
}
return $callbacks;
}
/**
* Check if we processed update for plugin passed in arguments.
*
* @since 1.0.0
* @return bool
*/
private function is_current_update() {
if ( empty( $_GET['cherry_x_db_update'] ) || empty( $_GET['slug'] ) || empty( $_GET['_nonce'] ) ) {
return false;
}
if ( $_GET['slug'] !== $this->args['slug'] ) {
return false;
}
$nonce_action = sprintf( $this->nonce, esc_attr( $this->args['slug'] ) );
if ( ! wp_verify_nonce( $_GET['_nonce'], $nonce_action ) ) {
return false;
}
return true;
}
/**
* Init admin notices.
*
* @since 1.0.0
* @return void
*/
public function init_notices() {
$enabled = $this->validate_module_args();
if ( ! $enabled ) {
return;
}
$slug = esc_attr( $this->args['slug'] );
if ( $this->is_update_required() ) {
$this->show_notice( $slug );
}
if ( $this->is_updated() ) {
$this->show_updated_notice();
}
}
/**
* Returns current DB version.
*
* @since 1.0.0
* @return string
*/
private function get_current_version() {
$option = sprintf( $this->version_key, esc_attr( $this->args['slug'] ) );
return get_option( $option, '1.0.0' );
}
/**
* Check if database requires update.
*
* @since 1.0.0
* @return bool
*/
private function is_update_required() {
$current = $this->get_current_version();
return version_compare( $current, esc_attr( $this->args['version'] ), '<' );
}
/**
* Check if update was successfully done.
*
* @since 1.0.0
* @return bool
*/
private function is_updated() {
if ( ! $this->is_current_update() ) {
return false;
}
return (bool) $this->updated;
}
/**
* Validate module arguments.
*
* @since 1.0.0
* @return bool
*/
private function validate_module_args() {
if ( empty( $this->args['slug'] ) || empty( $this->args['version'] ) ) {
echo '<div class="error"><p>';
printf(
$this->messages['error'],
'<b>' . str_replace( untrailingslashit( ABSPATH ), '', $this->args['path'] ) . '</b>'
);
echo '</p></div>';
return false;
}
return true;
}
/**
* Show notice.
*
* @since 1.0.0
* @param string $slug Plugin slug.
* @return void
*/
private function show_notice( $slug ) {
echo '<div class="notice notice-info">';
echo '<p>';
$this->notice_title( $slug );
echo $this->messages['update'];
echo '</p>';
echo '<p>';
$this->notice_submit( $slug );
echo '</p>';
echo '</div>';
}
/**
* Show update notice.
*
* @since 1.0.0
* @return void
*/
private function show_updated_notice() {
$slug = esc_attr( $this->args['slug'] );
echo '<div class="notice notice-success is-dismissible">';
echo '<p>';
$this->notice_title( $slug );
echo $this->messages['updated'];
echo '</p>';
echo '</div>';
}
/**
* Show plugin notice submit button.
*
* @since 1.0.0
* @param string $slug Plugin slug.
* @return void
*/
private function notice_submit( $slug = '' ) {
$format = '<a href="%1s" class="button button-primary">%2$s</a>';
$label = $this->args['labels']['start_update'];
$url = add_query_arg(
array(
'cherry_x_db_update' => true,
'slug' => $slug,
'_nonce' => $this->create_nonce( $slug ),
),
esc_url( admin_url( 'index.php' ) )
);
printf( $format, $url, $label );
}
/**
* Create DB update nonce.
*
* @since 1.0.0
* @param string $slug Plugin slug.
* @return string
*/
private function create_nonce( $slug ) {
return wp_create_nonce( sprintf( $this->nonce, $slug ) );
}
/**
* Show plugin notice title.
*
* @since 1.0.0
* @param string $slug Plugin slug.
* @return void
*/
private function notice_title( $slug ) {
$name = str_replace( '-', ' ', $slug );
$name = ucwords( $name );
printf( '<strong>%1$s %2$s</strong> &#8211; ', $name, $this->args['labels']['data_update'] );
}
}
}

File diff suppressed because one or more lines are too long

View File

@@ -0,0 +1,406 @@
var eventBus = new Vue();
( function( $, dashboardPageConfig ) {
'use strict';
Vue.config.devtools = true;
if ( ! $('#jet-dashboard-page')[0] ) {
return false;
}
/**
* [template description]
* @type {String}
*/
Vue.component( 'license-item', {
template: '#jet-dashboard-license-item',
props: {
licenseData: Object,
type: String
},
data: function() {
return {
licenseKey: this.licenseData.licenseKey,
licenseStatus: this.licenseData.licenseStatus,
licenseDetails: this.licenseData.licenseDetails,
activationStatus: false,
ajaxLicenseAction: null,
}
},
computed: {
isLicenseActive: function() {
return 'active' === this.licenseStatus ? true : false;
},
licenseActionType: function() {
return ! this.isLicenseActive ? 'activate' : 'deactivate';
},
maskedLicenseKey: function() {
let licenseKey = this.licenseKey,
licenseKeyArray = licenseKey.split(''),
maskerLicenseArray = [];
maskerLicenseArray = licenseKeyArray.map( ( item, index ) => {
if ( index > 4 && index < licenseKeyArray.length - 4 ) {
return '*';
}
return item;
} );
return maskerLicenseArray.join('');
},
licenseStatus: function() {
return this.isLicenseActive ? 'activated' : 'not-activated';
},
licenseType: function() {
return this.licenseDetails.type ? this.licenseDetails.type : '';
},
productName: function() {
return this.licenseDetails.product_name ? this.licenseDetails.product_name : '';
},
isLicenseExpired: function() {
return 'expired' === this.licenseStatus ? true : false;
},
expireDate: function() {
let expireCases = [
'0000-00-00 00:00:00',
'lifetime'
];
if ( expireCases.includes( this.licenseDetails.expire ) ) {
return 'Lifetime';
}
return this.licenseDetails.expire;
},
licensePlugins: function() {
return this.licenseDetails.plugins ? this.licenseDetails.plugins : [];
},
},
methods: {
showLicenseManager: function() {
eventBus.$emit( 'showLicenseManager' );
},
licenseAction: function() {
var self = this,
actionType = self.licenseActionType;
self.activationStatus = true;
self.ajaxLicenseAction = $.ajax( {
type: 'POST',
url: dashboardPageConfig.ajaxUrl,
dataType: 'json',
data: {
action: 'jet_license_action',
data: {
license: self.licenseKey,
action: actionType
}
},
beforeSend: function( jqXHR, ajaxSettings ) {
if ( null !== self.ajaxLicenseAction ) {
self.ajaxLicenseAction.abort();
}
},
success: function( responce, textStatus, jqXHR ) {
self.activationStatus = false;
self.$CXNotice.add( {
message: responce.message,
type: responce.status,
duration: 3000,
} );
if ( 'success' === responce.status ) {
if ( 'activate' === actionType ) {
self.licenseStatus = 'active';
self.licenseDetails = responce.data;
eventBus.$emit( 'addLicenseItem', {
'licenseKey': self.licenseKey,
'licenseStatus': 'active',
'licenseDetails': responce.data,
} );
}
if ( 'deactivate' === actionType ) {
eventBus.$emit( 'removeLicenseItem', self.licenseKey );
}
}
}
} );
}
}
});
/**
* [template description]
* @type {String}
*/
Vue.component( 'plugin-item-installed', {
template: '#jet-dashboard-plugin-item-installed',
props: {
pluginData: Object
},
data: function() {
return {
actionPlugin: false,
actionPluginRequest: null,
actionPluginProcessed: false,
licenseActionProcessed: false,
licenseKey: '',
ajaxLicenseAction: null
}
},
computed: {
deactivateAvaliable: function() {
return ( ! this.pluginData['licenseControl'] && this.pluginData['isInstalled'] && this.pluginData['isActivated'] ) ? true : false;
},
activateAvaliable: function() {
return ( this.pluginData['isInstalled'] && !this.pluginData['isActivated'] ) ? true : false;
},
updateAvaliable: function() {
return ( this.pluginData['updateAvaliable'] ) ? true : false;
},
updateActionAvaliable: function() {
return ( this.pluginData['licenseActivated'] && this.pluginData['updateAvaliable'] ) ? true : false;
},
activateLicenseVisible: function() {
return ( this.pluginData['licenseControl'] && !this.pluginData['licenseActivated'] ) ? true : false;
},
deactivateLicenseVisible: function() {
return ( this.pluginData['licenseActivated'] ) ? true : false;
},
},
methods: {
deactivatePlugin: function() {
this.actionPlugin = 'deactivate';
this.pluginAction();
},
activatePlugin: function() {
this.actionPlugin = 'activate';
this.pluginAction();
},
updatePlugin: function() {
console.log(this.updateActionAvaliable);
if ( this.updateActionAvaliable ) {
this.actionPlugin = 'update';
this.pluginAction();
} else {
eventBus.$emit( 'showPopupUpdateCheck' );
}
},
showPopupActivation: function() {
eventBus.$emit( 'showPopupActivation', this.pluginData['slug'] );
},
pluginAction: function() {
let self = this;
self.actionPluginRequest = $.ajax( {
type: 'POST',
url: dashboardPageConfig.ajaxUrl,
dataType: 'json',
data: {
action: 'jet_dashboard_plugin_action',
data: {
action: self.actionPlugin,
plugin: self.pluginData['slug'],
}
},
beforeSend: function( jqXHR, ajaxSettings ) {
if ( null !== self.actionPluginRequest ) {
self.actionPluginRequest.abort();
}
self.actionPluginProcessed = true;
},
success: function( responce, textStatus, jqXHR ) {
self.actionPluginProcessed = false;
self.$CXNotice.add( {
message: responce.message,
type: responce.status,
duration: 3000,
} );
if ( 'success' === responce.status ) {
eventBus.$emit( 'updateUserPluginData', {
'slug': self.pluginData['slug'],
'pluginData': responce.data,
} );
}
}
} );
},
deactivateLicense: function() {
eventBus.$emit( 'showPopupDeactivation', this.pluginData['slug'] );
}
}
});
/**
* [template description]
* @type {String}
*/
Vue.component( 'plugin-item-avaliable', {
template: '#jet-dashboard-plugin-item-avaliable',
props: {
pluginData: Object,
},
data: function() {
return {
pluginActionRequest: null,
pluginActionType: false,
pluginActionProcessed: false,
}
},
computed: {
installAvaliable: function() {
return !this.pluginData['isInstalled'] ? true : false;
},
},
methods: {
installPlugin: function() {
this.pluginActionType = 'install';
this.pluginAction();
},
pluginAction: function() {
let self = this;
self.pluginActionRequest = $.ajax( {
type: 'POST',
url: dashboardPageConfig.ajaxUrl,
dataType: 'json',
data: {
action: 'jet_dashboard_plugin_action',
data: {
action: self.pluginActionType,
plugin: self.pluginData['slug'],
}
},
beforeSend: function( jqXHR, ajaxSettings ) {
if ( null !== self.pluginActionRequest ) {
self.pluginActionRequest.abort();
}
self.pluginActionProcessed = true;
},
success: function( responce, textStatus, jqXHR ) {
self.pluginActionProcessed = false;
self.$CXNotice.add( {
message: responce.message,
type: responce.status,
duration: 3000,
} );
if ( 'success' === responce.status ) {
eventBus.$emit( 'updateUserPluginData', {
'slug': self.pluginData['slug'],
'pluginData': responce.data,
} );
}
}
} );
}
}
});
/**
* [template description]
* @type {String}
*/
Vue.component( 'plugin-item-more', {
template: '#jet-dashboard-plugin-item-more',
props: {
pluginData: Object
},
data: function() {
return {
morePluginsUrl: dashboardPageConfig.getMorePluginsUrl || {},
}
},
});
/**
* [template description]
* @type {String}
*/
Vue.component( 'jet-dashboard-header', {
template: '#jet-dashboard-header',
data: function() {
return {
title: dashboardPageConfig.headerTitle || '',
}
},
});
/**
* [mounted description]
*/
window.JetDasboardPage = new Vue( {
el: '#jet-dashboard-page',
data: {
page: dashboardPageConfig.page || false
},
} );
})( jQuery, window.JetDashboardPageConfig );

View File

@@ -0,0 +1,247 @@
(function () {
'use strict';
Vue.component( 'license-page', {
template: '#jet-dashboard-license-page',
data: function() {
return {
allJetPlugins: window.JetDashboardPageConfig.allJetPlugins || {},
licenseList: window.JetDashboardPageConfig.licenseList || [],
licenseManagerVisible: false,
licensePopupVisible: false,
deactivatePopupVisible: false,
updateCheckPopupVisible: false,
licenseActionProcessed: false,
ajaxLicenseAction: null,
activatingPluginSlug: false,
};
},
created: function() {
eventBus.$on( 'addLicenseItem', this.addLicense );
eventBus.$on( 'removeLicenseItem', this.removeLicense );
eventBus.$on( 'updateUserPluginData', this.updateUserPluginData );
eventBus.$on( 'showLicenseManager', this.showLicenseManager );
eventBus.$on( 'showPopupActivation', this.showPopupActivation );
eventBus.$on( 'showPopupDeactivation', this.showPopupDeactivation );
eventBus.$on( 'showPopupUpdateCheck', this.showPopupUpdateCheck );
},
computed: {
newlicenseData: function() {
return {
'licenseStatus': 'inactive',
'licenseKey': '',
'licenseDetails': {},
};
},
licencePluginList: function() {
let licencePluginList = {};
for ( let licence of this.licenseList ) {
let plugins = licence['licenseDetails']['plugins'];
for ( let plugin in plugins ) {
let pluginData = plugins[ plugin ];
let pluginSlug = pluginData.slug;
if ( ! licencePluginList.hasOwnProperty( plugin ) ) {
licencePluginList[ plugin ] = pluginData;
}
}
}
return licencePluginList;
},
installedPluginList: function() {
let installedPluginList = {};
for ( let pluginSlug in this.allJetPlugins ) {
if ( this.allJetPlugins[ pluginSlug ][ 'isInstalled' ] ) {
let pluginData = this.allJetPlugins[ pluginSlug ];
let licenseActivated = this.licencePluginList.hasOwnProperty( pluginSlug ) ? true : false;
this.$set( pluginData, 'licenseActivated', licenseActivated );
installedPluginList[ pluginSlug ] = pluginData;
}
}
return installedPluginList;
},
installedPluginListVisible: function() {
return 0 !== Object.keys( this.installedPluginList ).length ? true : false;
},
avaliablePluginList: function() {
let avaliablePluginList = {};
for ( let pluginSlug in this.allJetPlugins ) {
if ( ( ! this.allJetPlugins[ pluginSlug ]['isInstalled'] )
&& this.licencePluginList.hasOwnProperty( pluginSlug ) ) {
let pluginData = this.allJetPlugins[ pluginSlug ];
let licenseActivated = this.licencePluginList.hasOwnProperty( pluginSlug ) ? true : false;
this.$set( pluginData, 'licenseActivated', licenseActivated );
avaliablePluginList[ pluginSlug ] = pluginData;
}
}
return avaliablePluginList;
},
avaliablePluginListVisible: function() {
return 0 !== Object.keys( this.avaliablePluginList ).length ? true : false;
},
morePluginList: function() {
let morePluginList = {};
for ( let pluginSlug in this.allJetPlugins ) {
if ( ( ! this.allJetPlugins[ pluginSlug ]['isInstalled'] ) &&
( ! this.licencePluginList.hasOwnProperty( pluginSlug ) ) ) {
let pluginData = this.allJetPlugins[ pluginSlug ];
let licenseActivated = this.licencePluginList.hasOwnProperty( pluginSlug ) ? true : false;
this.$set( pluginData, 'licenseActivated', licenseActivated );
morePluginList[ pluginSlug ] = pluginData;
}
}
return morePluginList;
},
morePluginListVisible: function() {
return Object.keys( this.morePluginList ).length ? true : false;
},
},
methods: {
showLicenseManager: function() {
this.deactivatePopupVisible = false;
this.licensePopupVisible = false;
this.licenseManagerVisible = true;
},
showPopupActivation: function( slug ) {
this.activatingPluginSlug = slug;
this.updateCheckPopupVisible = false;
this.licensePopupVisible = true;
},
showPopupDeactivation: function( slug ) {
this.deactivatePopupVisible = true;
},
showPopupUpdateCheck: function() {
this.updateCheckPopupVisible = true;
},
addNewLicense: function() {
this.licenseManagerVisible = false;
this.licensePopupVisible = true;
},
addLicense: function( licenseData ) {
this.licenseList.push( licenseData );
},
removeLicense: function( licenceKey ) {
let removingIndex = false;
for ( let licenceIndex in this.licenseList ) {
let licenseData = this.licenseList[ licenceIndex ];
if ( licenseData['licenseKey'] === licenceKey ) {
removingIndex = licenceIndex;
break;
}
}
if ( removingIndex ) {
this.licenseList.splice( removingIndex, 1 );
}
this.licensePopupVisible = false;
},
updateUserPluginData: function( data ) {
let slug = data.slug,
pluginData = data.pluginData;
this.allJetPlugins[ slug ] = Object.assign( {}, this.allJetPlugins[ slug ], pluginData );
},
licenseAction: function() {
var self = this;
self.ajaxLicenseAction = jQuery.ajax( {
type: 'POST',
url: window.JetDashboardPageConfig.ajaxUrl,
dataType: 'json',
data: {
action: 'jet_license_action',
data: {
//plugin: self.activatingPluginSlug,
license: self.licenseKey,
action: 'activate'
}
},
beforeSend: function( jqXHR, ajaxSettings ) {
if ( null !== self.ajaxLicenseAction ) {
self.ajaxLicenseAction.abort();
}
self.licenseActionProcessed = true;
},
success: function( responce, textStatus, jqXHR ) {
self.licenseActionProcessed = false;
self.$CXNotice.add( {
message: responce.message,
type: responce.status,
duration: 3000,
} );
if ( 'success' === responce.status ) {
self.addLicense( {
'licenseKey': self.licenseKey,
'licenseStatus': 'active',
'licenseDetails': responce.data,
} );
}
}
} );
}
}
} );
})();

View File

@@ -0,0 +1,12 @@
(function () {
'use strict';
Vue.component( 'welcome-page', {
template: '#jet-dashboard-welcome-page',
data: function() {
return {};
}
} );
})();

View File

@@ -0,0 +1,715 @@
.cx-vui-notices {
z-index: 1000;
}
.jet-dashboard-page {
font-family: Roboto,-apple-system,BlinkMacSystemFont,Segoe UI,Oxygen-Sans,Ubuntu,Cantarell,Helvetica Neue,sans-serif;
margin: 25px 15px 0 15px;
&__header {
position: relative;
padding: 40px;
background: linear-gradient(90deg, #5B77E7 0%, #49B5D2 53.65%, #26E8A8 100%);
border-radius: 6px 6px 0px 0px;
.header-title {
color: white;
font-size: 18px;
font-weight: normal;
margin: 0;
}
.header-bg {
position: absolute;
top: 0;
right: 0;
}
}
&__content {
position: relative;
font-family: Roboto,-apple-system,BlinkMacSystemFont,Segoe UI,Oxygen-Sans,Ubuntu,Cantarell,Helvetica Neue,sans-serif;
}
&__footer {}
p {
font-size: 12px;
color: #7b7e81;
margin: 0 0 10px 0;
}
.dashicons {
display: flex;
justify-content: center;
align-items: center;
}
.cx-vui-subtitle {
font-size: 24px;
font-weight: 500;
margin-bottom: 40px;
padding-bottom: 16px;
border-bottom: 1px solid #DCDCDD;
}
.cx-vui-button {
background-color: transparent;
&:hover {
background-color: transparent;
}
.cx-vui-button__content {
> span {
display: flex;
justify-content: flex-start;
align-items: center;
}
.button-icon {
margin-right: 5px;
}
}
&.cx-vui-button--style-accent {
color: #007cba;
box-shadow: inset 0px 0px 0px 1px #007cba;
.cx-vui-button__loader {
svg, path {
fill: #007cba;
}
}
.button-icon, path {
fill: #007cba;
}
}
&.cx-vui-button--style-danger {
color: #D6336C;
box-shadow: inset 0px 0px 0px 1px #D6336C;
.cx-vui-button__loader {
svg, path {
fill: #D6336C;
}
}
.button-icon, path {
fill: #D6336C;
}
}
}
.cx-vui-alert {
width: 100%;
box-sizing: border-box;
padding: 10px 20px;
margin-top: 20px;
background-color: #F4F4F5;
border-radius: 4px;
display: flex;
justify-content: flex-start;
align-items: flex-start;
.cx-vui-alert__icon {
margin-top: 3px;
margin-right: 10px;
}
.cx-vui-alert__message {
flex: 1 1 auto;
color: #7B7E81;
font-size: 13px;
}
&.info-type {
background-color: #EDF6FA;
.cx-vui-alert__icon {
svg {
fill: #007CBA;
}
}
.cx-vui-alert__message {
color: #007CBA;
}
}
&.success-type {
background-color: #E9F6EA;
.cx-vui-alert__icon {
svg {
fill: #46B450;
}
}
.cx-vui-alert__message {
color: #46B450;
}
}
&.error-type {
background-color: #FBF0F0;
.cx-vui-alert__icon {
svg {
fill: #C92C2C;
}
}
.cx-vui-alert__message {
color: #C92C2C;
}
}
}
.cx-vui-popup {
.cx-vui-popup__header {
text-align: center;
margin-bottom: 30px;
}
.cx-vui-popup__header-label {
font-weight: 500;
font-size: 24px;
line-height: 36px;
text-align: center;
color: #23282D;
}
.cx-vui-popup__content {
}
&.license-manager-popup {
.cx-vui-popup__body {
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: stretch;
overflow: hidden;
max-height: calc( 100% - 100px );
}
.cx-vui-popup__header {
padding-bottom: 15px;
border-bottom: 1px solid #DCDCDD;
.cx-vui-popup__header-inner {
display: flex;
justify-content: space-between;
align-items: center;
}
}
.cx-vui-popup__content {
flex: 1 1 auto;
overflow-y: auto;
.license-manager {
width: 100%;
max-width: 1260px;
}
}
}
&.license-activation-popup {
.cx-vui-popup__header {
text-align: center;
}
.cx-vui-popup__body {
}
.popup-licence-control {
width: 100%;
display: flex;
justify-content: flex-start;
align-items: flex-start;
flex-wrap: wrap;
margin-top: 10px;
p {
width: 100%;
}
.popup-licence__key {
flex: 1 1 auto;
input {
border-radius: 4px 0 0 4px;
}
}
.popup-licence__action-button {
border-radius: 0 4px 4px 0;
box-shadow: none;
}
}
}
&.license-deactivation-popup {
.cx-vui-popup__content {
text-align: center;
.show-license-manager {
margin-top: 20px;
}
}
}
&.update-check-popup {
.cx-vui-popup__content {
text-align: center;
svg {
margin-bottom: 20px;
}
p {
text-align: center;
line-height: 30px;
span {
font-size: 20px;
color: #23282d;
display: block;
}
}
.cx-vui-button {
margin-top: 20px;
}
}
}
}
}
.jet-dashboard-license-page {
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: stretch;
.ready-for-use-plugins {
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: stretch;
padding: 40px;
}
.avaliable-plugins {
margin-top: 50px;
}
.license-manager-button {
align-self: flex-end;
}
.plugin-list--more-plugins {
display: flex;
justify-content: flex-start;
align-items: stretch;
flex-wrap: wrap;
.plugin-item {
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: stretch;
flex-wrap: wrap;
width: 19%;
min-width: 200px;
margin-right: 1%;
margin-bottom: 30px;
&__inner {
height: 100%;
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: stretch;
.plugin-tumbnail {
flex: 1 1 100%;
img {
width: auto;
max-width: 100%;
}
}
}
}
}
.plugin-list {
display: flex;
justify-content: flex-start;
align-items: flex-start;
flex-wrap: wrap;
.plugin-item {
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: stretch;
width: 30%;
min-width: 400px;
margin-right: 2%;
margin-bottom: 40px;
&__inner {
display: flex;
justify-content: flex-start;
align-items: flex-start;
}
&.is-installed {}
&.is-activated {}
&.update-avaliable {
.plugin-version {
background-color: #D6336C;
}
}
&--more {
.plugin-item__inner {
flex-direction: column;
align-items: stretch;
.plugin-tumbnail {
margin: 0;
img {
width: auto;
}
}
}
}
}
.plugin-tumbnail {
position: relative;
margin-right: 20px;
img {
width: 100px;
}
}
.plugin-info {
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: flex-start;
flex: 1 1 auto;
}
.plugin-name {
display: flex;
justify-content: flex-start;
align-items: center;
font-size: 15px;
color: #23282d;
font-weight: 500;
}
.plugin-desc {
margin: 10px 0 0 0;
}
.plugin-version {
font-size: 12px;
padding: 2px 6px;
border-radius: 3px;
background-color: #46B450;
color: white;
margin-left: 10px;
}
.plugin-actions {
width: 100%;
display: flex;
justify-content: flex-start;
align-items: center;
flex-wrap: wrap;
margin-top: 20px;
.cx-vui-button {
font-size: 13px;
margin-left: 20px;
&:first-child {
margin-left: 0;
}
}
.show-license-control {
color: #46B450;
}
.deactivate-plugin-button {
color: #D6336C;
}
}
.plugin-update-label {
display: flex;
justify-content: flex-start;
align-items: center;
margin-top: 10px;
color: #7B7E81;
font-size: 13px;
.latest-version {
color: #007DBA;
font-weight: 500;
margin: 0 3px;
}
.cx-vui-button {
font-size: 13px;
margin-left: 3px;
}
}
}
.add-new-license {
display: flex;
.cx-vui-button__content {
> span {
display: flex;
}
.dashicons {
font-size: 16px;
}
}
}
.license-manager {
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: stretch;
.license-list {
width: 100%;
display: flex;
justify-content: flex-start;
align-items: stretch;
flex-wrap: wrap;
.license-item {
margin: 10px;
}
}
}
.license-item {
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: stretch;
width: 400px;
&__label {
font-weight: 500;
font-size: 24px;
line-height: 36px;
text-align: center;
color: #23282D;
margin-bottom: 40px;
}
&__control {
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: stretch;
.license-item__activation-message {
text-align: center;
margin-bottom: 30px;
}
.license-item__key {
}
.license-item__action-button {
margin-top: 10px;
}
}
&__details {
flex-direction: 1 1 auto;
}
&__deactivation {
align-self: flex-start;
}
&.license-activated {
.license-status {
color: #46B450;
}
.license-item__deactivation {
color: #D6336C;
box-shadow: inset 0px 0px 0px 1px #D6336C;
}
}
}
.license-details {
margin: 30px 0;
&__label {
color: #23282D;
font-size: 15px;
font-weight: 700;
margin-bottom: 20px;
}
&__fields {
display: flex;
flex-direction: column;
justify-content: flex-start;
align-items: stretch;
}
&__field {
display: flex;
justify-content: flex-start;
align-items: stretch;
margin-bottom: 10px;
&:last-child {
margin-bottom: 0;
}
.label {
min-width: 120px;
font-weight: 700;
white-space: nowrap;
color: #23282D;
}
.status-label {
text-transform: capitalize;
color: #46B450;
}
.license-type {
display: flex;
justify-content: center;
align-items: center;
svg {
width: 110px;
height: auto;
}
}
.included-plugin-list {
display: flex;
justify-content: flex-start;
align-items: flex-start;
flex-wrap: wrap;
flex: 1 1 auto;
.included-plugin {
width: 50%;
margin-bottom: 10px;
display: flex;
justify-content: flex-start;
align-items: center;
svg {
margin-right: 5px;
}
}
}
&.license-status {
color: #C92C2C;
font-weight: 700;
text-transform: capitalize;
}
&.license-type {
text-transform: capitalize;
}
&.license-plugins {
flex: 1 1 auto;
}
}
&__actions {
display: flex;
justify-content: space-between;
align-items: center;
margin-top: 20px;
.show-license-manager {
font-size: 13px;
}
.cx-vui-button {
margin-left: 5px;
&:first-child {
margin-left: 0;
}
}
}
}
}
.popup-enter {
opacity: 0;
.cx-vui-popup__body {
transform: translateY(10px);
}
}
.popup-enter-active {
transition: opacity .3s;
.cx-vui-popup__body {
transition: transform .3s;
}
}
.popup-enter-to {
opacity: 1;
transform: translateY(0);
.cx-vui-popup__body {
transform: translateY(0px);
}
}
.popup-leave {
opacity: 1;
}
.popup-leave-leave {
transition: opacity .1s;
}
.popup-leave-to {
opacity: 0;
}

View File

@@ -0,0 +1,36 @@
'use strict';
let gulp = require('gulp'),
rename = require('gulp-rename'),
notify = require('gulp-notify'),
autoprefixer = require('gulp-autoprefixer'),
sass = require('gulp-sass'),
plumber = require('gulp-plumber');
gulp.task('jet-dashboard-admin', () => {
return gulp.src('./assets/scss/jet-dashboard-admin.scss')
.pipe(
plumber( {
errorHandler: function ( error ) {
console.log('=================ERROR=================');
console.log(error.message);
this.emit( 'end' );
}
})
)
.pipe(sass( { outputStyle: 'compressed' } ))
.pipe(autoprefixer({
browsers: ['last 10 versions'],
cascade: false
}))
.pipe(rename('jet-dashboard-admin.css'))
.pipe(gulp.dest('./assets/css/'))
.pipe(notify('Compile Sass Done!'));
});
//watch
gulp.task('watch', () => {
gulp.watch('./assets/scss/**', gulp.series( 'jet-dashboard-admin' ) );
});

View File

@@ -0,0 +1,220 @@
<?php
namespace Jet_Dashboard;
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
/**
* Define Jet_Dashboard_License_Manager class
*/
class License_Manager {
/**
* [$slug description]
* @var boolean
*/
public $license_data_key = 'jet-license-data';
/**
* [$sys_messages description]
* @var array
*/
public $sys_messages = [];
/**
* Init page
*/
public function __construct() {
$this->sys_messages = apply_filters( 'jet_dashboard_license_sys_messages', array(
'internal' => 'Internal error. Please, try again later',
'server_error' => 'Server error. Please, try again later',
) );
add_action( 'wp_ajax_jet_license_action', array( $this, 'jet_license_action' ) );
$this->license_expire_check();
$this->maybe_theme_core_license_exist();
}
/**
* [maybe_theme_core_license_exist description]
* @return [type] [description]
*/
public function maybe_theme_core_license_exist() {
$jet_theme_core_key = get_option( 'jet_theme_core_license', false );
if ( ! $jet_theme_core_key ) {
return false;
}
$jet_theme_core_license_sync = get_option( 'jet_theme_core_sync', 'false' );
if ( filter_var( $jet_theme_core_license_sync, FILTER_VALIDATE_BOOLEAN ) ) {
return false;
}
$license_list = Utils::get_license_data( 'license-list', [] );
if ( array_key_exists( $jet_theme_core_key, $license_list ) ) {
return false;
}
$responce = $this->license_action_query( 'activate_license', $jet_theme_core_key );
$responce_data = isset( $responce['data'] ) ? $responce['data'] : [];
$license_list[ $jet_theme_core_key ] = array(
'licenseStatus' => 'active',
'licenseKey' => $jet_theme_core_key,
'licenseDetails' => $responce_data,
);
update_option( 'jet_theme_core_sync', 'true' );
if ( 'error' === $responce['status'] ) {
Utils::set_license_data( 'license-list', $license_list );
return false;
}
Utils::set_license_data( 'license-list', $license_list );
}
/**
* [license_expire_check description]
* @return [type] [description]
*/
public function license_expire_check() {
$jet_dashboard_license_expire_check = get_site_transient( 'jet_dashboard_license_expire_check' );
if ( $jet_dashboard_license_expire_check ) {
return false;
}
Utils::license_data_expire_sync();
set_site_transient( 'jet_dashboard_license_expire_check', 'true', HOUR_IN_SECONDS * 12 );
}
/**
* Proccesing subscribe form ajax
*
* @return void
*/
public function jet_license_action() {
$data = ( ! empty( $_POST['data'] ) ) ? $_POST['data'] : false;
if ( ! $data ) {
wp_send_json(
array(
'status' => 'error',
'message' => $this->sys_messages['server_error'],
'data' => [],
)
);
}
$license_action = $data['action'];
$license_key = $data['license'];
if ( empty( $license_key ) && isset( $data['plugin'] ) ) {
$license_key = Utils::get_plugin_license_key( $data['plugin'] );
}
$responce = $this->license_action_query( $license_action . '_license', $license_key );
$responce_data = [];
if ( 'error' === $responce['status'] ) {
wp_send_json(
array(
'status' => 'error',
'message' => $responce['message'],
'data' => isset( $responce['data'] ) ? $responce['data'] : [],
)
);
}
if ( isset( $responce['data'] ) ) {
$responce_data = $responce['data'];
}
switch ( $license_action ) {
case 'activate':
$this->update_license_list( $license_key, $responce_data );
break;
case 'deactivate':
$license_list = Utils::get_license_data( 'license-list', [] );
unset( $license_list[ $license_key ] );
Utils::set_license_data( 'license-list', $license_list );
break;
}
$responce_data['license_key'] = $license_key;
set_site_transient( 'update_plugins', null );
wp_send_json(
array(
'status' => 'success',
'message' => $responce['message'],
'data' => $responce_data,
)
);
}
/**
* [update_license_list description]
* @param boolean $responce [description]
* @return [type] [description]
*/
public function update_license_list( $license_key = '', $responce = false ) {
$license_list = Utils::get_license_data( 'license-list', [] );
$license_list[ $license_key ] = array(
'licenseStatus' => 'active',
'licenseKey' => $license_key,
'licenseDetails' => $responce,
);
Utils::set_license_data( 'license-list', $license_list );
}
/**
* Remote request to updater API.
*
* @since 1.0.0
* @return array|bool
*/
public function license_action_query( $action = '', $license = '' ) {
$query_url = add_query_arg(
array(
'action' => $action,
'license' => $license,
'site_url' => urlencode( Utils::get_site_url() ),
),
Utils::get_api_url()
);
$response = wp_remote_get( $query_url );
if ( is_wp_error( $response ) || wp_remote_retrieve_response_code( $response ) != '200' ) {
return false;
}
return json_decode( $response['body'], true );
}
}

View File

@@ -0,0 +1,129 @@
<?php
namespace Jet_Dashboard;
use Jet_Dashboard\Dashboard as Dashboard;
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
/**
* Define Jet_Dashboard_License_Manager class
*/
class Module_Manager {
/**
* Modules map
*
* @var array
*/
private $registered_modules = array();
/**
* [__construct description]
*/
public function __construct() {
add_action( 'init', array( $this, 'init_module' ), -996 );
}
/**
* [$modules description]
* @var array
*/
public function register_modules( $modules = array() ) {
if ( empty( $modules ) ) {
return;
}
foreach ( $modules as $module_slug => $module_class ) {
if ( ! array_key_exists( $module_slug, $this->registered_modules ) ) {
$this->registered_modules[ $module_slug ] = $module_class;
}
}
}
/**
* [get_registeredregistered_modules description]
* @param array $modules [description]
* @return [type] [description]
*/
public function get_registered_modules() {
return $this->registered_modules;
}
/**
* Initialize modules on aproppriate AJAX or on module page
*
* @return [type] [description]
*/
public function init_module() {
if ( wp_doing_ajax() ) {
$this->maybe_load_module_on_ajax();
} else {
$this->maybe_load_module();
}
}
/**
* Maybe load on ajax request
*
* @return [type] [description]
*/
public function maybe_load_module_on_ajax() {
$action = ! empty( $_REQUEST['action'] ) ? $_REQUEST['action'] : false;
if ( ! $action ) {
return;
}
$parts = explode( '/', $action );
if ( empty( $parts[1] ) || Dashboard::get_instance()->dashboard_slug !== $parts[0] ) {
return;
}
$module = $parts[1];
$this->load_module( $module );
}
/**
* Maybe load on regular request
*
* @return [type] [description]
*/
public function maybe_load_module() {
if ( ! Dashboard::get_instance()->is_dashboard_page() ) {
return;
}
$module = Dashboard::get_instance()->get_subpage();
$this->load_module( $module );
}
/**
* Load module by slug
*
* @param [type] $module [description]
* @return [type] [description]
*/
public function load_module( $module ) {
if ( ! isset( $this->registered_modules[ $module ] ) ) {
return;
}
$class_name = $this->registered_modules[ $module ];
return new $class_name();
}
}

View File

@@ -0,0 +1,114 @@
<?php
namespace Jet_Dashboard\Base;
use Jet_Dashboard\Dashboard as Dashboard;
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
abstract class Module {
abstract public function get_slug();
public function __construct() {
$this->init();
add_action(
'jet-dashboard/before-enqueue-assets/' . $this->get_slug(),
array( $this, 'assets' )
);
add_action( 'wp_ajax_jet_dashboard/' . $this->get_slug(), array( $this, 'process_ajax' ) );
}
/**
* Initialize module-specific parts
*
* @return [type] [description]
*/
public function init() {}
/**
* Register module assets
*
* @return [type] [description]
*/
public function assets() {
$this->enqueue_module_assets();
add_filter( 'jet-dashboard/js-page-config', array( $this, 'page_config' ), 10, 2 );
add_filter( 'jet-dashboard/js-page-templates', array( $this, 'page_templates' ), 10, 2 );
}
/**
* Process ajax
*
* @return [type] [description]
*/
public function process_ajax() {
$handler = isset( $_REQUEST['handler'] ) ? $_REQUEST['handler'] : false;
if ( ! $handler || ! is_callable( array( $this, $handler ) ) ) {
return;
}
if ( ! current_user_can( 'manage_options' ) ) {
wp_send_json_error( array(
'message' => 'You are not allowed to access this',
) );
}
$nonce = isset( $_REQUEST['nonce'] ) ? esc_attr( $_REQUEST['nonce'] ) : false;
if ( ! $nonce || ! wp_verify_nonce( $nonce, Dashboard::get_instance()->get_dashboard_page_url() ) ) {
wp_send_json_error( array(
'message' => 'Nonce verfictaion failed',
) );
}
call_user_func( array( $this, $handler ) );
}
/**
* Enqueue module-specific assets
*
* @return void
*/
public function enqueue_module_assets() {}
/**
* Modify page config
*
* @param [type] $config [description]
* @return [type] [description]
*/
public function page_config( $config = array(), $subpage = '' ) {
return $config;
}
/**
* Add page templates
*
* @param [type] $config [description]
* @return [type] [description]
*/
public function page_templates( $templates = array(), $subpage = '' ) {
return $templates;
}
/**
* Returns link to current page
*
* @return [type] [description]
*/
public function get_page_link() {
return Dashboard::get_instance()->get_dashboard_page_url( $this->get_slug() );
}
}

View File

@@ -0,0 +1,86 @@
<?php
namespace Jet_Dashboard\Modules\License;
use Jet_Dashboard\Base\Module as Module_Base;
use Jet_Dashboard\Dashboard as Dashboard;
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
class Module extends Module_Base {
/**
* [init description]
* @return [type] [description]
*/
public function init() {
add_action( 'admin_menu', array( $this, 'register_license_page' ), 22 );
}
/**
* [register_license_page description]
* @return [type] [description]
*/
public function register_license_page() {
}
/**
* Returns module slug
*
* @return void
*/
public function get_slug() {
return 'license-page';
}
/**
* Enqueue module-specific assets
*
* @return void
*/
public function enqueue_module_assets() {
wp_enqueue_script(
'jet-dashboard-license-page',
Dashboard::get_instance()->get_dashboard_url() . 'assets/js/license-page.js',
array( 'cx-vue-ui' ),
Dashboard::get_instance()->get_dashboard_version(),
true
);
}
/**
* License page config
*
* @param array $config [description]
* @param string $subpage [description]
* @return [type] [description]
*/
public function page_config( $config = array(), $subpage = '' ) {
$config['headerTitle'] = 'License Manager';
$config['page'] = 'license-page';
$config['wrapperCss'] = 'license-page';
return $config;
}
/**
* [page_templates description]
* @param array $templates [description]
* @param string $subpage [description]
* @return [type] [description]
*/
public function page_templates( $templates = array(), $subpage = '' ) {
$templates['license-page'] = 'license/main';
$templates['license-item'] = 'license/license-item';
$templates['plugin-item-installed'] = 'license/plugin-item-installed';
$templates['plugin-item-avaliable'] = 'license/plugin-item-avaliable';
$templates['plugin-item-more'] = 'license/plugin-item-more';
return $templates;
}
}

View File

@@ -0,0 +1,68 @@
<?php
namespace Jet_Dashboard\Modules\Welcome;
use Jet_Dashboard\Base\Module as Module_Base;
use Jet_Dashboard\Dashboard as Dashboard;
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
class Module extends Module_Base {
/**
* Returns module slug
*
* @return void
*/
public function get_slug() {
return 'welcome-page';
}
/**
* Enqueue module-specific assets
*
* @return void
*/
public function enqueue_module_assets() {
wp_enqueue_script(
'jet-dashboard-welcome-page',
Dashboard::get_instance()->get_dashboard_url() . 'assets/js/welcome-page.js',
array( 'cx-vue-ui' ),
Dashboard::get_instance()->get_dashboard_version(),
true
);
}
/**
* License page config
*
* @param array $config [description]
* @param string $subpage [description]
* @return [type] [description]
*/
public function page_config( $config = array(), $subpage = '' ) {
$config['headerTitle'] = 'Welcome';
$config['page'] = 'welcome-page';
$config['wrapperCss'] = 'welcome-page';
return $config;
}
/**
* Add welcome component template
*
* @param array $templates [description]
* @param string $subpage [description]
* @return [type] [description]
*/
public function page_templates( $templates = array(), $subpage = '' ) {
$templates['welcome-page'] = 'welcome/main';
return $templates;
}
}

View File

@@ -0,0 +1,855 @@
<?php
namespace Jet_Dashboard;
use Jet_Dashboard\Dashboard as Dashboard;
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
/**
* Define plugin updater class.
*
* @since 1.0.0
*/
class Plugin_Manager {
/**
* [$jet_banners_url description]
* @var string
*/
public $jet_banners_url = 'https://account.crocoblock.com/free-download/images/jetbanners/';
/**
* [$jet_changelog_url description]
* @var string
*/
public $jet_changelog_url = 'https://crocoblock.com/wp-content/uploads/jet-changelog/%s.json';
/**
* [$remote_plugin_data description]
* @var boolean
*/
public $remote_plugin_data = false;
/**
* [$user_plugins description]
* @var boolean
*/
public $user_plugins = false;
/**
* [$update_plugins description]
* @var boolean
*/
public $update_plugins = false;
/**
* [$registered_plugins description]
* @var boolean
*/
public $registered_plugins = false;
/**
* [$registered_plugins description]
* @var boolean
*/
public $registered_plugins_data = false;
/**
* Init class parameters.
*
* @since 1.0.0
* @param array $attr Input attributes array.
* @return void
*/
public function __construct() {
add_action( 'wp_ajax_jet_dashboard_plugin_action', array( $this, 'plugin_action' ) );
$registered_plugins = Dashboard::get_instance()->get_registered_plugins();
if ( ! empty( $registered_plugins ) ) {
foreach ( $registered_plugins as $plugin_file => $plugin_data ) {
add_filter( 'in_plugin_update_message-' . $plugin_file , array( $this, 'in_plugin_update_message' ), 10, 2 );
}
}
/**
* Need for test update - set_site_transient( 'update_plugins', null );
*/
add_action( 'pre_set_site_transient_update_plugins', array( $this, 'check_update' ) );
add_action( 'admin_init', array( $this, 'generate_register_plugin_data' ) );
add_filter( 'plugins_api', array( $this, 'plugins_api_filter' ), 10, 3 );
add_filter( 'plugin_row_meta', array( $this, 'plugin_row_meta' ), 10, 3 );
}
/**
* [admin_init description]
* @return [type] [description]
*/
public function generate_register_plugin_data() {
$registered_plugins = Dashboard::get_instance()->get_registered_plugins();
if ( ! empty( $registered_plugins ) ) {
foreach ( $registered_plugins as $plugin_file => $plugin_data ) {
$plugin_info = get_plugin_data( WP_PLUGIN_DIR . '/' . $plugin_file );
$this->registered_plugins_data[ $plugin_file ] = array(
'name' => $plugin_info['Name'],
'author' => $plugin_info['Author'],
'plugin_url' => $plugin_info['PluginURI'],
'requires' => '5.2',
'tested' => '',
'banners' => array(
'high' => sprintf( 'https://account.crocoblock.com/free-download/images/jetbanners/%s.png', $plugin_data['slug'] ),
'low' => sprintf( 'https://account.crocoblock.com/free-download/images/jetbanners/%s.png', $plugin_data['slug'] ),
),
'version' => false,
'changelog' => false,
'slug' => $plugin_data['slug'],
'transient_key' => $plugin_data['slug'] . '_plugin_info_data'
);
}
}
}
/**
* [plugins_api_filter description]
* @param [type] $_data [description]
* @param string $_action [description]
* @param [type] $_args [description]
* @return [type] [description]
*/
public function plugins_api_filter( $_data, $_action = '', $_args = null ) {
if ( 'plugin_information' !== $_action ) {
return $_data;
}
if ( ! isset( $_args->slug ) ) {
return $_data;
}
$registered_plugin_data = false;
foreach ( $this->registered_plugins_data as $plugin_file => $plugin_data ) {
if ( $plugin_data['slug'] === $_args->slug ) {
$registered_plugin_data = $plugin_data;
break;
}
}
if ( ! $registered_plugin_data ) {
return $_data;
}
$plugin_api_data = get_site_transient( $registered_plugin_data['transient_key'] );
if ( empty( $plugin_api_data ) ) {
$changelog_remote_response = $this->changelog_remote_query( $registered_plugin_data['slug'] );
if ( ! $changelog_remote_response ) {
return $_data;
}
$plugin_api_data = new \stdClass();
$plugin_api_data->name = $registered_plugin_data['name'];
$plugin_api_data->slug = $registered_plugin_data['slug'];
$plugin_api_data->author = $registered_plugin_data['author'];
$plugin_api_data->homepage = $registered_plugin_data['plugin_url'];
$plugin_api_data->requires = $registered_plugin_data['requires'];
$plugin_api_data->tested = $registered_plugin_data['tested'];
$plugin_api_data->banners = $registered_plugin_data['banners'];
$plugin_api_data->version = $changelog_remote_response->current_version;
$plugin_api_data->sections = array(
'changelog' => $changelog_remote_response->changelog,
);
// Expires in 1 day
set_site_transient( $registered_plugin_data['transient_key'], $plugin_api_data, DAY_IN_SECONDS );
}
$_data = $plugin_api_data;
return $_data;
}
/**
* [changelog_remote_query description]
* @param [type] $slug [description]
* @return [type] [description]
*/
public function changelog_remote_query( $slug ) {
$response = wp_remote_get( sprintf( $this->jet_changelog_url, $slug ) );
if ( is_wp_error( $response ) || wp_remote_retrieve_response_code( $response ) != '200' ) {
return false;
}
$response = json_decode( $response['body'] );
return $response;
}
/**
* [plugin_row_meta description]
* @param [type] $plugin_meta [description]
* @param [type] $plugin_file [description]
* @param [type] $plugin_data [description]
* @return [type] [description]
*/
public function plugin_row_meta( $plugin_meta, $plugin_file, $plugin_data ) {
if ( array_key_exists( $plugin_file, $this->registered_plugins_data ) && empty( $plugin_data['update'] ) ) {
$plugin_meta['view-details'] = sprintf( '<a href="%s" class="thickbox open-plugin-details-modal" aria-label="%s" data-title="%s">%s</a>',
esc_url( network_admin_url( 'plugin-install.php?tab=plugin-information&plugin=' . $this->registered_plugins_data[ $plugin_file ]['slug'] . '&TB_iframe=true&width=600&height=550' ) ),
esc_attr( sprintf( __( 'More information about %s', 'jet-tricks' ), $this->registered_plugins_data[ $plugin_file ]['name'] ) ),
esc_attr( $this->registered_plugins_data[ $plugin_file ]['name'] ),
'View details'
);
}
return $plugin_meta;
}
/**
* [plugin_row_meta description]
* @param [type] $plugin_meta [description]
* @param [type] $plugin_file [description]
* @param [type] $plugin_data [description]
* @return [type] [description]
*/
public function in_plugin_update_message( $plugin_data, $response ) {
if ( ! $response->package ) {
echo sprintf( '&nbsp;<strong><a class="" href="%1$s">%2$s</a><strong>', Dashboard::get_instance()->get_dashboard_page_url(), 'Activate your license for automatic updates.' );
}
}
/**
* Process update.
*
* @since 1.0.0
* @param object $data Update data.
* @return object
*/
public function check_update( $data ) {
delete_site_transient( 'jet_dashboard_remote_jet_plugin_list' );
$registered_plugins = Dashboard::get_instance()->get_registered_plugins();
foreach ( $registered_plugins as $plugin_slug => $plugin_data ) {
$new_update_version = $this->check_new_update_version( $plugin_data );
if ( $new_update_version ) {
// Delete plugin api transient data
if ( ! empty( $this->registered_plugins_data ) && isset( $this->registered_plugins_data[ $plugin_data['file'] ] ) ) {
delete_site_transient( $this->registered_plugins_data[ $plugin_data['file'] ]['transient_key'] );
}
$update = new \stdClass();
$update->slug = $plugin_data['slug'];
$update->plugin = $plugin_data['file'];
$update->new_version = $new_update_version;
$update->url = false;
$update->package = Utils::package_url( $plugin_data['file'] );
$data->response[ $plugin_data['file'] ] = $update;
}
}
return $data;
}
/**
* [check_update description]
* @return [type] [description]
*/
public function check_new_update_version( $plugin_data = false ) {
$remote_plugin_data = $this->get_remote_jet_plugin_list();
if ( ! $remote_plugin_data || ! is_array( $remote_plugin_data ) ) {
return false;
}
$new_version = '1.0.0';
foreach ( $remote_plugin_data as $key => $plugin ) {
if ( $plugin_data['file'] === $plugin['slug'] ) {
$new_version = $plugin['version'];
break;
}
}
if ( version_compare( $plugin_data['version'], $new_version, '<' ) ) {
return $new_version;
}
return false;
}
/**
* Remote request to updater API.
*
* @since 1.0.0
* @return array|bool
*/
public function get_remote_jet_plugin_list() {
$remote_jet_plugin_list = get_site_transient( 'jet_dashboard_remote_jet_plugin_list' );
if ( $remote_jet_plugin_list ) {
return $remote_jet_plugin_list;
}
$query_url = add_query_arg(
array(
'action' => 'get_plugins_data',
),
Utils::get_api_url()
);
$response = wp_remote_get( $query_url );
if ( is_wp_error( $response ) || wp_remote_retrieve_response_code( $response ) != '200' ) {
return false;
}
$response = json_decode( $response['body'], true );
if ( 'error' === $response['status'] ) {
return false;
}
if ( ! isset( $response['data'] ) ) {
return false;
}
$remote_jet_plugin_list = $response['data'];
set_site_transient( 'jet_dashboard_remote_jet_plugin_list', $remote_jet_plugin_list, HOUR_IN_SECONDS * 12 );
return $remote_jet_plugin_list;
}
/**
* [get_plugin_list description]
* @return [type] [description]
*/
public function get_plugin_data_list() {
$jet_plugin_list = $this->get_remote_jet_plugin_list();
$user_plugin_list = $this->get_user_plugins();
$registered_plugins = Dashboard::get_instance()->get_registered_plugins();
$plugins_list = [];
if ( ! empty( $jet_plugin_list ) ) {
foreach ( $jet_plugin_list as $key => $plugin_data ) {
$plugin_slug = $plugin_data['slug'];
if ( array_key_exists( $plugin_slug, $user_plugin_list ) ) {
$plugin_data = wp_parse_args( $plugin_data, $user_plugin_list[ $plugin_slug ] );
} else {
$plugin_data = wp_parse_args( $plugin_data, array(
'version' => $plugin_data['version'],
'currentVersion' => $plugin_data['version'],
'updateAvaliable' => false,
'isActivated' => false,
'isInstalled' => false,
) );
}
$plugin_data['licenseControl'] = array_key_exists( $plugin_slug, $registered_plugins ) ? true : false;
$plugins_list[ $plugin_data['slug'] ] = $plugin_data;
}
}
return $plugins_list;
}
/**
* [get_plugin_data description]
* @return [type] [description]
*/
public function get_user_plugins() {
if ( ! $this->user_plugins ) {
$this->user_plugins = get_plugins();
}
$plugin_list = array();
if ( $this->user_plugins ) {
foreach ( $this->user_plugins as $plugin_file => $plugin_data ) {
$current_version = $plugin_data['Version'];
$latest_version = $this->get_latest_version( $plugin_file );
$plugin_list[ $plugin_file ] = array(
'version' => $latest_version,
'currentVersion' => $current_version,
'updateAvaliable' => version_compare( $latest_version, $current_version, '>' ),
'isActivated' => is_plugin_active( $plugin_file ),
'isInstalled' => true,
);
}
}
return $plugin_list;
}
/**
* [get_installed_plugin_data description]
* @param [type] $plugin [description]
* @return [type] [description]
*/
public function get_installed_plugin_data( $plugin_file ) {
if ( ! $this->user_plugins ) {
$this->user_plugins = get_plugins();
}
$plugin_data = $this->user_plugins[ $plugin_file ];
$current_version = $plugin_data['Version'];
$latest_version = $this->get_latest_version( $plugin_file );
return array(
'version' => $latest_version,
'currentVersion' => $current_version,
'updateAvaliable' => version_compare( $latest_version, $current_version, '>' ),
'isActivated' => is_plugin_active( $plugin_file ),
'isInstalled' => true,
);
}
/**
* Get latest version for passed plugin
*
* @param [type] $remote_plugin_data [description]
* @return [type] [description]
*/
public function get_latest_version( $plugin_file ) {
if ( ! $this->update_plugins ) {
$this->update_plugins = get_site_transient( 'update_plugins' );
}
$no_update = isset( $this->update_plugins->no_update ) ? $this->update_plugins->no_update : false;
$to_update = isset( $this->update_plugins->response ) ? $this->update_plugins->response : false;
if ( $to_update && ! empty( $to_update ) && array_key_exists( $plugin_file, $to_update ) ) {
$version = $to_update[ $plugin_file ]->new_version;
} elseif ( ! empty( $no_update ) && array_key_exists( $plugin_file, $no_update ) ) {
$version = $no_update[ $plugin_file ]->new_version;
} elseif ( array_key_exists( $plugin_file, $this->user_plugins ) ) {
$version = $this->user_plugins[ $plugin_file ]['Version'];
} else {
$version = '1.0.0';
}
return $version;
}
/**
* [install_plugin description]
* @param [type] $plugin [description]
* @param boolean $plugin_url [description]
* @return [type] [description]
*/
public function plugin_action() {
$data = ( ! empty( $_POST['data'] ) ) ? $_POST['data'] : false;
if ( ! $data ) {
wp_send_json(
array(
'status' => 'error',
'message' => $this->sys_messages['server_error']
)
);
}
$action = $data['action'];
$plugin = $data['plugin'];
switch ( $action ) {
case 'install':
$this->install_plugin( $plugin );
break;
case 'activate':
$this->activate_plugin( $plugin );
break;
case 'deactivate':
$this->deactivate_plugin( $plugin );
break;
case 'update':
$this->update_plugin( $plugin );
break;
}
wp_send_json(
array(
'status' => 'success',
'message' => 'Success',
'data' => [],
)
);
}
/**
* Perform plugin installtion by passed plugin slug and plugin package URL (optional)
*
* @param [type] $plugin [description]
* @param boolean $plugin_url [description]
* @return [type] [description]
*/
public function install_plugin( $plugin_file ) {
$status = array();
if ( ! current_user_can( 'install_plugins' ) ) {
wp_send_json(
array(
'status' => 'error',
'message' => 'Sorry, you are not allowed to install plugins on this site.'
)
);
}
if ( ! $plugin_file ) {
wp_send_json(
array(
'status' => 'error',
'message' => 'Plugin slug is required'
)
);
}
$package = Utils::package_url( $plugin_file );
include_once( ABSPATH . 'wp-admin/includes/class-wp-upgrader.php' );
include_once( ABSPATH . 'wp-admin/includes/plugin-install.php' );
$skin = new \WP_Ajax_Upgrader_Skin();
$upgrader = new \Plugin_Upgrader( $skin );
$result = $upgrader->install( $package );
if ( is_wp_error( $result ) ) {
$status['errorCode'] = $result->get_error_code();
$status['errorMessage'] = $result->get_error_message();
wp_send_json(
array(
'status' => 'error',
'message' => $result->get_error_message(),
'data' => [],
)
);
} elseif ( is_wp_error( $skin->result ) ) {
$status['errorCode'] = $skin->result->get_error_code();
$status['errorMessage'] = $skin->result->get_error_message();
wp_send_json(
array(
'status' => 'error',
'message' => $skin->result->get_error_message(),
'data' => [],
)
);
} elseif ( $skin->get_errors()->get_error_code() ) {
$status['errorMessage'] = $skin->get_error_messages();
wp_send_json(
array(
'status' => 'error',
'message' => $skin->get_error_messages(),
'data' => [],
)
);
} elseif ( is_null( $result ) ) {
global $wp_filesystem;
$status['errorMessage'] = 'Unable to connect to the filesystem. Please confirm your credentials.';
// Pass through the error from WP_Filesystem if one was raised.
if ( $wp_filesystem instanceof \WP_Filesystem_Base && is_wp_error( $wp_filesystem->errors ) && $wp_filesystem->errors->get_error_code() ) {
$status['errorMessage'] = esc_html( $wp_filesystem->errors->get_error_message() );
}
wp_send_json(
array(
'status' => 'error',
'message' => $status['errorMessage'],
'data' => [],
)
);
}
wp_send_json(
array(
'status' => 'success',
'message' => 'The plugin has been Installed',
'data' => $this->get_installed_plugin_data( $plugin_file ),
)
);
}
/**
* Performs plugin activation
*
* @param [type] $plugin [description]
* @return [type] [description]
*/
public function activate_plugin( $plugin_file ) {
$status = array();
if ( ! current_user_can( 'activate_plugins' ) ) {
wp_send_json(
array(
'status' => 'error',
'message' => 'Sorry, you are not allowed to install plugins on this site.'
)
);
}
if ( ! $plugin_file ) {
wp_send_json(
array(
'status' => 'error',
'message' => 'Plugin slug is required'
)
);
}
$activate = null;
if ( ! is_plugin_active( $plugin_file ) ) {
$activate = activate_plugin( $plugin_file );
}
if ( is_wp_error( $activate ) ) {
wp_send_json(
array(
'status' => 'error',
'message' => $activate->get_error_message(),
)
);
}
wp_send_json(
array(
'status' => 'success',
'message' => 'The plugin has been activated',
'data' => $this->get_installed_plugin_data( $plugin_file ),
)
);
}
/**
* Performs plugin activation
*
* @param [type] $plugin [description]
* @return [type] [description]
*/
public function deactivate_plugin( $plugin_file ) {
$status = array();
if ( ! current_user_can( 'activate_plugins' ) ) {
wp_send_json(
array(
'status' => 'error',
'message' => 'Sorry, you are not allowed to install plugins on this site.'
)
);
}
if ( ! $plugin_file ) {
wp_send_json(
array(
'status' => 'error',
'message' => 'Plugin slug is required'
)
);
}
$deactivate_handler = null;
if ( is_plugin_active( $plugin_file ) ) {
$deactivate_handler = deactivate_plugins( $plugin_file );
}
if ( is_wp_error( $deactivate_handler ) ) {
wp_send_json(
array(
'status' => 'error',
'message' => $deactivate_handler->get_error_message(),
)
);
}
wp_send_json(
array(
'status' => 'success',
'message' => 'The plugin has been deactivated',
'data' => $this->get_installed_plugin_data( $plugin_file ),
)
);
}
/**
* [update_plugin description]
* @param [type] $plugin_slug [description]
* @return [type] [description]
*/
public function update_plugin( $plugin_file ) {
if ( ! $plugin_file ) {
wp_send_json(
array(
'status' => 'error',
'message' => 'Plugin slug is required'
)
);
}
$plugin = plugin_basename( sanitize_text_field( wp_unslash( $plugin_file ) ) );
$slug = dirname( $plugin );
$status = array(
'update' => 'plugin',
'slug' => $slug,
'oldVersion' => '',
'newVersion' => '',
);
if ( ! current_user_can( 'update_plugins' ) || 0 !== validate_file( $plugin ) ) {
wp_send_json(
array(
'status' => 'error',
'message' => 'Sorry, you are not allowed to update plugins for this site.',
)
);
}
$plugin_data = get_plugin_data( WP_PLUGIN_DIR . '/' . $plugin );
include_once( ABSPATH . 'wp-admin/includes/class-wp-upgrader.php' );
wp_update_plugins();
$skin = new \WP_Ajax_Upgrader_Skin();
$upgrader = new \Plugin_Upgrader( $skin );
$result = $upgrader->bulk_upgrade( array( $plugin ) );
$upgrade_messages = [];
if ( defined( 'WP_DEBUG' ) && WP_DEBUG ) {
$upgrade_messages = $skin->get_upgrade_messages();
}
if ( is_wp_error( $skin->result ) ) {
wp_send_json(
array(
'status' => 'error',
'message' => $skin->result->get_error_message(),
'debug' => $upgrade_messages,
)
);
} elseif ( $skin->get_errors()->get_error_code() ) {
wp_send_json(
array(
'status' => 'error',
'message' => $skin->get_error_messages(),
'debug' => $upgrade_messages,
)
);
} elseif ( is_array( $result ) && ! empty( $result[ $plugin ] ) ) {
$plugin_update_data = current( $result );
/*
* If the `update_plugins` site transient is empty (e.g. when you update
* two plugins in quick succession before the transient repopulates),
* this may be the return.
*
* Preferably something can be done to ensure `update_plugins` isn't empty.
* For now, surface some sort of error here.
*/
if ( true === $plugin_update_data ) {
wp_send_json(
array(
'status' => 'error',
'message' => 'Plugin update failed.',
'debug' => $upgrade_messages,
)
);
}
$plugin_data = get_plugins( '/' . $result[ $plugin ]['destination_name'] );
$plugin_data = reset( $plugin_data );
wp_send_json(
array(
'status' => 'success',
'message' => 'The plugin has been updated',
'data' => $this->get_installed_plugin_data( $plugin_file ),
)
);
} elseif ( false === $result ) {
global $wp_filesystem;
$errorMessage = 'Unable to connect to the filesystem. Please confirm your credentials.';
// Pass through the error from WP_Filesystem if one was raised.
if ( $wp_filesystem instanceof \WP_Filesystem_Base && is_wp_error( $wp_filesystem->errors ) && $wp_filesystem->errors->get_error_code() ) {
$errorMessage = esc_html( $wp_filesystem->errors->get_error_message() );
}
wp_send_json(
array(
'status' => 'error',
'message' => $errorMessage,
)
);
}
wp_send_json(
array(
'status' => 'error',
'message' => 'Plugin update failed.',
)
);
}
}

View File

@@ -0,0 +1,223 @@
<?php
namespace Jet_Dashboard;
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
/**
* Define Jet_Dashboard_Utils class
*/
class Utils {
/**
* [$api_url description]
* @var string
*/
public static $api_url = 'https://api.crocoblock.com';
/**
* [$settings description]
* @var null
*/
public static $license_data = null;
/**
* [$license_data_key description]
* @var string
*/
public static $license_data_key = 'jet-license-data';
/**
* [get_api_url description]
* @return [type] [description]
*/
public static function get_api_url() {
return apply_filters( 'jet-dashboard/license/api-url', self::$api_url );
}
/**
* [get_site_url description]
* @return [type] [description]
*/
public static function get_site_url() {
$urlParts = parse_url( site_url( '/' ) );
$site_url = $urlParts['host'] . $urlParts['path'];
$site_url = preg_replace('#^https?://#', '', rtrim( $site_url ));
return $site_url;
}
/**
* [get description]
* @param [type] $setting [description]
* @param boolean $default [description]
* @return [type] [description]
*/
public static function get_license_data( $setting = false, $default = false ) {
if ( ! $setting ) {
return get_option( self::$license_data_key, array() );
}
if ( null === self::$license_data ) {
self::$license_data = get_option( self::$license_data_key, array() );
}
return isset( self::$license_data[ $setting ] ) ? self::$license_data[ $setting ] : $default;
}
/**
* [set_license_data description]
* @param [type] $setting [description]
* @param boolean $value [description]
*/
public static function set_license_data( $setting = false, $value = false ) {
$current_license_data = get_option( self::$license_data_key, array() );
$current_license_data[ $setting ] = $value;
update_option( self::$license_data_key, $current_license_data );
}
/**
* [get_license_list description]
* @return [type] [description]
*/
public static function get_license_list() {
$license_list = self::get_license_data( 'license-list', [] );
return $license_list;
}
/**
* [license_data_expire_sync description]
* @return [type] [description]
*/
public static function license_data_expire_sync() {
$license_list = self::get_license_data( 'license-list', [] );
if ( ! empty( $license_list ) ) {
foreach ( $license_list as $license_key => $license_data ) {
$license_details = $license_data['licenseDetails'];
$is_expired = ( 'expired' === $license_data['licenseStatus'] ) ? true : false;
if ( ! empty( $license_details ) ) {
$is_expired = self::license_expired_check( $license_details['expire'] );
}
if ( $is_expired ) {
$license_list[$license_key]['licenseStatus'] = 'expired';
}
}
}
self::set_license_data( 'license-list', $license_list );
}
/**
* [get_plugin_license_key description]
* @param boolean $setting [description]
* @param boolean $value [description]
* @return [type] [description]
*/
public static function get_plugin_license_key( $plugin_slug ) {
$license_list = self::get_license_data( 'license-list', [] );
$plugin_license_key = false;
if ( ! empty( $license_list ) ) {
foreach ( $license_list as $license_key => $license_data ) {
if ( 'expired' === $license_data['licenseStatus'] ) {
continue;
}
$license_details = $license_data['licenseDetails'];
if ( empty( $license_details ) ) {
continue;
}
$is_expired = self::license_expired_check( $license_details['expire'] );
if ( $is_expired ) {
$license_list[$license_key]['licenseStatus'] = 'expired';
continue;
}
$license_plugins = $license_details['plugins'];
if ( array_key_exists( $plugin_slug, $license_plugins ) ) {
$plugin_license_key = $license_key;
break;
}
}
}
if ( $plugin_license_key ) {
return $plugin_license_key;
}
return false;
}
/**
* [package_url description]
* @param [type] $key [description]
* @return [type] [description]
*/
public static function package_url( $plugin_slug = false ) {
$license_key = self::get_plugin_license_key( $plugin_slug );
if ( ! $license_key ) {
return false;
}
return add_query_arg(
array(
'action' => 'get_plugin_update',
'license' => self::get_plugin_license_key( $plugin_slug ),
'plugin' => $plugin_slug,
'site_url' => urlencode( self::get_site_url() ),
),
self::get_api_url()
);
}
/**
* [if_license_expire_check description]
* @param boolean $expire_date [description]
* @return [type] [description]
*/
public static function license_expired_check( $expire_date = false ) {
if ( '0000-00-00 00:00:00' === $expire_date || 'lifetime' === $expire_date ) {
return false;
}
$current_time = time( 'Y-m-d H:i:s' );
$expire_time = strtotime( $expire_date );
if ( $current_time > $expire_time ) {
return true;
}
return false;
}
}

View File

@@ -0,0 +1,447 @@
<?php
/**
* Jet Dashboard Module
*
* Version: 1.0.2
*/
namespace Jet_Dashboard;
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
class Dashboard {
/**
* A reference to an instance of this class.
*
* @since 1.0.0
* @access private
* @var object
*/
private static $instance = null;
/**
* Module directory path.
*
* @since 1.0.0
* @access protected
* @var srting.
*/
protected $path;
/**
* Module directory URL.
*
* @since 1.0.0
* @access protected
* @var srting.
*/
protected $url;
/**
* Module version
*
* @var string
*/
protected $version = '1.0.2';
/**
* [$dashboard_slug description]
* @var string
*/
public $dashboard_slug = 'jet-dashboard';
/**
* [$module_manager description]
* @var null
*/
public $module_manager = null;
/**
* [$license_manager description]
* @var null
*/
public $license_manager = null;
/**
* [$plugin_updater description]
* @var null
*/
public $plugin_manager = null;
/**
* [$subpage description]
* @var null
*/
private $subpage = null;
/**
* [$default_args description]
* @var [type]
*/
public $default_args = array(
'path' => '',
'url' => '',
'cx_ui_instance' => false,
'plugin_data' => array(
'slug' => false,
'version' => '',
),
);
/**
* [$cx_ui_instance description]
* @var boolean
*/
public $cx_ui_instance = false;
/**
* [$plugin_slug description]
* @var boolean
*/
public $plugin_data = false;
/**
* [$assets_enqueued description]
* @var boolean
*/
protected $assets_enqueued = false;
/**
* [$registered_plugins description]
* @var array
*/
public $registered_plugins = array();
/**
* Jet_Dashboard constructor.
*
* @since 1.0.0
* @access public
* @return void
*/
public function __construct() {
$this->load_files();
add_action( 'admin_menu', array( $this, 'register_page' ), 21 );
add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_assets' ) );
add_action( 'init', array( $this, 'init_managers' ), -998 );
add_action( 'init', array( $this, 'register_modules' ), -997 );
}
/**
* [load_files description]
* @return [type] [description]
*/
public function load_files() {
require $this->path . 'inc/utils.php';
require $this->path . 'inc/license-manager.php';
require $this->path . 'inc/plugin-manager.php';
require $this->path . 'inc/module-manager.php';
require $this->path . 'inc/modules/base.php';
require $this->path . 'inc/modules/welcome/module.php';
require $this->path . 'inc/modules/license/module.php';
}
/**
* [init description]
* @return [type] [description]
*/
public function init( $args = [] ) {
$args = wp_parse_args( $args, $this->default_args );
$this->path = ! empty( $args['path'] ) ? $args['path'] : false;
$this->url = ! empty( $args['url'] ) ? $args['url'] : false;
if ( ! $this->path || ! $this->url || ! $args['cx_ui_instance'] ) {
wp_die(
'Jet_Dashboard not initialized. Module URL, Path, UI instance and plugin data should be passed into constructor',
'Jet_Dashboard Error'
);
}
$this->cx_ui_instance = $args['cx_ui_instance'];
$this->plugin_data = $args['plugin_data'];
$this->register_plugin( $args['plugin_data']['file'], $args['plugin_data'] );
}
/**
* [init_managers description]
* @param array $args [description]
* @return [type] [description]
*/
public function init_managers() {
$this->module_manager = new Module_Manager();
$this->license_manager = new License_Manager();
$this->plugin_manager = new Plugin_Manager();
}
/**
* [register_modules description]
* @return [type] [description]
*/
public function register_modules() {
$this->module_manager->register_modules( array(
'welcome-page' => '\\Jet_Dashboard\\Modules\\Welcome\\Module',
'license-page' => '\\Jet_Dashboard\\Modules\\License\\Module',
) );
}
/**
* Register add/edit page
*
* @return void
*/
public function register_page() {
add_menu_page(
'JetPlugins',
'JetPlugins',
'manage_options',
$this->dashboard_slug,
array( $this, 'render_dashboard' ),
"data:image/svg+xml,%3Csvg width='18' height='15' viewBox='0 0 18 15' fill='none' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath d='M16.0767 0.00309188C17.6897 -0.0870077 18.6099 1.81257 17.5381 3.02007L7.99824 13.7682C6.88106 15.0269 4.79904 14.2223 4.82092 12.5403L4.87766 8.17935C4.88509 7.60797 4.62277 7.06644 4.16961 6.71768L0.710961 4.05578C-0.623014 3.02911 0.0373862 0.899003 1.71878 0.805085L16.0767 0.00309188Z' fill='white'/%3E%3C/svg%3E%0A",
59
);
add_submenu_page(
'jet-dashboard',
esc_html__( 'Dashboard', 'jet-tricks' ),
esc_html__( 'Dashboard', 'jet-tricks' ),
'manage_options',
'jet-dashboard'
);
}
/**
* Render installation wizard page
*
* @return void
*/
public function render_dashboard() {
include $this->get_view( 'common/dashboard' );
}
/**
* Enqueue builder assets
*
* @return void
*/
public function enqueue_assets( $hook ) {
if ( 'toplevel_page_' . $this->dashboard_slug !== $hook ) {
return;
}
if ( $this->assets_enqueued ) {
return;
}
$this->cx_ui_instance->enqueue_assets();
/**
* Fires before enqueue page assets
*/
do_action( 'jet-dashboard/before-enqueue-assets', $this );
/**
* Fires before enqueue page assets with dynamic subpage name
*/
do_action( 'jet-dashboard/before-enqueue-assets/' . $this->get_subpage(), $this );
wp_enqueue_style(
'jet-dashboard-admin-css',
$this->url . 'assets/css/jet-dashboard-admin.css',
false,
$this->version
);
wp_enqueue_script(
'jet-dashboard-script',
$this->url . 'assets/js/jet-dashboard.js',
array( 'cx-vue-ui' ),
$this->version,
true
);
wp_localize_script(
'jet-dashboard-script',
'JetDashboardPageConfig',
apply_filters( 'jet-dashboard/js-page-config', array(
'headerTitle' => '',
'mainPage' => $this->get_dashboard_page_url( $this->get_initial_page() ),
'page' => false,
'module' => $this->get_subpage(),
'nonce' => wp_create_nonce( $this->dashboard_slug ),
'ajaxUrl' => esc_url( admin_url( 'admin-ajax.php' ) ),
'licenseList' => array_values( Utils::get_license_list() ),
'allJetPlugins' => $this->plugin_manager->get_plugin_data_list(),
) )
);
add_action( 'admin_footer', array( $this, 'print_vue_templates' ), 0 );
$this->assets_enqueued = true;
}
/**
* Print components templates
*
* @return void
*/
public function print_vue_templates() {
$templates = apply_filters(
'jet-dashboard/js-page-templates',
array(
'header' => 'common/header',
),
$this->get_subpage()
);
foreach ( $templates as $name => $path ) {
ob_start();
include $this->get_view( $path );
$content = ob_get_clean();
printf(
'<script type="text/x-template" id="jet-dashboard-%1$s">%2$s</script>',
$name,
$content
);
}
}
/**
* [get_registered_plugins description]
* @return [type] [description]
*/
public function get_registered_plugins() {
return $this->registered_plugins;
}
/**
* [get_registered_plugins description]
* @return [type] [description]
*/
public function register_plugin( $plugin_slug = false, $plugin_data = array() ) {
if ( ! array_key_exists( $plugin_slug, $this->registered_plugins ) ) {
$this->registered_plugins[ $plugin_slug ] = $plugin_data;
}
return false;
}
/**
* [get_dashboard_version description]
* @return [type] [description]
*/
public function get_dashboard_path() {
return $this->path;
}
/**
* [get_dashboard_version description]
* @return [type] [description]
*/
public function get_dashboard_url() {
return $this->url;
}
/**
* [get_dashboard_version description]
* @return [type] [description]
*/
public function get_dashboard_version() {
return $this->version;
}
/**
* Returns path to view file
*
* @param [type] $path [description]
* @return [type] [description]
*/
public function get_view( $path ) {
return apply_filters( 'jet-dashboard/get-view', $this->path . 'views/' . $path . '.php' );
}
/**
* Returns current subpage slug
*
* @return string
*/
public function get_subpage() {
if ( null === $this->subpage ) {
$this->subpage = isset( $_GET['sub'] ) ? esc_attr( $_GET['sub'] ) : $this->get_initial_page();
}
return $this->subpage;
}
/**
* Returns wizard initial subpage
*
* @return string
*/
public function get_initial_page() {
return 'license-page';
}
/**
* Check if dashboard page is currently displayiing
*
* @return boolean [description]
*/
public function is_dashboard_page() {
return ( ! empty( $_GET['page'] ) && $this->dashboard_slug === $_GET['page'] );
}
/**
* [get_admin_url description]
* @return [type] [description]
*/
public function get_dashboard_page_url( $subpage = null, $args = array() ) {
$page_args = array(
'page' => $this->dashboard_slug,
'sub' => $subpage,
);
if ( ! empty( $args ) ) {
$page_args = array_merge( $page_args, $args );
}
return add_query_arg( $page_args, admin_url( 'admin.php' ) );
}
/**
* Returns the instance.
*
* @since 1.0.0
* @access public
* @return object
*/
public static function get_instance() {
// If the single instance hasn't been set, set it now.
if ( null == self::$instance ) {
self::$instance = new self;
}
return self::$instance;
}
}

View File

@@ -0,0 +1,30 @@
{
"name": "gulp-tasks",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"repository": {
"type": "git",
"url": "git+https://github.com/ZemezLab/jet-tabs.git"
},
"author": "Shin",
"license": "ISC",
"bugs": {
"url": "https://github.com/ZemezLab/jet-tabs/issues"
},
"homepage": "https://github.com/ZemezLab/jet-tabs#readme",
"devDependencies": {
"gulp": "^4.0.2",
"gulp-autoprefixer": "^4.1.0",
"gulp-notify": "^3.2.0",
"gulp-plumber": "^1.2.1",
"gulp-rename": "^1.4.0",
"gulp-sass": "^4.0.2"
},
"dependencies": {
"gulp-checktextdomain": "^2.2.0"
}
}

View File

@@ -0,0 +1,12 @@
<?php
/**
* Main dashboard template
*/
?><div id="jet-dashboard-page" class="jet-dashboard-page">
<jet-dashboard-header></jet-dashboard-header>
<div class="jet-dashboard-page__content">
<component
:is="page"
></component>
</div>
</div>

View File

@@ -0,0 +1,48 @@
<div class="jet-dashboard-page__header">
<h1 class="header-title">{{ title }}</h1>
<svg class="header-bg" width="470" height="171" viewBox="0 0 470 171" fill="none" xmlns="http://www.w3.org/2000/svg">
<path opacity="0.1" d="M439.752 24.3614C439.752 28.0668 436.738 31.0802 433.033 31.0802C428.725 31.0802 428.167 28.223 425.801 28.223C424.685 28.223 422.564 28.5355 422.564 31.0355V50.0533H403.546C401.046 50.0533 400.734 47.9327 400.734 46.8167C400.734 44.4506 403.591 43.8926 403.591 39.5846C403.591 35.8792 400.578 32.8659 396.872 32.8659C393.167 32.8659 390.154 35.8792 390.154 39.5846C390.154 43.8926 393.011 44.4506 393.011 46.8167C393.011 47.9327 392.721 50.0533 390.198 50.0533H371.181V31.0355C371.181 28.5355 369.06 28.223 367.944 28.223C365.578 28.223 365.02 31.0802 360.712 31.0802C357.007 31.0802 353.993 28.0668 353.993 24.3614C353.993 20.6561 357.007 17.6427 360.712 17.6427C365.02 17.6427 365.578 20.4999 367.944 20.4999C369.06 20.4999 371.181 20.1874 371.181 17.6874V-1.33036H422.564V17.6874C422.564 20.1874 424.685 20.4999 425.801 20.4999C428.167 20.4999 428.725 17.6427 433.033 17.6427C436.738 17.6204 439.752 20.6338 439.752 24.3614Z" fill="#4FA4D8"/>
<path opacity="0.4" d="M423.234 50.7006H403.546C401.381 50.7006 400.064 49.2497 400.064 46.7943C400.064 45.5667 400.689 44.7408 401.314 43.9372C402.095 42.8881 402.921 41.8167 402.921 39.5846C402.921 36.2587 400.198 33.5355 396.872 33.5355C393.546 33.5355 390.823 36.2587 390.823 39.5846C390.823 41.839 391.649 42.9104 392.43 43.9595C393.033 44.7631 393.68 45.589 393.68 46.8167C393.68 49.272 392.385 50.7229 390.198 50.7229H370.511V31.0355C370.511 30.4998 370.511 28.8927 367.944 28.8927C367.162 28.8927 366.627 29.2945 365.89 29.8748C364.796 30.723 363.412 31.7498 360.712 31.7498C356.627 31.7498 353.323 28.4462 353.323 24.3615C353.323 20.2767 356.627 16.9731 360.712 16.9731C363.412 16.9731 364.796 18.0222 365.89 18.8481C366.627 19.4061 367.162 19.8302 367.944 19.8302C370.511 19.8302 370.511 18.2231 370.511 17.6874V-2H423.234V17.6874C423.234 18.2231 423.234 19.8302 425.8 19.8302C426.582 19.8302 427.117 19.4284 427.854 18.8481C428.948 17.9999 430.332 16.9731 433.033 16.9731C437.095 16.9731 440.421 20.299 440.421 24.3615C440.421 28.4462 437.117 31.7498 433.033 31.7498C430.332 31.7498 428.948 30.7007 427.854 29.8748C427.117 29.3168 426.582 28.8927 425.8 28.8927C423.234 28.8927 423.234 30.4998 423.234 31.0355V50.7006ZM396.872 32.1739C400.957 32.1739 404.26 35.4775 404.26 39.5623C404.26 42.2631 403.211 43.6471 402.385 44.7408C401.827 45.4774 401.403 46.0131 401.403 46.7943C401.403 49.3613 403.01 49.3613 403.546 49.3613H421.894V31.0132C421.894 28.8257 423.345 27.5311 425.8 27.5311C427.028 27.5311 427.854 28.1561 428.658 28.7811C429.707 29.5623 430.778 30.3882 433.033 30.3882C436.358 30.3882 439.082 27.665 439.082 24.3391C439.082 21.0133 436.358 18.2901 433.033 18.2901C430.778 18.2901 429.707 19.1159 428.658 19.8972C427.854 20.4999 427.028 21.1472 425.8 21.1472C423.345 21.1472 421.894 19.8526 421.894 17.6651V-0.660722H371.85V17.6874C371.85 19.8525 370.399 21.1695 367.944 21.1695C366.716 21.1695 365.89 20.5445 365.087 19.9195C364.037 19.1383 362.966 18.3124 360.712 18.3124C357.386 18.3124 354.663 21.0356 354.663 24.3615C354.663 27.6873 357.386 30.4105 360.712 30.4105C362.966 30.4105 364.037 29.5846 365.087 28.8034C365.89 28.2007 366.716 27.5534 367.944 27.5534C370.399 27.5534 371.85 28.848 371.85 31.0355V49.3836H390.198C390.734 49.3836 392.341 49.3836 392.341 46.8167C392.341 46.0354 391.939 45.4997 391.359 44.7631C390.511 43.6694 389.484 42.2854 389.484 39.5846C389.484 35.4998 392.787 32.1739 396.872 32.1739Z" fill="#4EFEC3"/>
<path opacity="0.8" d="M319.798 101.415V82.3969C319.798 79.8969 317.677 79.5844 316.561 79.5844C314.195 79.5844 313.637 82.4415 309.329 82.4415C305.624 82.4415 302.61 79.4281 302.61 75.7228C302.61 72.0175 305.624 69.0041 309.329 69.0041C313.637 69.0041 314.195 71.8612 316.561 71.8612C317.677 71.8612 319.798 71.571 319.798 69.0487V50.031H338.815C341.315 50.031 341.628 52.1515 341.628 53.2676C341.628 55.6336 338.771 56.1917 338.771 60.4997C338.771 64.205 341.784 67.2184 345.49 67.2184C349.195 67.2184 352.208 64.205 352.208 60.4997C352.208 56.1917 349.351 55.6336 349.351 53.2676C349.351 52.1515 349.641 50.031 352.164 50.031H371.181V69.0487C371.181 71.5487 373.302 71.8612 374.418 71.8612C376.784 71.8612 377.342 69.0041 381.65 69.0041C385.355 69.0041 388.369 72.0175 388.369 75.7228C388.369 79.4281 385.355 82.4415 381.65 82.4415C377.342 82.4415 376.784 79.5844 374.418 79.5844C373.302 79.5844 371.181 79.8745 371.181 82.3969V101.415H352.164C349.664 101.415 349.351 99.2941 349.351 98.178C349.351 95.812 352.208 95.2539 352.208 90.9459C352.208 87.2406 349.195 84.2272 345.49 84.2272C341.784 84.2272 338.771 87.2406 338.771 90.9459C338.771 95.2539 341.628 95.812 341.628 98.178C341.628 99.2941 341.338 101.415 338.815 101.415H319.798Z" fill="#4FA4D8"/>
<path opacity="0.4" d="M371.851 102.084H352.163C349.998 102.084 348.681 100.633 348.681 98.178C348.681 96.9503 349.306 96.1244 349.931 95.3209C350.712 94.2718 351.538 93.2004 351.538 90.9459C351.538 87.62 348.815 84.8968 345.489 84.8968C342.163 84.8968 339.44 87.62 339.44 90.9459C339.44 93.2004 340.266 94.2718 341.047 95.3209C341.65 96.1244 342.297 96.9503 342.297 98.178C342.297 100.633 341.003 102.084 338.815 102.084H319.128V82.3968C319.128 81.8611 319.128 80.254 316.561 80.254C315.78 80.254 315.244 80.6558 314.507 81.2361C313.414 82.0844 312.03 83.1111 309.329 83.1111C305.266 83.1111 301.94 79.7853 301.94 75.7228C301.94 71.638 305.244 68.3344 309.329 68.3344C312.03 68.3344 313.414 69.3835 314.507 70.2094C315.244 70.7675 315.78 71.1916 316.561 71.1916C319.128 71.1916 319.128 69.5844 319.128 69.0487V49.3613H338.815C340.98 49.3613 342.297 50.8122 342.297 53.2676C342.297 54.4952 341.672 55.3211 341.047 56.1247C340.266 57.1738 339.44 58.2452 339.44 60.4997C339.44 63.8255 342.163 66.5487 345.489 66.5487C348.815 66.5487 351.538 63.8255 351.538 60.4997C351.538 58.2452 350.712 57.1738 349.931 56.1247C349.329 55.3211 348.681 54.4952 348.681 53.2676C348.681 50.8122 349.976 49.3613 352.163 49.3613H371.851V69.0487C371.851 69.5844 371.851 71.1916 374.418 71.1916C375.199 71.1916 375.735 70.7898 376.471 70.2094C377.565 69.3612 378.949 68.3344 381.65 68.3344C385.712 68.3344 389.038 71.6603 389.038 75.7228C389.038 79.8076 385.735 83.1111 381.65 83.1111C378.949 83.1111 377.565 82.062 376.471 81.2361C375.735 80.6781 375.199 80.254 374.418 80.254C371.851 80.254 371.851 81.8611 371.851 82.3968V102.084ZM345.489 83.5576C349.574 83.5576 352.878 86.8611 352.878 90.9459C352.878 93.6468 351.829 95.0307 351.003 96.1244C350.445 96.861 350.02 97.3968 350.02 98.178C350.02 100.745 351.628 100.745 352.163 100.745H370.511V82.3968C370.511 80.2317 371.962 78.9147 374.418 78.9147C375.645 78.9147 376.471 79.5397 377.275 80.1647C378.324 80.946 379.395 81.7719 381.65 81.7719C384.976 81.7719 387.699 79.0487 387.699 75.7228C387.699 72.3969 384.976 69.6737 381.65 69.6737C379.395 69.6737 378.324 70.4996 377.275 71.2808C376.471 71.8835 375.645 72.5308 374.418 72.5308C371.962 72.5308 370.511 71.2362 370.511 69.0487V50.7006H352.163C351.628 50.7006 350.02 50.7006 350.02 53.2676C350.02 54.0488 350.422 54.5845 351.003 55.3211C351.851 56.4149 352.878 57.7988 352.878 60.4997C352.878 64.5621 349.552 67.888 345.489 67.888C341.427 67.888 338.101 64.5845 338.101 60.4997C338.101 57.7988 339.15 56.4149 339.976 55.3211C340.534 54.5845 340.958 54.0488 340.958 53.2676C340.958 50.7006 339.351 50.7006 338.815 50.7006H320.467V69.0487C320.467 71.2139 319.016 72.5308 316.561 72.5308C315.333 72.5308 314.507 71.9058 313.704 71.2808C312.655 70.4996 311.583 69.6737 309.329 69.6737C306.003 69.6737 303.28 72.3969 303.28 75.7228C303.28 79.0487 306.003 81.7719 309.329 81.7719C311.583 81.7719 312.655 80.946 313.704 80.1647C314.507 79.562 315.333 78.9147 316.561 78.9147C319.016 78.9147 320.467 80.2094 320.467 82.3968V100.745H338.815C339.351 100.745 340.958 100.745 340.958 98.178C340.958 97.3968 340.556 96.861 339.976 96.1244C339.128 95.0307 338.101 93.6468 338.101 90.9459C338.101 86.8834 341.427 83.5576 345.489 83.5576Z" fill="#4EFEC3"/>
<path opacity="0.5" d="M405.378 75.7228C405.378 79.4281 408.391 82.4415 412.097 82.4415C416.405 82.4415 416.963 79.5844 419.329 79.5844C420.445 79.5844 422.565 79.8745 422.565 82.3968V101.415H403.548C401.048 101.415 400.735 103.535 400.735 104.651C400.735 107.017 403.592 107.575 403.592 111.883C403.592 115.589 400.579 118.602 396.873 118.602C393.168 118.602 390.155 115.589 390.155 111.883C390.155 107.575 393.012 107.017 393.012 104.651C393.012 103.535 392.722 101.415 390.199 101.415H371.182V82.3968C371.182 79.8969 373.302 79.5844 374.418 79.5844C376.784 79.5844 377.342 82.4415 381.65 82.4415C385.356 82.4415 388.369 79.4281 388.369 75.7228C388.369 72.0174 385.356 69.0041 381.65 69.0041C377.342 69.0041 376.784 71.8612 374.418 71.8612C373.302 71.8612 371.182 71.5487 371.182 69.0487V50.031H390.199C392.699 50.031 393.012 47.9104 393.012 46.7944C393.012 44.4283 390.155 43.8703 390.155 39.5623C390.155 35.8569 393.168 32.8436 396.873 32.8436C400.579 32.8436 403.592 35.8569 403.592 39.5623C403.592 43.8703 400.735 44.4283 400.735 46.7944C400.735 47.9104 401.048 50.031 403.548 50.031H422.565V69.0487C422.565 71.5487 420.445 71.8612 419.329 71.8612C416.963 71.8612 416.405 69.0041 412.097 69.0041C408.369 69.0041 405.378 72.0174 405.378 75.7228Z" fill="#4FA4D8"/>
<path opacity="0.4" d="M396.874 119.272C392.789 119.272 389.486 115.968 389.486 111.883C389.486 109.182 390.535 107.798 391.361 106.705C391.919 105.968 392.343 105.432 392.343 104.651C392.343 102.084 390.736 102.084 390.2 102.084H370.513V82.3969C370.513 80.2317 371.964 78.9147 374.419 78.9147C375.647 78.9147 376.472 79.5397 377.276 80.1647C378.325 80.946 379.397 81.7719 381.651 81.7719C384.977 81.7719 387.7 79.0487 387.7 75.7228C387.7 72.3969 384.977 69.6737 381.651 69.6737C379.397 69.6737 378.325 70.4996 377.276 71.2808C376.472 71.8835 375.647 72.5308 374.419 72.5308C371.964 72.5308 370.513 71.2362 370.513 69.0487V49.3613H390.2C390.736 49.3613 392.343 49.3613 392.343 46.7944C392.343 46.0131 391.941 45.4774 391.361 44.7408C390.513 43.6471 389.486 42.2632 389.486 39.5623C389.486 35.4775 392.789 32.1739 396.874 32.1739C400.959 32.1739 404.262 35.4775 404.262 39.5623C404.262 42.2632 403.213 43.6471 402.388 44.7408C401.829 45.4774 401.405 46.0131 401.405 46.7944C401.405 49.3613 403.013 49.3613 403.548 49.3613H423.236V69.0487C423.236 71.2139 421.785 72.5308 419.329 72.5308C418.102 72.5308 417.276 71.9058 416.472 71.2808C415.423 70.4996 414.352 69.6737 412.097 69.6737C408.771 69.6737 406.048 72.3969 406.048 75.7228C406.048 79.0487 408.771 81.7719 412.097 81.7719C414.352 81.7719 415.423 80.946 416.472 80.1647C417.276 79.562 418.102 78.9147 419.329 78.9147C421.785 78.9147 423.236 80.2094 423.236 82.3969V102.084H403.548C403.013 102.084 401.405 102.084 401.405 104.651C401.405 105.432 401.807 105.968 402.388 106.705C403.236 107.798 404.262 109.182 404.262 111.883C404.262 115.968 400.937 119.272 396.874 119.272ZM371.852 100.745H390.2C392.365 100.745 393.682 102.196 393.682 104.651C393.682 105.879 393.057 106.705 392.432 107.508C391.651 108.557 390.825 109.629 390.825 111.883C390.825 115.209 393.548 117.932 396.874 117.932C400.2 117.932 402.923 115.209 402.923 111.883C402.923 109.629 402.097 108.557 401.316 107.508C400.713 106.705 400.066 105.879 400.066 104.651C400.066 102.196 401.361 100.745 403.548 100.745H421.896V82.3969C421.896 81.8611 421.896 80.254 419.329 80.254C418.548 80.254 418.012 80.6558 417.276 81.2361C416.182 82.0844 414.798 83.1111 412.097 83.1111C408.012 83.1111 404.709 79.8076 404.709 75.7228C404.709 71.638 408.012 68.3344 412.097 68.3344C414.798 68.3344 416.182 69.3835 417.276 70.2094C418.012 70.7675 418.548 71.1916 419.329 71.1916C421.896 71.1916 421.896 69.5844 421.896 69.0487V50.7006H403.548C401.383 50.7006 400.066 49.2497 400.066 46.7944C400.066 45.5667 400.691 44.7408 401.316 43.9373C402.097 42.8882 402.923 41.8167 402.923 39.5846C402.923 36.2587 400.2 33.5355 396.874 33.5355C393.548 33.5355 390.825 36.2587 390.825 39.5846C390.825 41.8391 391.651 42.9105 392.432 43.9596C393.035 44.7631 393.682 45.589 393.682 46.8167C393.682 49.272 392.388 50.7229 390.2 50.7229H371.852V69.071C371.852 69.6068 371.852 71.2139 374.419 71.2139C375.2 71.2139 375.736 70.8121 376.472 70.2317C377.566 69.3835 378.95 68.3568 381.651 68.3568C385.736 68.3568 389.039 71.6826 389.039 75.7451C389.039 79.8299 385.736 83.1335 381.651 83.1335C378.95 83.1335 377.566 82.0844 376.472 81.2585C375.736 80.7004 375.2 80.2763 374.419 80.2763C371.852 80.2763 371.852 81.8835 371.852 82.4192V100.745Z" fill="#4EFEC3"/>
<path opacity="0.4" d="M491.113 75.7228C491.113 79.4281 488.1 82.4415 484.394 82.4415C480.086 82.4415 479.528 79.5844 477.162 79.5844C476.046 79.5844 473.926 79.8745 473.926 82.3969V101.415H454.908C452.408 101.415 452.095 99.2941 452.095 98.178C452.095 95.812 454.952 95.2539 454.952 90.9459C454.952 87.2406 451.939 84.2272 448.234 84.2272C444.528 84.2272 441.515 87.2406 441.515 90.9459C441.515 95.2539 444.372 95.812 444.372 98.178C444.372 99.2941 444.06 101.415 441.56 101.415H422.542V82.3969C422.542 79.8969 420.421 79.5844 419.305 79.5844C416.939 79.5844 416.381 82.4415 412.073 82.4415C408.368 82.4415 405.354 79.4281 405.354 75.7228C405.354 72.0175 408.368 69.0041 412.073 69.0041C416.381 69.0041 416.939 71.8612 419.305 71.8612C420.421 71.8612 422.542 71.5487 422.542 69.0487V50.031H441.56C444.06 50.031 444.372 52.1515 444.372 53.2676C444.372 55.6336 441.515 56.1917 441.515 60.4997C441.515 64.205 444.528 67.2184 448.234 67.2184C451.939 67.2184 454.952 64.205 454.952 60.4997C454.952 56.1917 452.095 55.6336 452.095 53.2676C452.095 52.1515 452.408 50.031 454.908 50.031H473.926V69.0487C473.926 71.5487 476.046 71.8612 477.162 71.8612C479.528 71.8612 480.086 69.0041 484.394 69.0041C488.122 69.0041 491.113 72.0175 491.113 75.7228Z" fill="#4FA4D8"/>
<path opacity="0.4" d="M474.595 102.084H454.907C452.742 102.084 451.425 100.633 451.425 98.178C451.425 96.9503 452.05 96.1244 452.675 95.3209C453.457 94.2718 454.283 93.2004 454.283 90.9459C454.283 87.62 451.559 84.8968 448.233 84.8968C444.908 84.8968 442.184 87.62 442.184 90.9459C442.184 93.2004 443.01 94.2718 443.792 95.3209C444.394 96.1244 445.041 96.9503 445.041 98.178C445.041 100.633 443.747 102.084 441.559 102.084H421.872V82.3968C421.872 81.8611 421.872 80.254 419.305 80.254C418.524 80.254 417.988 80.6558 417.251 81.2361C416.158 82.0844 414.774 83.1111 412.073 83.1111C407.988 83.1111 404.685 79.8076 404.685 75.7228C404.685 71.638 407.988 68.3344 412.073 68.3344C414.774 68.3344 416.158 69.3835 417.251 70.2094C417.988 70.7675 418.524 71.1916 419.305 71.1916C421.872 71.1916 421.872 69.5844 421.872 69.0487V49.3613H441.559C443.725 49.3613 445.041 50.8122 445.041 53.2676C445.041 54.4952 444.416 55.3211 443.792 56.1247C443.01 57.1738 442.184 58.2452 442.184 60.4997C442.184 63.8255 444.908 66.5487 448.233 66.5487C451.582 66.5487 454.283 63.8255 454.283 60.4997C454.283 58.2452 453.457 57.1738 452.675 56.1247C452.073 55.3211 451.425 54.4952 451.425 53.2676C451.425 50.8122 452.72 49.3613 454.907 49.3613H474.595V69.0487C474.595 69.5844 474.595 71.1916 477.162 71.1916C477.943 71.1916 478.479 70.7898 479.215 70.2094C480.309 69.3612 481.693 68.3344 484.394 68.3344C488.456 68.3344 491.782 71.6603 491.782 75.7228C491.782 79.8076 488.479 83.1111 484.394 83.1111C481.693 83.1111 480.309 82.062 479.215 81.2361C478.479 80.6781 477.943 80.254 477.162 80.254C474.595 80.254 474.595 81.8611 474.595 82.3968V102.084ZM448.256 83.5576C452.341 83.5576 455.644 86.8611 455.644 90.9459C455.644 93.6468 454.595 95.0307 453.769 96.1244C453.211 96.861 452.787 97.3968 452.787 98.178C452.787 100.745 454.394 100.745 454.93 100.745H473.278V82.3968C473.278 80.2317 474.729 78.9147 477.184 78.9147C478.412 78.9147 479.238 79.5397 480.041 80.1647C481.09 80.946 482.162 81.7719 484.416 81.7719C487.742 81.7719 490.465 79.0487 490.465 75.7228C490.465 72.3969 487.742 69.6737 484.416 69.6737C482.162 69.6737 481.09 70.4996 480.041 71.2808C479.238 71.8835 478.412 72.5308 477.184 72.5308C474.729 72.5308 473.278 71.2362 473.278 69.0487V50.7006H454.93C454.394 50.7006 452.787 50.7006 452.787 53.2676C452.787 54.0488 453.189 54.5845 453.769 55.3211C454.617 56.4149 455.644 57.7988 455.644 60.4997C455.644 64.5845 452.318 67.888 448.256 67.888C444.171 67.888 440.867 64.5845 440.867 60.4997C440.867 57.7988 441.916 56.4149 442.742 55.3211C443.3 54.5845 443.725 54.0488 443.725 53.2676C443.725 50.7006 442.117 50.7006 441.582 50.7006H423.234V69.0487C423.234 71.2139 421.783 72.5308 419.327 72.5308C418.1 72.5308 417.274 71.9058 416.47 71.2808C415.421 70.4996 414.35 69.6737 412.095 69.6737C408.769 69.6737 406.046 72.3969 406.046 75.7228C406.046 79.0487 408.769 81.7719 412.095 81.7719C414.35 81.7719 415.421 80.946 416.47 80.1647C417.274 79.562 418.1 78.9147 419.327 78.9147C421.783 78.9147 423.234 80.2094 423.234 82.3968V100.745H441.582C442.117 100.745 443.725 100.745 443.725 98.178C443.725 97.3968 443.323 96.861 442.742 96.1244C441.894 95.0307 440.867 93.6468 440.867 90.9459C440.867 86.8834 444.171 83.5576 448.256 83.5576Z" fill="#4EFEC3"/>
<path opacity="0.4" d="M448.258 67.888C444.173 67.888 440.87 64.5844 440.87 60.4996C440.87 57.7988 441.919 56.4148 442.745 55.3211C443.303 54.5845 443.727 54.0488 443.727 53.2675C443.727 50.7006 442.12 50.7006 441.584 50.7006H421.896V31.0132C421.896 28.8257 423.347 27.5311 425.803 27.5311C427.03 27.5311 427.856 28.1561 428.66 28.7811C429.709 29.5623 430.78 30.3882 433.035 30.3882C436.361 30.3882 439.084 27.665 439.084 24.3391C439.084 21.0133 436.361 18.2901 433.035 18.2901C430.78 18.2901 429.709 19.1159 428.66 19.8972C427.856 20.4999 427.03 21.1472 425.803 21.1472C423.347 21.1472 421.896 19.8526 421.896 17.6651V-2H474.619V17.6874C474.619 19.8525 473.169 21.1695 470.713 21.1695C469.486 21.1695 468.66 20.5445 467.856 19.9195C466.807 19.1383 465.736 18.3124 463.481 18.3124C460.155 18.3124 457.432 21.0356 457.432 24.3615C457.432 27.6873 460.155 30.4105 463.481 30.4105C465.736 30.4105 466.807 29.5846 467.856 28.8034C468.66 28.2007 469.486 27.5534 470.713 27.5534C473.169 27.5534 474.619 28.848 474.619 31.0355V50.7229H454.932C454.396 50.7229 452.789 50.7229 452.789 53.2898C452.789 54.0711 453.191 54.6068 453.771 55.3434C454.62 56.4371 455.646 57.8211 455.646 60.5219C455.646 64.5844 452.32 67.888 448.258 67.888ZM423.236 49.3613H441.584C443.749 49.3613 445.066 50.8122 445.066 53.2675C445.066 54.4952 444.441 55.3211 443.816 56.1247C443.035 57.1738 442.209 58.2452 442.209 60.4996C442.209 63.8255 444.932 66.5487 448.258 66.5487C451.606 66.5487 454.307 63.8255 454.307 60.4996C454.307 58.2452 453.481 57.1738 452.7 56.1247C452.097 55.3211 451.45 54.4952 451.45 53.2675C451.45 50.8122 452.745 49.3613 454.932 49.3613H473.28V31.0132C473.28 30.4775 473.28 28.8704 470.713 28.8704C469.932 28.8704 469.396 29.2721 468.66 29.8525C467.566 30.7007 466.182 31.7275 463.481 31.7275C459.419 31.7275 456.093 28.4239 456.093 24.3391C456.093 20.2543 459.396 16.9508 463.481 16.9508C466.182 16.9508 467.566 17.9999 468.66 18.8258C469.396 19.3838 469.932 19.8079 470.713 19.8079C473.28 19.8079 473.28 18.2008 473.28 17.6651V-0.660722H423.236V17.6874C423.236 18.2231 423.236 19.8302 425.803 19.8302C426.584 19.8302 427.12 19.4284 427.856 18.8481C428.95 17.9999 430.334 16.9731 433.035 16.9731C437.097 16.9731 440.423 20.299 440.423 24.3615C440.423 28.4462 437.12 31.7498 433.035 31.7498C430.334 31.7498 428.95 30.7007 427.856 29.8748C427.12 29.3168 426.584 28.8927 425.803 28.8927C423.236 28.8927 423.236 30.4998 423.236 31.0355V49.3613Z" fill="#4EFEC3"/>
<path opacity="0.5" d="M353.994 127.106C353.994 130.812 357.007 133.825 360.713 133.825C365.021 133.825 365.579 130.968 367.945 130.968C369.061 130.968 371.181 131.258 371.181 133.78V152.798H352.164C351.226 152.798 350.601 153.088 350.177 153.535C349.485 154.249 349.351 155.343 349.351 156.035C349.351 158.401 352.208 158.959 352.208 163.267C352.208 166.972 349.195 169.986 345.49 169.986C341.784 169.986 338.771 166.972 338.771 163.267C338.771 158.959 341.628 158.401 341.628 156.035C341.628 155.343 341.516 154.249 340.802 153.535C340.378 153.111 339.753 152.798 338.816 152.798H319.798V133.78C319.798 131.28 321.918 130.968 323.034 130.968C325.4 130.968 325.959 133.825 330.267 133.825C333.972 133.825 336.985 130.812 336.985 127.106C336.985 123.401 333.972 120.388 330.267 120.388C325.959 120.388 325.4 123.245 323.034 123.245C321.918 123.245 319.798 122.932 319.798 120.432V101.415H338.816C341.316 101.415 341.628 99.294 341.628 98.178C341.628 95.8119 338.771 95.2539 338.771 90.9459C338.771 87.2405 341.784 84.2272 345.49 84.2272C349.195 84.2272 352.208 87.2405 352.208 90.9459C352.208 95.2539 349.351 95.8119 349.351 98.178C349.351 99.294 349.664 101.415 352.164 101.415H371.181V120.432C371.181 122.932 369.061 123.245 367.945 123.245C365.579 123.245 365.021 120.388 360.713 120.388C357.007 120.388 353.994 123.401 353.994 127.106Z" fill="#4FA4D8"/>
<path opacity="0.4" d="M345.49 170.655C341.406 170.655 338.102 167.352 338.102 163.267C338.102 160.566 339.151 159.182 339.977 158.088C340.535 157.352 340.959 156.816 340.959 156.035C340.959 155.41 340.848 154.539 340.334 154.004C339.999 153.646 339.486 153.468 338.816 153.468H319.129V133.78C319.129 131.615 320.58 130.298 323.035 130.298C324.263 130.298 325.089 130.923 325.892 131.548C326.941 132.33 328.013 133.155 330.267 133.155C333.593 133.155 336.316 130.432 336.316 127.106C336.316 123.781 333.593 121.057 330.267 121.057C328.013 121.057 326.941 121.883 325.892 122.664C325.089 123.267 324.263 123.914 323.035 123.914C320.58 123.914 319.129 122.62 319.129 120.432V100.745H338.816C339.352 100.745 340.959 100.745 340.959 98.178C340.959 97.3967 340.557 96.861 339.977 96.1244C339.129 95.0307 338.102 93.6468 338.102 90.9459C338.102 86.8611 341.406 83.5575 345.49 83.5575C349.575 83.5575 352.879 86.8611 352.879 90.9459C352.879 93.6468 351.83 95.0307 351.004 96.1244C350.446 96.861 350.022 97.3967 350.022 98.178C350.022 100.745 351.629 100.745 352.164 100.745H371.852V120.432C371.852 122.597 370.401 123.914 367.946 123.914C366.718 123.914 365.892 123.289 365.088 122.664C364.039 121.883 362.968 121.057 360.713 121.057C357.388 121.057 354.664 123.781 354.664 127.106C354.664 130.432 357.388 133.155 360.713 133.155C362.968 133.155 364.039 132.33 365.088 131.548C365.892 130.946 366.718 130.298 367.946 130.298C370.401 130.298 371.852 131.593 371.852 133.78V153.468H352.164C351.495 153.468 351.004 153.646 350.669 154.004C350.156 154.539 350.044 155.41 350.044 156.035C350.044 156.816 350.446 157.352 351.026 158.088C351.874 159.182 352.901 160.566 352.901 163.267C352.879 167.329 349.575 170.655 345.49 170.655ZM320.468 152.129H338.816C339.843 152.129 340.691 152.441 341.294 153.066C341.941 153.736 342.298 154.762 342.298 156.035C342.298 157.262 341.673 158.088 341.048 158.892C340.267 159.941 339.441 161.012 339.441 163.267C339.441 166.593 342.164 169.316 345.49 169.316C348.816 169.316 351.539 166.593 351.539 163.267C351.539 161.012 350.714 159.941 349.932 158.892C349.33 158.088 348.682 157.262 348.682 156.035C348.682 155.142 348.861 153.914 349.687 153.066C350.289 152.441 351.115 152.129 352.164 152.129H370.513V133.78C370.513 133.245 370.513 131.638 367.946 131.638C367.164 131.638 366.629 132.039 365.892 132.62C364.798 133.468 363.414 134.495 360.713 134.495C356.629 134.495 353.325 131.169 353.325 127.106C353.325 123.044 356.629 119.718 360.713 119.718C363.414 119.718 364.798 120.767 365.892 121.593C366.629 122.151 367.164 122.575 367.946 122.575C370.513 122.575 370.513 120.968 370.513 120.432V102.084H352.164C349.999 102.084 348.682 100.633 348.682 98.178C348.682 96.9503 349.307 96.1244 349.932 95.3209C350.714 94.2718 351.539 93.2003 351.539 90.9459C351.539 87.62 348.816 84.8968 345.49 84.8968C342.164 84.8968 339.441 87.62 339.441 90.9459C339.441 93.2003 340.267 94.2718 341.048 95.3209C341.651 96.1244 342.298 96.9503 342.298 98.178C342.298 100.633 341.004 102.084 338.816 102.084H320.468V120.432C320.468 120.968 320.468 122.575 323.035 122.575C323.816 122.575 324.352 122.173 325.089 121.593C326.182 120.745 327.566 119.718 330.267 119.718C334.352 119.718 337.656 123.044 337.656 127.106C337.656 131.169 334.352 134.495 330.267 134.495C327.566 134.495 326.182 133.446 325.089 132.62C324.352 132.062 323.816 131.638 323.035 131.638C320.468 131.638 320.468 133.245 320.468 133.78V152.129Z" fill="#4EFEC3"/>
<path d="M398 17.8073H391.714V-21H382.286V17.8073H376L387 29L398 17.8073Z" fill="#4F8ED8"/>
<path d="M91 47.1357H84.4286V26H74.5714V47.1357H68L79.5 59L91 47.1357Z" fill="#4F8ED8"/>
<path opacity="0.5" d="M173 29.5385H153.286V0H123.714V29.5385H104L138.5 64L173 29.5385Z" fill="#4FA4D8"/>
<path opacity="0.5" d="M43 18.9231H30.7143V0H12.2857V18.9231H0L21.5 41L43 18.9231Z" fill="#4EFEC3"/>
<path d="M199 69.0206H188.714V50H173.286V69.0206H163L181 87L199 69.0206Z" fill="#4EFEC3"/>
<path d="M304 95.1349C304 94.8254 303.794 94.619 303.484 94.4127L295.333 91.627C294.405 87.6032 292.754 83.7857 290.587 80.381L294.302 72.6429C294.405 72.3333 294.405 72.0238 294.198 71.8175L286.873 64.5952C286.667 64.3889 286.254 64.3889 286.048 64.4921L278.31 68.3095C274.905 66.246 271.087 64.5952 267.063 63.6667L264.175 55.5159C264.071 55.2063 263.762 55.1032 263.452 55H253.135C252.825 55 252.619 55.2063 252.413 55.5159L249.627 63.6667C245.603 64.5952 241.786 66.246 238.381 68.4127L230.643 64.6984C230.333 64.5952 230.024 64.5952 229.817 64.8016L222.595 72.127C222.389 72.3333 222.389 72.746 222.492 72.9524L226.31 80.6905C224.246 84.0952 222.595 87.9127 221.667 91.9365L213.516 94.8254C213.206 94.9286 213.103 95.2381 213 95.5476V105.865C213 106.175 213.206 106.381 213.516 106.587L221.667 109.373C222.595 113.397 224.246 117.214 226.413 120.619L222.698 128.357C222.595 128.667 222.595 128.976 222.802 129.183L230.127 136.405C230.333 136.611 230.746 136.611 230.952 136.508L238.69 132.69C242.095 134.754 245.913 136.405 249.937 137.333L252.825 145.484C252.929 145.794 253.238 145.897 253.548 146H263.865C264.175 146 264.381 145.794 264.587 145.484L267.373 137.333C271.397 136.405 275.214 134.754 278.619 132.587L286.357 136.302C286.667 136.405 286.976 136.405 287.183 136.198L294.405 128.873C294.611 128.667 294.611 128.254 294.508 128.048L290.69 120.31C292.754 116.905 294.405 113.087 295.333 109.063L303.484 106.175C303.794 106.071 303.897 105.762 304 105.452V95.1349ZM264.794 121.341C253.341 124.746 241.27 118.246 237.865 106.794C234.46 95.3413 240.96 83.2698 252.516 79.8651C263.968 76.4603 276.04 82.9603 279.444 94.5159C282.849 105.865 276.246 117.937 264.794 121.341Z" fill="url(#paint0_linear)"/>
<path d="M220.727 32.3125L217.615 31.2188C217.232 29.6875 216.632 28.2109 215.813 26.8984L217.287 23.9453C217.342 23.8906 217.342 23.7266 217.232 23.6172L214.448 20.7734C214.393 20.7188 214.229 20.7188 214.12 20.7188L211.172 22.1406C209.861 21.3203 208.387 20.6641 206.858 20.3359L205.766 17.2188C205.711 17.0547 205.657 17 205.548 17H201.562C201.452 17.0547 201.343 17.0547 201.289 17.2188L200.197 20.3359C198.668 20.7188 197.193 21.3203 195.883 22.1406L192.934 20.6641C192.88 20.6094 192.716 20.6094 192.607 20.7188L189.768 23.5078C189.713 23.5625 189.713 23.7266 189.713 23.8359L191.133 26.7891C190.314 28.1016 189.658 29.5781 189.331 31.1094L186.218 32.2031C186.055 32.2578 186 32.3125 186 32.4219V36.4141C186.055 36.5234 186.055 36.6328 186.218 36.6875L189.331 37.7812C189.713 39.3125 190.314 40.7891 191.133 42.1016L189.658 45.0547C189.604 45.1094 189.604 45.2734 189.713 45.3828L192.498 48.2266C192.552 48.2812 192.716 48.2812 192.825 48.2812L195.774 46.8594C197.084 47.6797 198.559 48.3359 200.087 48.6641L201.179 51.7812C201.234 51.8906 201.343 52 201.452 52H205.438C205.548 51.9453 205.657 51.9453 205.711 51.7812L206.803 48.6641C208.332 48.2812 209.807 47.6797 211.117 46.8594L214.066 48.3359C214.12 48.3906 214.284 48.3906 214.393 48.2812L217.232 45.4922C217.287 45.4375 217.287 45.2734 217.287 45.1641L215.867 42.2109C216.686 40.8984 217.342 39.4219 217.669 37.8906L220.782 36.7969C220.891 36.7422 221 36.6328 221 36.5234V32.5312C220.891 32.4766 220.891 32.3672 220.727 32.3125ZM203.473 38.875C201.07 38.875 199.105 36.9062 199.105 34.5C199.105 32.0938 201.07 30.125 203.473 30.125C205.875 30.125 207.841 32.0938 207.841 34.5C207.841 36.9062 205.875 38.875 203.473 38.875Z" fill="url(#paint1_linear)"/>
<path d="M283.878 92.955C279.662 78.9428 264.954 70.9078 250.932 75.1213C236.911 79.2368 228.968 94.0328 233.087 108.045C237.303 122.057 252.011 130.092 266.032 125.879C280.054 121.665 288.094 106.967 283.878 92.955ZM264.365 120.195C253.482 123.429 242.009 117.256 238.774 106.379C235.538 95.5026 241.715 84.0381 252.697 80.8046C263.581 77.571 275.053 83.7442 278.289 94.7188C281.525 105.497 275.249 116.962 264.365 120.195Z" fill="url(#paint2_linear)"/>
<path d="M327 -6.33673C327 -6.67347 326.776 -6.89796 326.439 -7.12245L317.571 -10.1531C316.561 -14.5306 314.765 -18.6837 312.408 -22.3878L316.449 -30.8061C316.561 -31.1429 316.561 -31.4796 316.337 -31.7041L308.367 -39.5612C308.143 -39.7857 307.694 -39.7857 307.469 -39.6735L299.051 -35.5204C295.347 -37.7653 291.194 -39.5612 286.816 -40.5714L283.673 -49.4388C283.561 -49.7755 283.224 -49.8878 282.888 -50H271.663C271.327 -50 271.102 -49.7755 270.878 -49.4388L267.847 -40.5714C263.469 -39.5612 259.316 -37.7653 255.612 -35.4082L247.194 -39.449C246.857 -39.5612 246.52 -39.5612 246.296 -39.3367L238.439 -31.3673C238.214 -31.1429 238.214 -30.6939 238.327 -30.4694L242.48 -22.051C240.235 -18.3469 238.439 -14.1939 237.429 -9.81633L228.561 -6.67347C228.224 -6.56123 228.112 -6.22449 228 -5.88775V5.33673C228 5.67347 228.224 5.89796 228.561 6.12244L237.429 9.15306C238.439 13.5306 240.235 17.6837 242.592 21.3878L238.551 29.8061C238.439 30.1429 238.439 30.4796 238.663 30.7041L246.633 38.5612C246.857 38.7857 247.306 38.7857 247.531 38.6735L255.949 34.5204C259.653 36.7653 263.806 38.5612 268.184 39.5714L271.327 48.4388C271.439 48.7755 271.776 48.8878 272.112 49H283.337C283.673 49 283.898 48.7755 284.122 48.4388L287.153 39.5714C291.531 38.5612 295.684 36.7653 299.388 34.4082L307.806 38.449C308.143 38.5612 308.48 38.5612 308.704 38.3367L316.561 30.3673C316.786 30.1429 316.786 29.6939 316.673 29.4694L312.52 21.051C314.765 17.3469 316.561 13.1939 317.571 8.81633L326.439 5.67347C326.776 5.56123 326.888 5.22449 327 4.88775V-6.33673ZM284.347 22.1735C271.888 25.8775 258.755 18.8061 255.051 6.34694C251.347 -6.11225 258.418 -19.2449 270.99 -22.949C283.449 -26.6531 296.582 -19.5816 300.286 -7.0102C303.99 5.33673 296.806 18.4694 284.347 22.1735Z" fill="url(#paint3_linear)"/>
<path d="M305.751 -8.89917C301.057 -24.4976 284.684 -33.4422 269.075 -28.7518C253.466 -24.1704 244.625 -7.69929 249.21 7.89918C253.903 23.4976 270.276 32.4422 285.885 27.7518C301.494 23.0613 310.445 6.6993 305.751 -8.89917ZM284.029 21.4251C271.913 25.0248 259.142 18.1527 255.54 6.04481C251.938 -6.06309 258.815 -18.8255 271.04 -22.4251C283.156 -26.0248 295.927 -19.1527 299.529 -6.93572C303.131 5.0631 296.145 17.8255 284.029 21.4251Z" fill="url(#paint4_linear)"/>
<defs>
<linearGradient id="paint0_linear" x1="298.485" y1="145.989" x2="247.47" y2="59.1364" gradientUnits="userSpaceOnUse">
<stop stop-color="#2BE4C3"/>
<stop offset="1" stop-color="#4EFEC3"/>
</linearGradient>
<linearGradient id="paint1_linear" x1="218.879" y1="51.9959" x2="199.258" y2="18.5909" gradientUnits="userSpaceOnUse">
<stop stop-color="#2BE4C3"/>
<stop offset="1" stop-color="#4EFEC3"/>
</linearGradient>
<linearGradient id="paint2_linear" x1="258.562" y1="74.114" x2="258.562" y2="126.994" gradientUnits="userSpaceOnUse">
<stop stop-color="#2BE4C3"/>
<stop offset="1" stop-color="#4EFEC3"/>
</linearGradient>
<linearGradient id="paint3_linear" x1="321" y1="48.9884" x2="265.5" y2="-45.5" gradientUnits="userSpaceOnUse">
<stop stop-color="#2BE4C3"/>
<stop offset="1" stop-color="#4EFEC3"/>
</linearGradient>
<linearGradient id="paint4_linear" x1="277.569" y1="-29.8731" x2="277.569" y2="28.9931" gradientUnits="userSpaceOnUse">
<stop stop-color="#2BE4C3"/>
<stop offset="1" stop-color="#4EFEC3"/>
</linearGradient>
</defs>
</svg>
</div>

View File

@@ -0,0 +1,111 @@
<div
class="license-item"
:class="{ 'license-activated': isLicenseActive }"
>
<div
class="license-item__label"
v-if="type === 'single-item'"
>
<span v-if="!isLicenseActive">JetPlugins License Activation</span>
<span v-if="isLicenseActive">Congratulations!<br/>Your license has been activated!</span>
</div>
<div class="license-item__control" v-if="!isLicenseActive">
<span class="license-item__activation-message">Activate license for automatic updates and awesome support</span>
<cx-vui-input
class="license-item__key"
size="fullwidth"
type="password"
autofocus="true"
:prevent-wrap="true"
placeholder="Just paste it here"
:disabled="isLicenseActive"
v-model="licenseKey"
></cx-vui-input>
<cx-vui-button
class="license-item__action-button"
button-style="accent"
size="mini"
:loading="activationStatus"
@click="licenseAction"
>
<span slot="label" v-if="!isLicenseActive">Activate License</span>
<span slot="label" v-if="isLicenseActive">Deactivate License</span>
</cx-vui-button>
</div>
<div
class="license-item__details"
v-if="isLicenseActive"
>
<!-- <span class="license-details__label">Your License Information</span> -->
<div class="license-details__fields">
<div class="license-details__field license-key">
<span class="label">License Key:</span>{{ maskedLicenseKey }}
</div>
<div class="license-details__field license-name">
<span class="label">Product Name:</span>{{ productName }}
</div>
<div class="license-details__field license-status">
<span class="label">Status:</span>{{ licenseStatus }}
</div>
<div class="license-details__field license-type">
<span class="label">Type:</span>{{ licenseType }}
</div>
<div class="license-details__field license-expiration-date">
<span class="label">Expiration Date:</span>{{ expireDate }}
</div>
<div class="license-details__field license-plugins">
<span class="label">Included Plugins:</span>
<div class="included-plugin-list">
<div
class="included-plugin"
v-for="( plugin, index ) in licensePlugins"
:key="index"
>
<svg width="12" height="10" viewBox="0 0 12 10" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M12 0.799997L10.4 0L4.39998 5.19998L1.59999 3.19999L0 4.39998L4.39998 9.19996L12 0.799997Z" fill="#34D7A1"/>
</svg>
<span>{{ plugin.name }}</span>
</div>
</div>
</div>
<div class="cx-vui-alert info-type">
<div class="cx-vui-alert__icon">
<svg width="18" height="21" viewBox="0 0 18 21" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M9 20.5C10.3672 20.5 11.4609 19.4062 11.4609 18H6.5C6.5 19.4062 7.59375 20.5 9 20.5ZM17.3984 14.6797C16.6562 13.8594 15.2109 12.6484 15.2109 8.625C15.2109 5.61719 13.1016 3.19531 10.2109 2.57031V1.75C10.2109 1.08594 9.66406 0.5 9 0.5C8.29688 0.5 7.75 1.08594 7.75 1.75V2.57031C4.85938 3.19531 2.75 5.61719 2.75 8.625C2.75 12.6484 1.30469 13.8594 0.5625 14.6797C0.328125 14.9141 0.210938 15.2266 0.25 15.5C0.25 16.1641 0.71875 16.75 1.5 16.75H16.4609C17.2422 16.75 17.7109 16.1641 17.75 15.5C17.75 15.2266 17.6328 14.9141 17.3984 14.6797Z"/>
</svg>
</div>
<div class="cx-vui-alert__message">This license will activate licenses for all plugins included in this set.</div>
</div>
<div class="license-details__actions">
<cx-vui-button
class="show-license-manager"
button-style="link-accent"
size="link"
@click="showLicenseManager"
v-if="type === 'single-item'"
>
<span slot="label">License Manager</span>
</cx-vui-button>
<cx-vui-button
class="cx-vui-button--style-danger"
button-style="accent"
size="mini"
:loading="activationStatus"
@click="licenseAction"
>
<span slot="label" v-if="!isLicenseActive">Activate License</span>
<span slot="label" v-if="isLicenseActive">Deactivate License</span>
</cx-vui-button>
</div>
</div>
</div>
</div>

View File

@@ -0,0 +1,159 @@
<div class="jet-dashboard-license-page">
<div class="ready-for-use-plugins cx-vui-panel">
<cx-vui-button
class="license-manager-button"
button-style="accent"
size="mini"
@click="showLicenseManager"
>
<span slot="label">License Manager</span>
</cx-vui-button>
<div
class="installed-plugins"
v-if="installedPluginListVisible"
>
<div class="cx-vui-subtitle">Your Installed JetPlugins</div>
<div class="plugin-list">
<plugin-item-installed
v-for="( pluginData, index ) in installedPluginList"
:key="index"
:plugin-data="pluginData"
></plugin-item-installed>
</div>
</div>
<div
class="avaliable-plugins"
v-if="avaliablePluginListVisible"
>
<div class="cx-vui-subtitle">The following plugins are also included in your license</div>
<div class="plugin-list">
<plugin-item-avaliable
v-for="( pluginData, index ) in avaliablePluginList"
:key="index"
:plugin-data="pluginData"
></plugin-item-avaliable>
</div>
</div>
</div>
<div
class="more-plugins"
v-if="morePluginListVisible"
>
<div class="cx-vui-subtitle">Get More Plugins</div>
<div class="plugin-list--more-plugins">
<plugin-item-more
v-for="( pluginData, index ) in morePluginList"
:key="index"
:plugin-data="pluginData"
></plugin-item-more>
</div>
</div>
<transition name="popup">
<cx-vui-popup
class="license-activation-popup"
v-model="licensePopupVisible"
:header="false"
:footer="false"
>
<div class="license-manager" slot="content">
<license-item
:license-data="newlicenseData"
type="single-item"
></license-item>
</div>
</cx-vui-popup>
</transition>
<transition name="popup">
<cx-vui-popup
class="license-deactivation-popup"
v-model="deactivatePopupVisible"
:footer="false"
body-width="520px"
>
<div slot="title">
<div class="cx-vui-popup__header-label">JetPlugins License Deactivation</div>
</div>
<div slot="content">
<p>Your license includes several plugins within the package. License deactivation in one plugin disables it in the rest of them. You can manage it through the License Manager.</p>
<cx-vui-button
class="show-license-manager"
button-style="accent"
size="mini"
@click="showLicenseManager"
>
<span slot="label">License Manager</span>
</cx-vui-button>
</div>
</cx-vui-popup>
</transition>
<transition name="popup">
<cx-vui-popup
class="update-check-popup"
v-model="updateCheckPopupVisible"
:footer="false"
body-width="520px"
>
<div slot="title">
<div class="cx-vui-popup__header-label">JetPlugins Update</div>
</div>
<div slot="content">
<svg width="91" height="100" viewBox="0 0 91 100" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M16.748 43.3361C20.4863 43.3361 23.4143 38.9426 23.4143 33.336C23.4143 27.7301 20.4863 23.3365 16.748 23.3365C13.0098 23.3365 10.0818 27.7301 10.0818 33.336C10.0818 38.9426 13.0098 43.3361 16.748 43.3361ZM16.748 26.6697C18.3212 26.6697 20.0812 29.5199 20.0812 33.336C20.0812 37.1528 18.3212 40.0022 16.748 40.0022C15.1749 40.0022 13.4149 37.1528 13.4149 33.336C13.4149 29.5199 15.1749 26.6697 16.748 26.6697Z" fill="black"/>
<path d="M48.4132 43.3361C52.1515 43.3361 55.0795 38.9426 55.0795 33.336C55.0795 27.7301 52.1515 23.3365 48.4132 23.3365C44.675 23.3365 41.747 27.7301 41.747 33.336C41.747 38.9426 44.675 43.3361 48.4132 43.3361ZM48.4132 26.6697C49.9871 26.6697 51.7464 29.5199 51.7464 33.336C51.7464 37.1528 49.9871 40.0022 48.4132 40.0022C46.8401 40.0022 45.0801 37.1528 45.0801 33.336C45.0801 29.5199 46.8401 26.6697 48.4132 26.6697V26.6697Z" fill="black"/>
<path d="M45.914 100C67.2212 100 83.2537 92.375 89.9115 79.079C90.2007 78.5015 90.1305 77.8088 89.7307 77.3015C89.331 76.7941 88.6741 76.5637 88.0455 76.7094C80.154 78.5427 76.682 74.2094 75.546 72.2648C74.1049 69.6915 73.3687 66.7833 73.4122 63.8346V36.6691C73.4137 26.8467 69.4733 17.4347 62.4751 10.5418C55.477 3.64972 46.0055 -0.1465 36.1839 0.00455508C16.2781 0.307429 0.0823603 17.1066 0.0823603 37.4579V70.0012C0.0960926 73.1375 0.813225 76.2311 2.18035 79.0539C8.18214 91.5823 25.758 100 45.914 100ZM3.4155 37.4579C3.4155 18.9185 18.1381 3.61386 36.2327 3.33769H36.7476C55.1558 3.33769 70.079 18.2609 70.079 36.6691V63.8346C70.0355 67.3699 70.9274 70.8534 72.6638 73.9325C75.2538 78.3543 80.1585 80.8886 85.2639 80.4439C78.3871 90.8003 64.2809 96.6671 45.914 96.6671C27.3074 96.6671 10.5601 88.8336 5.18697 77.6196C4.03498 75.2439 3.42923 72.6409 3.4155 70.0012V37.4579Z" fill="black"/>
<path d="M16.748 80.0007C21.3484 79.9953 25.0759 76.2678 25.0813 71.6682V63.335C25.0813 62.4142 24.3351 61.668 23.4143 61.668C22.4943 61.668 21.7481 62.4142 21.7481 63.335V71.6682C21.7481 74.4292 19.5098 76.6675 16.748 76.6675C13.9871 76.6675 11.7487 74.4292 11.7487 71.6682V63.335C11.7487 62.4142 11.0026 61.668 10.0818 61.668C9.16171 61.668 8.41559 62.4142 8.41559 63.335V71.6682C8.42093 76.2678 12.1485 79.9953 16.748 80.0007Z" fill="black"/>
<path d="M50.0802 80.0007C54.6798 79.9953 58.4073 76.2678 58.4134 71.6682V63.335C58.4134 62.4142 57.6665 61.668 56.7465 61.668C55.8256 61.668 55.0795 62.4142 55.0795 63.335V71.6682C55.0795 74.4292 52.8412 76.6675 50.0802 76.6675C47.3185 76.6675 45.0801 74.4292 45.0801 71.6682V63.335C45.0801 62.4142 44.334 61.668 43.4139 61.668C42.4931 61.668 41.747 62.4142 41.747 63.335V71.6682C41.7523 76.2678 45.4799 79.9953 50.0802 80.0007V80.0007Z" fill="black"/>
<path d="M26.1631 49.8971C26.5773 50.0528 27.0366 50.0367 27.4387 49.8529C27.8415 49.6698 28.155 49.3333 28.3091 48.9191C28.5891 48.1539 29.0095 47.4474 29.5473 46.8356C30.0409 46.2695 30.6436 45.8087 31.3196 45.4807C32.644 44.8436 34.1866 44.8436 35.511 45.4807C36.1854 45.8087 36.7873 46.2695 37.2809 46.8356C37.8188 47.4467 38.2391 48.1524 38.5191 48.9176C38.7617 49.5698 39.3842 50.0024 40.0808 50.0024C40.2799 50.0024 40.4783 49.9666 40.6652 49.8971C41.5272 49.5744 41.9644 48.6139 41.6424 47.7526C41.2183 46.6052 40.5858 45.5463 39.7771 44.6293C38.9875 43.7283 38.024 42.9959 36.9437 42.4756C34.7084 41.406 32.1084 41.406 29.8723 42.4756C28.7928 42.9951 27.8293 43.7275 27.0397 44.6293C26.2302 45.5463 25.5985 46.6052 25.1744 47.7526C25.0202 48.1676 25.0378 48.6277 25.2232 49.0297C25.4086 49.4325 25.7465 49.7445 26.1631 49.8971Z" fill="black"/>
</svg>
<p><span>Ooops!</span>Sorry, but you need to activate license to update your JetPlugin</p>
<cx-vui-button
class="cx-vui-button--style-accent"
button-style="default"
size="mini"
@click="showPopupActivation"
>
<span slot="label">Activate License</span>
</cx-vui-button>
</div>
</cx-vui-popup>
</transition>
<transition name="popup">
<cx-vui-popup
class="license-manager-popup"
v-model="licenseManagerVisible"
:footer="false"
>
<div class="cx-vui-popup__header-inner" slot="title">
<div class="cx-vui-popup__header-label">Your Licenses</div>
<cx-vui-button
class="add-new-license"
button-style="accent"
size="mini"
@click="addNewLicense"
>
<span slot="label">
<span class="dashicons dashicons-plus"></span>
<span>Add New License</span>
</span>
</cx-vui-button>
</div>
<div class="license-manager" slot="content">
<p v-if="licenseList.length === 0">Add and Activate license for automatic updates, awesome support and bla bla features</p>
<div
class="license-list"
>
<license-item
v-for="( license, index ) in licenseList"
:key="index"
:license-data="license"
type="listing-item"
></license-item>
</div>
</div>
</cx-vui-popup>
</transition>
</div>

View File

@@ -0,0 +1,37 @@
<div
class="plugin-item plugin-item--avaliable"
>
<div class="plugin-item__inner">
<div class="plugin-tumbnail">
<img :src="pluginData.thumb">
</div>
<div class="plugin-info">
<div class="plugin-name">
<span class="plugin-label">{{ pluginData.name }}</span>
<span
class="plugin-version"
>
{{ pluginData.currentVersion }}
</span>
</div>
<p class="plugin-desc">{{ pluginData.desc }}</p>
<div class="plugin-actions">
<cx-vui-button
class="cx-vui-button--style-accent"
button-style="default"
size="mini"
:loading="pluginActionProcessed"
v-if="installAvaliable"
@click="installPlugin"
>
<span slot="label">
<span>Install Plugin</span>
</span>
</cx-vui-button>
</div>
</div>
</div>
</div>

View File

@@ -0,0 +1,89 @@
<div
class="plugin-item plugin-item--installed"
:class="{ 'update-avaliable': updateAvaliable }"
>
<div class="plugin-item__inner">
<div class="plugin-tumbnail">
<img :src="pluginData.thumb">
</div>
<div class="plugin-info">
<div class="plugin-name">
<span class="plugin-label">{{ pluginData.name }}</span>
<span class="plugin-version">{{ pluginData.currentVersion }}</span>
</div>
<div
class="plugin-update-label"
>
<div v-if="!updateAvaliable">Your plugin is up to date</div>
<div v-if="updateAvaliable">
Version <span class="latest-version">{{pluginData.version}}</span> available
<cx-vui-button
button-style="link-accent"
size="link"
:loading="actionPluginProcessed"
@click="updatePlugin"
>
<span slot="label">
<span>Update Now</span>
</span>
</cx-vui-button>
</div>
</div>
<div class="plugin-actions">
<cx-vui-button
class="cx-vui-button--style-accent"
button-style="default"
size="mini"
@click="showPopupActivation"
v-if="activateLicenseVisible"
>
<span slot="label">
<svg class="button-icon" width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M15.4985 0H12.4897C12.4166 0 12.3487 0.0156709 12.286 0.0470127C12.2338 0.0679073 12.1867 0.104473 12.145 0.156709L5.7669 6.47209C5.62063 6.44074 5.46392 6.41463 5.29677 6.39373C5.12961 6.37284 4.96768 6.36239 4.81097 6.36239C4.16324 6.36239 3.54685 6.48776 2.9618 6.73849C2.37675 6.97878 1.85961 7.32354 1.41038 7.77277C0.961149 8.222 0.611166 8.73914 0.360431 9.32419C0.120144 9.90924 0 10.5309 0 11.189C0 11.8368 0.120144 12.4532 0.360431 13.0382C0.611166 13.6232 0.961149 14.1404 1.41038 14.5896C1.85961 15.0389 2.37675 15.3836 2.9618 15.6239C3.54685 15.8746 4.16324 16 4.81097 16C5.46915 16 6.09076 15.8746 6.67581 15.6239C7.26086 15.3836 7.778 15.0389 8.22723 14.5896C8.80183 14.015 9.19882 13.3464 9.41822 12.5837C9.64806 11.8211 9.68462 11.0375 9.52791 10.2331L10.8913 8.86974C10.9331 8.82795 10.9644 8.78093 10.9853 8.7287C11.0167 8.66601 11.0323 8.59811 11.0323 8.52498V7.02057H12.5367C12.6934 7.02057 12.8136 6.97356 12.8972 6.87953C12.9912 6.7855 13.0382 6.66536 13.0382 6.5191V5.01469H14.5426C14.6157 5.01469 14.6784 5.00424 14.7307 4.98335C14.7933 4.95201 14.8508 4.91022 14.903 4.85798L15.906 3.85504C15.9269 3.81326 15.9478 3.76624 15.9687 3.71401C15.9896 3.65132 16 3.58342 16 3.51028V0.501469C16 0.355207 15.953 0.235064 15.859 0.141038C15.7649 0.0470127 15.6448 0 15.4985 0ZM4.96768 12.7875C4.79008 12.9651 4.5968 13.0957 4.38786 13.1792C4.18936 13.2524 3.96474 13.2889 3.71401 13.2889C3.46327 13.2889 3.23343 13.2419 3.02449 13.1479C2.82599 13.0539 2.63794 12.9337 2.46033 12.7875C2.28273 12.6099 2.15214 12.4218 2.06856 12.2233C1.99543 12.0144 1.95886 11.7845 1.95886 11.5338C1.95886 11.2831 2.00588 11.0584 2.0999 10.8599C2.19393 10.651 2.31407 10.4577 2.46033 10.2801C2.7842 9.95625 3.19164 9.79432 3.68266 9.79432C4.18413 9.79432 4.5968 9.95625 4.92067 10.2801C5.09827 10.4577 5.22364 10.651 5.29677 10.8599C5.38035 11.0584 5.42214 11.2831 5.42214 11.5338C5.42214 11.7845 5.38035 12.0144 5.29677 12.2233C5.22364 12.4218 5.11394 12.6099 4.96768 12.7875Z" fill="#D3D3D3"/>
</svg>
<span>Activate License</span>
</span>
</cx-vui-button>
<cx-vui-button
class="cx-vui-button--style-danger"
button-style="default"
size="mini"
:loading="licenseActionProcessed"
@click="deactivateLicense"
v-if="deactivateLicenseVisible"
>
<span slot="label">
<svg class="button-icon" width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M15.4985 0H12.4897C12.4166 0 12.3487 0.0156709 12.286 0.0470127C12.2338 0.0679073 12.1867 0.104473 12.145 0.156709L5.7669 6.47209C5.62063 6.44074 5.46392 6.41463 5.29677 6.39373C5.12961 6.37284 4.96768 6.36239 4.81097 6.36239C4.16324 6.36239 3.54685 6.48776 2.9618 6.73849C2.37675 6.97878 1.85961 7.32354 1.41038 7.77277C0.961149 8.222 0.611166 8.73914 0.360431 9.32419C0.120144 9.90924 0 10.5309 0 11.189C0 11.8368 0.120144 12.4532 0.360431 13.0382C0.611166 13.6232 0.961149 14.1404 1.41038 14.5896C1.85961 15.0389 2.37675 15.3836 2.9618 15.6239C3.54685 15.8746 4.16324 16 4.81097 16C5.46915 16 6.09076 15.8746 6.67581 15.6239C7.26086 15.3836 7.778 15.0389 8.22723 14.5896C8.80183 14.015 9.19882 13.3464 9.41822 12.5837C9.64806 11.8211 9.68462 11.0375 9.52791 10.2331L10.8913 8.86974C10.9331 8.82795 10.9644 8.78093 10.9853 8.7287C11.0167 8.66601 11.0323 8.59811 11.0323 8.52498V7.02057H12.5367C12.6934 7.02057 12.8136 6.97356 12.8972 6.87953C12.9912 6.7855 13.0382 6.66536 13.0382 6.5191V5.01469H14.5426C14.6157 5.01469 14.6784 5.00424 14.7307 4.98335C14.7933 4.95201 14.8508 4.91022 14.903 4.85798L15.906 3.85504C15.9269 3.81326 15.9478 3.76624 15.9687 3.71401C15.9896 3.65132 16 3.58342 16 3.51028V0.501469C16 0.355207 15.953 0.235064 15.859 0.141038C15.7649 0.0470127 15.6448 0 15.4985 0ZM4.96768 12.7875C4.79008 12.9651 4.5968 13.0957 4.38786 13.1792C4.18936 13.2524 3.96474 13.2889 3.71401 13.2889C3.46327 13.2889 3.23343 13.2419 3.02449 13.1479C2.82599 13.0539 2.63794 12.9337 2.46033 12.7875C2.28273 12.6099 2.15214 12.4218 2.06856 12.2233C1.99543 12.0144 1.95886 11.7845 1.95886 11.5338C1.95886 11.2831 2.00588 11.0584 2.0999 10.8599C2.19393 10.651 2.31407 10.4577 2.46033 10.2801C2.7842 9.95625 3.19164 9.79432 3.68266 9.79432C4.18413 9.79432 4.5968 9.95625 4.92067 10.2801C5.09827 10.4577 5.22364 10.651 5.29677 10.8599C5.38035 11.0584 5.42214 11.2831 5.42214 11.5338C5.42214 11.7845 5.38035 12.0144 5.29677 12.2233C5.22364 12.4218 5.11394 12.6099 4.96768 12.7875Z" fill="#D3D3D3"/>
</svg>
<span>Deactivate License</span>
</span>
</cx-vui-button>
<cx-vui-button
button-style="link-accent"
size="link"
:loading="actionPluginProcessed"
v-if="activateAvaliable"
@click="activatePlugin"
>
<span slot="label">
<span>Activate Plugin</span>
</span>
</cx-vui-button>
<cx-vui-button
class="deactivate-plugin-button"
button-style="link-accent"
size="link"
:loading="actionPluginProcessed"
v-if="deactivateAvaliable"
@click="deactivatePlugin"
>
<span slot="label">
<span>Deactivate Plugin</span>
</span>
</cx-vui-button>
</div>
</div>
</div>
</div>

View File

@@ -0,0 +1,27 @@
<div class="plugin-item plugin-item--more">
<div class="plugin-item__inner">
<div class="plugin-tumbnail">
<img :src="pluginData.thumb_alt">
</div>
<div class="plugin-info">
<p class="plugin-desc">{{ pluginData.desc }}</p>
<div class="plugin-actions">
<cx-vui-button
class="cx-vui-button--style-accent"
button-style="default"
size="mini"
:url="pluginData.demo"
tag-name="a"
target="_blank"
>
<span slot="label">
<span>Get Plugin</span>
</span>
</cx-vui-button>
</div>
</div>
</div>
</div>

View File

@@ -0,0 +1,3 @@
<div class="jet-dashboard-welcome-page">
<h1>jet-dashboard-welcome-page</h1>
</div>

View File

@@ -0,0 +1,216 @@
<?php
/**
* Cherry X framework loader class.
*
* How to use:
*
* 1. Copy and include this class into your theme/plugin
* 2. Add unique prefix for the class name, e.g. - Twentyseventeen_CX_Loader
* 3. Initialize loader on after_setup_theme hook with priority -20, Example:
*
* add_action( 'after_setup_theme', 'twentyseventeen_framework_loader', -20 );
* function twentyseventeen_framework_loader() {
* require get_theme_file_path( 'framework/loader.php' );
* new Twentyseventeen_CX_Loader(
* array(
* get_theme_file_path( 'framework/modules/module-1/module-1.php' ),
* get_theme_file_path( 'framework/modules/module-2/module-2.php' ),
* get_theme_file_path( 'framework/modules/module-3/module-3.php' ),
* )
* );
* }
*
* Notes:
*
* 1. This class only select latest version of each module from all Cherry X frameworks loaded in current environment
* 2. You should manually initialize selected modules later, when them will be needed you, but not eralier than after_setup_theme hook with priority 0.
*/
// If this file is called directly, abort.
if ( ! defined( 'WPINC' ) ) {
die;
}
if ( ! class_exists( 'Jet_Tabs_CX_Loader' ) ) {
/**
* Define Jet_Tabs_CX_Loader class
*/
class Jet_Tabs_CX_Loader {
/**
* Key for object cache where are stored information about all modules in current environment
*
* @var string
*/
private $key = 'cherry_x_modules';
/**
* Holder for modules list of current loader instance.
*
* @var array
*/
private $modules = array();
/**
* Holder for modules slugs list of current loader instance.
*
* @var array
*/
private $modules_slugs = array();
/**
* Included modules paths and URLs
*
* @var array
*/
private $included_modules = array();
/**
* Loads latest versions of all modules passed into modules array
*
* @param array $modules List of loaded modules. Format:
* array(
* get_theme_file_path( 'framework/modules/module-1/module-1.php' ),
* get_theme_file_path( 'framework/modules/module-2/module-2.php' ),
* get_theme_file_path( 'framework/modules/module-3/module-3.php' ),
* )
*/
public function __construct( array $modules = array() ) {
$this->modules = $modules;
add_action( 'after_setup_theme', array( $this, 'store_versions' ), -10 );
add_action( 'after_setup_theme', array( $this, 'include_modules' ), -1 );
}
/**
* Store versions for modules passed in current instance into global modules versions list
*
* @return void
*/
public function store_versions() {
foreach ( $this->modules as $module ) {
$this->store_module_version( $module );
}
}
/**
* Include latest versions of modules in current loader instance.
* All available version preiously stored by 'store_versions' methods of each loader instance.
*
* @return boolean
*/
public function include_modules() {
$modules_data = wp_cache_get( $this->key );
foreach ( $this->modules_slugs as $slug ) {
if ( empty( $modules_data[ $slug ] ) ) {
continue;
}
$path = $this->get_latest_version_path( $modules_data[ $slug ] );
if ( file_exists( $path ) ) {
$dir = pathinfo( $path, PATHINFO_DIRNAME );
$url = str_replace(
'\\',
'/',
str_replace( untrailingslashit( ABSPATH ), esc_url( site_url() ), $dir )
);
$this->included_modules[ $slug ] = array(
'path' => trailingslashit( $dir ),
'url' => apply_filters( 'cx_include_module_url', trailingslashit( $url ), $path ),
);
require_once $path;
}
}
return true;
}
/**
* Retireve path and URL of included module directory
*
* @param [type] $file [description]
* @return [type] [description]
*/
public function get_included_module_data( $file ) {
return isset( $this->included_modules[ $file ] ) ? $this->included_modules[ $file ] : false;
}
/**
* Select latest version path from all available.
*
* @param array $module_versions All available vaerions paths for selected module
* @return string Module path.
*/
private function get_latest_version_path( array $module_versions = array() ) {
// Immediately return path if array contain sinle element.
if ( 1 === count( $module_versions ) ) {
$module_versions = array_values( $module_versions );
return $module_versions[0];
}
// Sort array by version and return highest
uksort( $module_versions, 'version_compare' );
return end( $module_versions );
}
/**
* Store passed module version and path into global modules data.
*
* @param string $module_path Module path
* @return boolean
*/
private function store_module_version( $module_path = null ) {
$slug = basename( $module_path );
$modules_data = wp_cache_get( $this->key );
$modules_data = ! empty( $modules_data ) ? $modules_data : array();
if ( empty( $modules_data[ $slug ] ) ) {
$modules_data[ $slug ] = array();
}
$filedata = get_file_data( $module_path, array(
'version' => 'Version',
) );
if ( empty( $filedata['version'] ) ) {
// If version not passed in file header, so module defined not correctly and not be included
return false;
}
$current_version = $filedata['version'];
if ( empty( $modules_data[ $slug ][ $current_version ] ) ) {
$modules_data[ $slug ][ $current_version ] = $module_path;
}
$this->modules_slugs[] = $slug;
wp_cache_set( $this->key, $modules_data, '', 1 );
return true;
}
}
}

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load Diff

File diff suppressed because one or more lines are too long

View File

@@ -0,0 +1,254 @@
import { oneOf } from '../../utils/assist';
import { checkConditions } from '../../mixins/check-conditions';
const Checkbox = {
name: 'cx-vui-checkbox',
template: '#cx-vui-checkbox',
mixins: [ checkConditions ],
props: {
returnType: {
validator ( value ) {
return oneOf( value, [ 'array', 'object', 'single' ] );
},
default: 'object'
},
value: {
default: ''
},
disabled: {
type: Boolean,
default: false
},
name: {
type: String
},
optionsList: {
type: Array,
default() {
return [];
}
},
returnTrue: {
type: [ Boolean, String, Number ],
default: true,
},
returnFalse: {
type: [ Boolean, String, Number ],
default: false,
},
elementId: {
type: String
},
conditions: {
type: Array,
default() {
return [];
}
},
// Wrapper related props (should be passed into wrapper component)
preventWrap: {
type: Boolean,
default: false
},
label: {
type: String
},
description: {
type: String
},
wrapperCss: {
type: Array,
default: function() {
return [];
}
},
},
data() {
return {
currentValues: this.value,
currentId: this.elementId,
optionInFocus: null,
};
},
watch: {
value( val ) {
this.setCurrentValues( val );
},
},
mounted() {
if ( ! this.currentId && this.name ) {
this.currentId = 'cx_' + this.name;
}
},
computed: {
inputType() {
if ( 'array' === this.returnType ) {
return 'checkbox';
} else {
return 'hidden';
}
},
},
methods: {
inputValue( optionValue ) {
if ( 'checkbox' === this.inputType ) {
return this.returnTrue;
} else {
if ( this.isChecked( optionValue ) ) {
return this.returnTrue;
} else {
return this.returnFalse;
}
}
},
isChecked( optionValue ) {
if ( ! this.currentValues ) {
return false;
}
switch ( this.returnType ) {
case 'single':
return optionValue === this.currentValues;
case 'array':
return oneOf( optionValue, this.currentValues );
case 'object':
if ( ! this.currentValues[ optionValue ] ) {
return false;
} else {
if ( this.currentValues[ optionValue ] === this.returnTrue ) {
return true;
} else {
return false;
}
}
break;
};
},
handleEnter( event ) {
this.$emit( 'on-enter', event );
},
handleClick( event ) {
this.$emit( 'on-click', event );
},
handleFocus( event, value ) {
if ( this.disabled ) {
return;
}
this.optionInFocus = value;
this.$emit( 'on-focus', event, value );
},
handleBlur ( event, value ) {
if ( this.disabled ) {
return;
}
if ( value === this.optionInFocus ) {
this.optionInFocus = null;
}
this.$emit( 'on-blur', event, value );
},
handleParentFocus() {
if ( this.disabled ) {
return;
}
if ( null === this.optionInFocus && this.optionsList.length ) {
this.optionInFocus = this.optionsList[0].value;
}
},
handleInput ( event, value ) {
if ( this.disabled ) {
return;
}
this.updateValueState( value );
this.$emit( 'input', this.currentValues );
this.$emit( 'on-change', event );
},
isOptionInFocus( value ) {
return value === this.optionInFocus;
},
updateValueState( value ) {
switch ( this.returnType ) {
case 'single':
if ( value !== this.currentValues ) {
this.currentValues = value;
}
break;
case 'array':
if ( ! oneOf( value, this.currentValues ) ) {
this.currentValues.push( value );
} else {
this.currentValues.splice( this.currentValues.indexOf( value ), 1 );
}
break;
case 'object':
if ( ! this.currentValues[ value ] ) {
this.$set( this.currentValues, value, this.returnTrue );
} else {
if ( this.currentValues[ value ] === this.returnTrue ) {
this.$set( this.currentValues, value, this.returnFalse );
} else {
this.$set( this.currentValues, value, this.returnTrue );
}
}
break;
}
},
setCurrentValues( value ) {
switch ( this.returnType ) {
case 'single':
if ( value !== this.currentValues ) {
this.currentValues = value;
}
break;
case 'array':
case 'object':
this.currentValues = value;
break;
};
},
},
};
export default Checkbox;

View File

@@ -0,0 +1,422 @@
import { oneOf, arraysEqual } from '../../utils/assist';
import { checkConditions } from '../../mixins/check-conditions';
import { directive as clickOutside } from 'v-click-outside-x';
const FilterableSelect = {
name: 'cx-vui-f-select',
template: '#cx-vui-f-select',
mixins: [ checkConditions ],
directives: { clickOutside },
props: {
value: {
type: [String, Number, Array],
default: ''
},
placeholder: {
type: String,
default: ''
},
optionsList: {
type: Array,
default: function() {
return [];
}
},
disabled: {
type: Boolean,
default: false
},
readonly: {
type: Boolean,
default: false
},
name: {
type: String
},
error: {
type: Boolean,
default: false
},
multiple: {
type: Boolean,
default: false
},
elementId: {
type: String
},
autocomplete: {
validator (value) {
return oneOf( value, ['on', 'off'] );
},
default: 'off'
},
conditions: {
type: Array,
default: function() {
return [];
}
},
remote: {
type: Boolean,
default: false
},
remoteCallback: {
type: Function
},
remoteTrigger: {
type: Number,
default: 3
},
remoteTriggerMessage: {
type: String,
default: 'Please enter %d char(s) to start search'
},
notFoundMeassge: {
type: String,
default: 'There is no items find matching this query'
},
loadingMessage: {
type: String,
default: 'Loading...'
},
// Wrapper related props (should be passed into wrapper component)
preventWrap: {
type: Boolean,
default: false
},
label: {
type: String
},
description: {
type: String
},
wrapperCss: {
type: Array,
default: function() {
return [];
}
},
},
data() {
return {
options: this.optionsList,
currentValues: this.value,
currentId: this.elementId,
selectedOptions: [],
query: '',
inFocus: false,
optionInFocus: false,
loading: false,
loaded: false,
};
},
watch: {
value( newValue, oldValue ) {
if ( this.multiple ) {
if ( arraysEqual( newValue, oldValue ) ) {
return;
}
} else {
if ( newValue === oldValue ) {
return;
}
}
this.storeValues( newValue );
},
optionsList( options ) {
this.setOptions( options );
},
},
created() {
if ( ! this.currentValues ) {
this.currentValues = [];
} else if ( 'object' !== typeof this.currentValues ) {
if ( '[object Array]' === Object.prototype.toString.call( this.currentValues ) ) {
} else {
this.currentValues = [ this.currentValues ];
}
}
},
mounted() {
if ( ! this.currentId && this.name ) {
this.currentId = 'cx_' + this.name;
}
if ( this.remote && this.remoteCallback && this.currentValues.length ) {
this.remoteUpdateSelected();
} else if ( this.currentValues.length ) {
this.options.forEach( option => {
if ( oneOf( option.value, this.currentValues ) ) {
this.selectedOptions.push( option );
}
} );
}
},
computed: {
filteredOptions() {
if ( ! this.query ) {
return this.options;
} else {
return this.options.filter( option => {
if ( this.remote ) {
return true;
} else {
return option.label.includes( this.query ) || option.value.includes( this.query );
}
});
}
},
parsedRemoteTriggerMessage() {
return this.remoteTriggerMessage.replace( /\%d/g, this.charsDiff );
},
charsDiff() {
let queryLength = 0;
if ( this.query ) {
queryLength = this.query.length
}
return this.remoteTrigger - queryLength;
},
},
methods: {
remoteUpdateSelected() {
this.loading = true;
const promise = this.remoteCallback( this.query, this.currentValues );
if ( promise && promise.then ) {
promise.then( options => {
if ( options ) {
this.selectedOptions = options;
this.loaded = true;
this.loading = false;
}
} );
}
},
handleFocus( event ) {
this.inFocus = true;
this.$emit( 'on-focus', event );
},
handleOptionsNav( event ) {
// next
if ( 'ArrowUp' === event.key || 'Tab' === event.key ) {
this.navigateOptions( -1 );
}
// prev
if ( 'ArrowDown' === event.key ) {
this.navigateOptions( 1 );
}
},
navigateOptions( direction ) {
if ( false === this.optionInFocus ) {
this.optionInFocus = -1;
}
let index = this.optionInFocus + direction;
let maxLength = this.options.length - 1;
if ( maxLength < 0 ) {
maxLength = 0;
}
if ( index < 0 ) {
index = 0;
} else if ( index > maxLength ) {
index = maxLength;
}
this.optionInFocus = index;
},
onClickOutside( event ) {
if ( this.inFocus ) {
this.inFocus = false;
this.$emit( 'on-blur', event );
}
},
handleInput( event ) {
let value = event.target.value;
this.query = value;
this.$emit( 'input', this.currentValues );
this.$emit( 'on-change', event );
if ( ! this.inFocus ) {
this.inFocus = true;
}
if ( this.remote && this.remoteCallback && this.charsDiff <= 0 && ! this.loading && ! this.loaded ) {
this.loading = true;
const promise = this.remoteCallback( this.query, [] );
if ( promise && promise.then ) {
promise.then( options => {
if ( options ) {
this.options = options;
this.loaded = true;
this.loading = false;
}
} );
}
} else if ( this.remote && this.remoteCallback && this.loaded && this.charsDiff > 0 ) {
this.resetRemoteOptions();
}
},
handleEnter() {
if ( false === this.optionInFocus || ! this.options[ this.optionInFocus ] ) {
return;
}
let value = this.options[ this.optionInFocus ].value;
this.handleResultClick( value );
},
handleResultClick( value ) {
if ( oneOf( value, this.currentValues ) ) {
this.removeValue( value );
} else {
this.storeValues( value );
}
this.$emit( 'input', this.currentValues );
this.$emit( 'on-change', this.currentValues );
this.inFocus = false;
this.optionInFocus = false;
this.query = '';
if ( this.remote && this.remoteCallback && this.loaded ) {
this.resetRemoteOptions();
}
},
resetRemoteOptions() {
this.options = [];
this.loaded = false;
},
removeValue( value ) {
this.currentValues.splice( this.currentValues.indexOf( value ), 1 );
this.removeFromSelected( value );
},
removeFromSelected( value ) {
this.selectedOptions.forEach( ( option, index ) => {
if ( option.value === value ) {
this.selectedOptions.splice( index, 1 );
}
} );
},
pushToSelected( value, single ) {
this.options.forEach( option => {
if ( option.value === value ) {
if ( ! single ) {
this.selectedOptions.push( option );
} else {
this.selectedOptions = [ option ];
}
}
} );
},
storeValues( value ) {
if ( oneOf( value, this.currentValues ) ) {
return;
}
if ( this.multiple ) {
if ( 'object' === typeof value ) {
if ( '[object Array]' === Object.prototype.toString.call( value ) ) {
value.forEach( singleVal => {
if ( ! oneOf( singleVal, this.currentValues ) ) {
this.currentValues.push( singleVal );
this.pushToSelected( singleVal );
}
} );
} else {
this.currentValues.push( value );
this.pushToSelected( value );
}
} else {
this.currentValues.push( value );
this.pushToSelected( value );
}
} else {
if ( 'object' === typeof value ) {
if ( '[object Array]' === Object.prototype.toString.call( value ) ) {
this.currentValues = value;
value.forEach( singleVal => {
this.pushToSelected( singleVal, true );
} );
} else {
this.currentValues = [ value ];
this.pushToSelected( value, true );
}
} else {
this.currentValues = [ value ];
this.pushToSelected( value, true );
}
}
},
setOptions( options ) {
this.options = options;
},
isOptionSelected( option ) {
if ( ! this.currentValues ) {
return false;
}
return oneOf( option.value, this.currentValues );
},
},
};
export default FilterableSelect;

View File

@@ -0,0 +1,193 @@
import { directive as clickOutside } from 'v-click-outside-x';
import { oneOf } from '../../utils/assist';
import { checkConditions } from '../../mixins/check-conditions';
const Iconpicker = {
name: 'cx-vui-iconpicker',
template: '#cx-vui-iconpicker',
mixins: [ checkConditions ],
directives: { clickOutside },
props: {
value: {
type: [String],
default: ''
},
size: {
validator (value) {
return oneOf( value, [ 'small', 'large', 'default', 'fullwidth' ] );
},
default: 'default'
},
placeholder: {
type: String,
default: ''
},
disabled: {
type: Boolean,
default: false
},
readonly: {
type: Boolean,
default: false
},
name: {
type: String
},
autofocus: {
type: Boolean,
default: false
},
elementId: {
type: String
},
autocomplete: {
validator (value) {
return oneOf(value, ['on', 'off']);
},
default: 'off'
},
conditions: {
type: Array,
default: function() {
return [];
}
},
iconBase: {
type: String,
default: '',
},
iconPrefix: {
type: String,
default: '',
},
icons: {
type: Array,
default: function() {
return [];
}
},
// Wrapper related props (should be passed into wrapper component)
preventWrap: {
type: Boolean,
default: false
},
label: {
type: String
},
description: {
type: String
},
wrapperCss: {
type: Array,
default: function() {
return [];
}
},
},
data() {
return {
currentValue: this.value,
currentId: this.elementId,
filterQuery: '',
panelActive: false,
prefixedIcons: [],
};
},
watch: {
value( val ) {
this.setCurrentValue( val );
},
},
mounted() {
if ( ! this.currentId && this.name ) {
this.currentId = 'cx_' + this.name;
}
this.icons.forEach( icon => {
this.prefixedIcons.push( this.iconPrefix + icon )
} );
},
computed: {
filteredIcons() {
if ( ! this.filterQuery ) {
return this.prefixedIcons;
} else {
return this.prefixedIcons.filter( icon => {
return icon.includes( this.filterQuery );
});
}
},
},
methods: {
handleEnter( event ) {
this.$emit( 'on-enter', event );
},
handleKeydown( event ) {
this.$emit( 'on-keydown', event );
},
handleKeypress( event ) {
this.$emit( 'on-keypress', event );
},
handleKeyup( event ) {
this.$emit( 'on-keyup', event );
},
handleFocus( event ) {
this.panelActive = true;
this.$emit( 'on-focus', event );
},
handleBlur( event ) {
this.$emit( 'on-blur', event );
},
seclectIcon( icon ) {
this.$emit( 'input', icon );
this.setCurrentValue( icon );
this.$emit( 'on-change', icon );
this.closePanel();
},
handleInput( event ) {
let value = event.target.value;
this.filterQuery = value;
this.$emit( 'input', value );
this.setCurrentValue( value );
this.$emit( 'on-change', event );
},
handleChange ( event ) {
this.$emit( 'on-input-change', event );
},
setCurrentValue ( value ) {
if ( value === this.currentValue ) {
return;
}
this.currentValue = value;
},
onClickOutside( event ) {
this.closePanel();
},
closePanel() {
if ( this.panelActive ) {
this.panelActive = false;
this.filterQuery = '';
this.$emit( 'on-panel-closed' );
}
}
},
};
export default Iconpicker;

View File

@@ -0,0 +1,154 @@
import { oneOf } from '../../utils/assist';
import { checkConditions } from '../../mixins/check-conditions';
const Input = {
name: 'cx-vui-input',
template: '#cx-vui-input',
mixins: [ checkConditions ],
props: {
type: {
validator ( value ) {
return oneOf(value, ['text', 'textarea', 'password', 'url', 'email', 'date', 'number', 'tel']);
},
default: 'text'
},
value: {
type: [String, Number],
default: ''
},
size: {
validator (value) {
return oneOf( value, [ 'small', 'large', 'default', 'fullwidth' ] );
},
default: 'default'
},
placeholder: {
type: String,
default: ''
},
maxlength: {
type: Number
},
disabled: {
type: Boolean,
default: false
},
error: {
type: Boolean,
default: false
},
readonly: {
type: Boolean,
default: false
},
name: {
type: String
},
autofocus: {
type: Boolean,
default: false
},
autocomplete: {
validator (value) {
return oneOf(value, ['on', 'off']);
},
default: 'off'
},
elementId: {
type: String
},
conditions: {
type: Array,
default: function() {
return [];
}
},
// Wrapper related props (should be passed into wrapper component)
preventWrap: {
type: Boolean,
default: false
},
label: {
type: String
},
description: {
type: String
},
wrapperCss: {
type: Array,
default: function() {
return [];
}
},
},
data() {
return {
currentValue: this.value,
currentId: this.elementId,
};
},
watch: {
value( val ) {
this.setCurrentValue( val );
},
},
mounted() {
if ( ! this.currentId && this.name ) {
this.currentId = 'cx_' + this.name;
}
},
computed: {
controlClasses() {
var classesList = [ 'cx-vui-input' ]
classesList.push( 'size-' + this.size );
if ( this.error ) {
classesList.push( 'has-error' );
}
return classesList;
},
},
methods: {
handleEnter( event ) {
this.$emit( 'on-enter', event );
},
handleKeydown( event ) {
this.$emit( 'on-keydown', event );
},
handleKeypress( event ) {
this.$emit( 'on-keypress', event );
},
handleKeyup ( event ) {
this.$emit( 'on-keyup', event );
},
handleFocus ( event ) {
this.$emit( 'on-focus', event );
},
handleBlur ( event ) {
this.$emit( 'on-blur', event );
},
handleInput ( event ) {
let value = event.target.value;
this.$emit( 'input', value );
this.setCurrentValue( value );
this.$emit( 'on-change', event );
},
handleChange ( event ) {
this.$emit( 'on-input-change', event );
},
setCurrentValue ( value ) {
if ( value === this.currentValue ) {
return;
}
this.currentValue = value;
},
},
};
export default Input;

View File

@@ -0,0 +1,124 @@
import { oneOf } from '../../utils/assist';
import { checkConditions } from '../../mixins/check-conditions';
const Radio = {
name: 'cx-vui-radio',
template: '#cx-vui-radio',
mixins: [ checkConditions ],
props: {
value: {
default: ''
},
disabled: {
type: Boolean,
default: false
},
name: {
type: String
},
optionsList: {
type: Array,
default() {
return [];
}
},
elementId: {
type: String
},
conditions: {
type: Array,
default() {
return [];
}
},
// Wrapper related props (should be passed into wrapper component)
preventWrap: {
type: Boolean,
default: false
},
label: {
type: String
},
description: {
type: String
},
wrapperCss: {
type: Array,
default: function() {
return [];
}
},
},
data() {
return {
currentValue: this.value,
currentId: this.elementId,
optionInFocus: null,
};
},
watch: {
value( val ) {
this.setCurrentValue( val );
},
},
mounted() {
if ( ! this.currentId && this.name ) {
this.currentId = 'cx_' + this.name;
}
},
methods: {
handleEnter( event ) {
this.$emit( 'on-enter', event );
},
handleClick( event ) {
this.$emit( 'on-click', event );
},
handleFocus( event, value ) {
if ( this.disabled ) {
return;
}
this.optionInFocus = value;
this.$emit( 'on-focus', event, value );
},
handleBlur ( event, value ) {
if ( this.disabled ) {
return;
}
if ( value === this.optionInFocus ) {
this.optionInFocus = null;
}
this.$emit( 'on-blur', event, value );
},
handleInput ( event, value ) {
if ( this.disabled ) {
return;
}
this.setCurrentValue( value );
this.$emit( 'input', this.currentValue );
this.$emit( 'on-change', event );
},
isOptionInFocus( value ) {
return value === this.optionInFocus;
},
setCurrentValue( value ) {
if ( value !== this.currentValue ) {
this.currentValue = value;
}
},
},
};
export default Radio;

View File

@@ -0,0 +1,195 @@
import { oneOf } from '../../utils/assist';
import { checkConditions } from '../../mixins/check-conditions';
const SelectPlain = {
name: 'cx-vui-select',
template: '#cx-vui-select',
mixins: [ checkConditions ],
props: {
value: {
type: [String, Number, Array],
default: ''
},
size: {
validator (value) {
return oneOf( value, [ 'small', 'large', 'default', 'fullwidth' ] );
},
default: 'default'
},
placeholder: {
type: String,
default: ''
},
optionsList: {
type: Array,
default: function() {
return [];
}
},
disabled: {
type: Boolean,
default: false
},
readonly: {
type: Boolean,
default: false
},
name: {
type: String
},
multiple: {
type: Boolean,
default: false
},
elementId: {
type: String
},
conditions: {
type: Array,
default: function() {
return [];
}
},
remote: {
type: Boolean,
default: false
},
remoteCallback: {
type: Function
},
// Wrapper related props (should be passed into wrapper component)
preventWrap: {
type: Boolean,
default: false
},
label: {
type: String
},
description: {
type: String
},
wrapperCss: {
type: Array,
default: function() {
return [];
}
},
},
data() {
return {
options: this.optionsList,
currentValue: this.value,
currentId: this.elementId,
};
},
watch: {
value( val ) {
this.storeCurrentValue( val );
},
optionsList( options ) {
this.setOptions( options );
},
},
created() {
if ( this.multiple ) {
if ( this.currentValue && 'object' !== typeof this.currentValue ) {
this.currentValue = [ this.currentValue ];
}
} else {
if ( this.currentValue && 'object' === typeof this.currentValue ) {
this.currentValue = this.currentValue[0];
}
}
},
mounted() {
if ( ! this.currentId && this.name ) {
this.currentId = 'cx_' + this.name;
}
if ( this.remote && this.remoteCallback ) {
const promise = this.remoteCallback();
if ( promise && promise.then ) {
promise.then( options => {
if ( options ) {
this.options = options;
}
} );
}
}
},
methods: {
controlClasses() {
var classesList = [ 'cx-vui-select' ]
classesList.push( 'size-' + this.size );
return classesList;
},
handleFocus ( event ) {
this.$emit( 'on-focus', event );
},
handleBlur ( event ) {
this.$emit( 'on-blur', event );
},
handleInput() {
this.$emit( 'input', this.currentValue );
this.$emit( 'on-change', event );
},
storeCurrentValue( value ) {
if ( this.multiple ) {
if ( oneOf( value, this.currentValue ) ) {
return;
}
if ( 'object' === typeof value ) {
if ( '[object Array]' === Object.prototype.toString.call( value ) ) {
this.currentValues.concat( value );
} else {
this.currentValues.push( value );
}
} else {
this.currentValue.push( value );
}
} else {
if ( value === this.currentValue ) {
return;
}
this.currentValue = value;
}
},
setOptions( options ) {
this.options = options;
},
isOptionSelected( option ) {
if ( ! this.currentValue ) {
return false;
}
if ( this.multiple ) {
return oneOf( option.value, this.currentValue );
} else {
return option.value === this.currentValue;
}
},
},
};
export default SelectPlain;

View File

@@ -0,0 +1,134 @@
import { checkConditions } from '../../mixins/check-conditions';
const Switcher = {
name: 'cx-vui-switcher',
template: '#cx-vui-switcher',
mixins: [ checkConditions ],
props: {
value: {
type: [String, Number, Boolean],
default: ''
},
disabled: {
type: Boolean,
default: false
},
name: {
type: String
},
elementId: {
type: String
},
conditions: {
type: Array,
default: function() {
return [];
}
},
returnTrue: {
type: [String, Number, Boolean],
default: true,
},
returnFalse: {
type: [String, Number, Boolean],
default: '',
},
// Wrapper related props (should be passed into wrapper component)
preventWrap: {
type: Boolean,
default: false
},
label: {
type: String
},
description: {
type: String
},
wrapperCss: {
type: Array,
default: function() {
return [];
}
},
},
data() {
return {
currentValue: this.value,
currentId: this.elementId,
isOn: false,
inFocus: false,
};
},
watch: {
value( val ) {
this.setCurrentValue( val );
if ( val === this.returnTrue ) {
this.isOn = true;
} else {
this.isOn = false;
}
},
},
mounted() {
if ( ! this.currentId && this.name ) {
this.currentId = 'cx_' + this.name;
}
if ( this.value === this.returnTrue ) {
this.isOn = true;
}
},
methods: {
handleEnter( event ) {
this.$emit( 'on-enter', event );
this.switchState();
this.inFocus = true;
},
handleFocus ( event ) {
this.inFocus = true;
this.$emit( 'on-focus', event );
},
handleBlur ( event ) {
this.inFocus = false;
this.$emit( 'on-blur', event );
},
switchState () {
let value;
this.isOn = ! this.isOn;
if ( this.isOn ) {
value = this.returnTrue;
} else {
value = this.returnFalse;
}
this.$emit( 'input', value );
this.setCurrentValue( value );
this.$emit( 'on-change', event );
this.inFocus = false;
},
handleChange ( event ) {
this.$emit( 'on-input-change', event );
},
setCurrentValue ( value ) {
if ( value === this.currentValue ) {
return;
}
this.currentValue = value;
},
},
};
export default Switcher;

View File

@@ -0,0 +1,138 @@
import { oneOf } from '../../utils/assist';
import { checkConditions } from '../../mixins/check-conditions';
const Input = {
name: 'cx-vui-textarea',
template: '#cx-vui-textarea',
mixins: [ checkConditions ],
props: {
value: {
type: [String, Number],
default: ''
},
size: {
validator (value) {
return oneOf( value, [ 'small', 'large', 'default', 'fullwidth' ] );
},
default: 'default'
},
placeholder: {
type: String,
default: ''
},
rows: {
type: Number
},
disabled: {
type: Boolean,
default: false
},
error: {
type: Boolean,
default: false
},
readonly: {
type: Boolean,
default: false
},
name: {
type: String
},
elementId: {
type: String
},
conditions: {
type: Array,
default: function() {
return [];
}
},
// Wrapper related props (should be passed into wrapper component)
preventWrap: {
type: Boolean,
default: false
},
label: {
type: String
},
description: {
type: String
},
wrapperCss: {
type: Array,
default: function() {
return [];
}
},
},
data() {
return {
currentValue: this.value,
currentId: this.elementId,
};
},
watch: {
value( val ) {
this.setCurrentValue( val );
},
},
mounted() {
if ( ! this.currentId && this.name ) {
this.currentId = 'cx_' + this.name;
}
},
computed: {
controlClasses() {
var classesList = [ 'cx-vui-textarea' ]
classesList.push( 'size-' + this.size );
if ( this.error ) {
classesList.push( 'has-error' );
}
return classesList;
},
},
methods: {
handleEnter( event ) {
this.$emit( 'on-enter', event );
},
handleKeydown( event ) {
this.$emit( 'on-keydown', event );
},
handleKeypress( event ) {
this.$emit( 'on-keypress', event );
},
handleKeyup ( event ) {
this.$emit( 'on-keyup', event );
},
handleFocus ( event ) {
this.$emit( 'on-focus', event );
},
handleBlur ( event ) {
this.$emit( 'on-blur', event );
},
handleInput ( event ) {
let value = event.target.value;
this.$emit( 'input', value );
this.setCurrentValue( value );
this.$emit( 'on-change', event );
},
handleChange ( event ) {
this.$emit( 'on-input-change', event );
},
setCurrentValue ( value ) {
if ( value === this.currentValue ) {
return;
}
this.currentValue = value;
},
},
};
export default Input;

View File

@@ -0,0 +1,121 @@
import { oneOf } from '../../utils/assist';
import { checkConditions } from '../../mixins/check-conditions';
const Button = {
name: 'cx-vui-button',
template: '#cx-vui-button',
mixins: [ checkConditions ],
props: {
type: {
validator ( value ) {
return oneOf( value, [ 'button', 'submit', 'reset' ] );
},
default: 'button'
},
buttonStyle: {
validator ( value ) {
return oneOf( value, [ 'default', 'accent', 'link-accent', 'link-error' ] );
},
default: 'default'
},
size: {
validator ( value ) {
return oneOf( value, [ 'default', 'mini', 'link' ] );
},
default: 'default'
},
disabled: {
type: Boolean,
default: false
},
loading: {
type: Boolean,
default: false
},
customCss: {
type: String,
},
url: {
type: String,
},
target: {
type: String,
},
tagName: {
validator( value ) {
return oneOf( value, [ 'a', 'button' ] );
},
default: 'button'
},
elementId: {
type: String
},
conditions: {
type: Array,
default() {
return [];
}
},
},
data() {
return {
baseClass: 'cx-vui-button',
};
},
computed: {
classesList() {
let classesList = [
this.baseClass,
this.baseClass + '--style-' + this.buttonStyle,
this.baseClass + '--size-' + this.size,
];
if ( this.loading ) {
classesList.push( this.baseClass + '--loading' );
}
if ( this.disabled ) {
classesList.push( this.baseClass + '--disabled' );
}
if ( this.customCss ) {
classesList.push( this.customCss );
}
return classesList;
},
tagAtts() {
let atts = {};
if ( 'a' === this.tagName ) {
if ( this.url ) {
atts.href = this.url;
}
if ( this.target ) {
atts.target = this.target;
}
} else {
atts.type = this.type;
}
return atts;
}
},
methods: {
handleClick() {
if ( this.loading || this.disabled ) {
return;
}
this.$emit( 'click', event );
}
},
};
export default Button;

View File

@@ -0,0 +1,53 @@
import { checkConditions } from '../../mixins/check-conditions';
const Collapse = {
name: 'cx-vui-collapse',
template: '#cx-vui-collapse',
mixins: [ checkConditions ],
props: {
collapsed: {
type: Boolean,
default: false
},
conditions: {
type: Array,
default() {
return [];
}
},
},
data() {
return {
state: '',
};
},
mounted() {
if ( this.collapsed ) {
this.state = 'collapsed';
}
},
computed: {
iconArrow() {
if ( 'collapsed' === this.state ) {
return 'dashicons-arrow-right-alt2';
} else {
return 'dashicons-arrow-down-alt2';
}
},
},
methods: {
switchState() {
if ( 'collapsed' === this.state ) {
this.state = '';
} else {
this.state = 'collapsed';
}
this.$emit( 'state-switched', this.state );
},
},
};
export default Collapse;

View File

@@ -0,0 +1,52 @@
import { wrapperClasses } from '../../mixins/wrapper-classes';
import { checkConditions } from '../../mixins/check-conditions';
const ComponentWrapper = {
name: 'cx-vui-component-wrapper',
template: '#cx-vui-component-wrapper',
mixins: [ wrapperClasses, checkConditions ],
props: {
elementId: {
type: String
},
label: {
type: String
},
description: {
type: String
},
preventWrap: {
type: Boolean,
default: false
},
wrapperCss: {
type: Array,
default: function() {
return [];
}
},
conditions: {
type: Array,
default() {
return [];
}
},
},
computed: {
wrapperClassesRaw() {
let classesList = [ 'cx-vui-component-raw' ];
if ( this.wrapperCss ) {
this.wrapperCss.forEach( className => {
classesList.push( className );
} );
}
return classesList;
}
}
};
export default ComponentWrapper;

View File

@@ -0,0 +1,18 @@
const ListTableHeading = {
name: 'cx-vui-list-table-heading',
template: '#cx-vui-list-table-heading',
props: {
slots: {
type: Array,
default() {
return [];
}
},
className: {
type: String,
default: '',
},
},
};
export default ListTableHeading;

View File

@@ -0,0 +1,27 @@
import { checkConditions } from '../../mixins/check-conditions';
const ListTableItem = {
name: 'cx-vui-list-table-item',
template: '#cx-vui-list-table-item',
mixins: [ checkConditions ],
props: {
slots: {
type: Array,
default() {
return [];
}
},
conditions: {
type: Array,
default() {
return [];
}
},
className: {
type: String,
default: '',
},
},
};
export default ListTableItem;

View File

@@ -0,0 +1,25 @@
import { checkConditions } from '../../mixins/check-conditions';
const ListTable = {
name: 'cx-vui-list-table',
template: '#cx-vui-list-table',
mixins: [ checkConditions ],
props: {
conditions: {
type: Array,
default() {
return [];
}
},
isEmpty: {
type: Boolean,
default: false,
},
emptyMessage: {
type: String,
default: '',
},
},
};
export default ListTable;

View File

@@ -0,0 +1,72 @@
const NoticeComponent = {
name: 'cx-vui-notice',
template: '#cx-vui-notice',
data: function() {
return {
stack: {},
destroyQueue: {},
}
},
methods: {
addToStack: function( item, itemID ) {
var self = this;
var destroyTimeout = setTimeout( function() {
self.destroyItem( itemID );
}, item.duration );
self.$set( self.stack, itemID, item );
self.$set( self.destroyQueue, itemID, destroyTimeout );
},
destroyItem: function( itemID ) {
this.$delete( this.stack, itemID );
if ( this.destroyQueue[ itemID ] ) {
clearTimeout( this.destroyQueue[ itemID ] );
this.$delete( this.destroyQueue, itemID );
}
},
destroyAll: function() {
for ( var itemID in this.destroyQueue ) {
console.log( this.destroyQueue[ itemID ] );
clearTimeout( this.destroyQueue[ itemID ] );
}
this.stack = {};
this.destroyQueue = {};
},
getIcon: function( type ) {
var icon;
switch ( type ) {
case 'success':
icon = '<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><path d="M6.38498 12.0188L13.5962 4.80751L12.4695 3.64319L6.38498 9.7277L3.53052 6.87324L2.40376 8L6.38498 12.0188ZM2.32864 2.3662C3.9061 0.788732 5.79656 0 8 0C10.2034 0 12.0814 0.788732 13.6338 2.3662C15.2113 3.91862 16 5.79656 16 8C16 10.2034 15.2113 12.0939 13.6338 13.6714C12.0814 15.2238 10.2034 16 8 16C5.79656 16 3.9061 15.2238 2.32864 13.6714C0.776213 12.0939 0 10.2034 0 8C0 5.79656 0.776213 3.91862 2.32864 2.3662Z"/></svg>';
break;
case 'error':
icon = '<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><path d="M8.71489 10.1136V6.71605H7.28511V10.1136H8.71489ZM8.71489 13.4716V11.7728H7.28511V13.4716H8.71489ZM0 16L8 0L16 16H0Z"/></svg>';
break;
default:
icon = '<svg viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><path d="M8.78873 5.59624V3.98122H7.21127V5.59624H8.78873ZM8.78873 12.0188V7.21127H7.21127V12.0188H8.78873ZM2.32864 2.3662C3.9061 0.788732 5.79656 0 8 0C10.2034 0 12.0814 0.788732 13.6338 2.3662C15.2113 3.91862 16 5.79656 16 8C16 10.2034 15.2113 12.0939 13.6338 13.6714C12.0814 15.2238 10.2034 16 8 16C5.79656 16 3.9061 15.2238 2.32864 13.6714C0.776213 12.0939 0 10.2034 0 8C0 5.79656 0.776213 3.91862 2.32864 2.3662Z"/></svg>';
break;
}
return icon;
}
},
};
export default NoticeComponent;

View File

@@ -0,0 +1,51 @@
import NoticeComponent from './notice-component';
const CXNotice = {
instance: null,
stack: {},
newInstance: function() {
var NoticeComponentClass = Vue.extend( NoticeComponent );
this.instance = new NoticeComponentClass({
propsData: { type: 'primary' }
});
this.instance.$mount();
document.body.appendChild( this.instance.$el );
},
getRandId: function() {
// Generates random string with 10 characters length
return Math.random().toString( 36 ).substring( 2, 7 ) + Math.random().toString( 36 ).substring( 2, 7 );
},
add: function( options, id ) {
id = id || this.getRandId();
if ( ! this.instance ) {
this.newInstance();
}
options.duration = options.duration || 4500;
options.type = options.type || 'info';
this.instance.addToStack( options, id );
},
close: function( id ) {
if ( id ) {
id = id.toString();
if ( this.instance ) {
this.instance.destroyItem( id );
}
} else {
return false;
}
},
closeAll: function() {
this.instance.destroyAll();
},
};
export default CXNotice;

View File

@@ -0,0 +1,70 @@
const Popup = {
name: 'cx-vui-popup',
template: '#cx-vui-popup',
props: {
value: {
type: Boolean,
default: false,
},
overlay: {
type: Boolean,
default: true,
},
close: {
type: Boolean,
default: true,
},
header: {
type: Boolean,
default: true,
},
footer: {
type: Boolean,
default: true,
},
okLabel: {
type: String,
default: 'OK',
},
cancelLabel: {
type: String,
default: 'Cancel',
},
bodyWidth: {
type: String,
default: 'auto',
},
},
data() {
return {
currentValue: this.value,
};
},
watch: {
value( val ) {
this.setCurrentValue( val );
}
},
methods: {
handleCancel() {
this.setCurrentValue( false );
this.$emit( 'input', false );
this.$emit( 'on-cancel' );
},
handleOk() {
this.setCurrentValue( false );
this.$emit( 'input', false );
this.$emit( 'on-ok' );
},
setCurrentValue( value ) {
if ( this.currentValue === value ) {
return;
}
this.currentValue = value;
},
},
};
export default Popup;

View File

@@ -0,0 +1,47 @@
import { ElementMixin, HandleDirective } from 'vue-slicksort';
const RepeaterItem = {
name: 'cx-vui-repeater-item',
template: '#cx-vui-repeater-item',
mixins: [ ElementMixin ],
directives: { handle: HandleDirective },
props: {
title: {
type: String,
},
subtitle: {
type: String,
},
collapsed: {
type: Boolean,
default: true,
},
index: {
type: Number,
},
},
data() {
return {
fieldData: this.field,
isCollapsed: this.collapsed,
showConfirmTip: false,
};
},
methods: {
handleCopy() {
this.$emit( 'clone-item', this.index );
},
handleDelete() {
this.showConfirmTip = true;
},
confrimDeletion() {
this.showConfirmTip = false;
this.$emit( 'delete-item', this.index );
},
cancelDeletion() {
this.showConfirmTip = false;
},
},
};
export default RepeaterItem;

View File

@@ -0,0 +1,53 @@
import { ContainerMixin } from 'vue-slicksort';
import { checkConditions } from '../../mixins/check-conditions';
const Repeater = {
name: 'cx-vui-repeater',
template: '#cx-vui-repeater',
mixins: [ ContainerMixin, checkConditions ],
props: {
buttonLabel: {
type: String,
},
buttonStyle: {
type: String,
default: 'accent',
},
buttonSize: {
type: String,
default: 'default',
},
value: {
type: Array,
default() {
return [];
}
},
distance: {
type: Number,
default: 20,
},
useDragHandle: {
type: Boolean,
default: true,
},
conditions: {
type: Array,
default() {
return [];
}
},
},
data() {
return {
inFocus: false,
}
},
methods: {
handleClick( event ) {
this.$emit( 'add-new-item', event );
},
},
};
export default Repeater;

View File

@@ -0,0 +1,27 @@
const TabsPanel = {
name: 'cx-vui-tabs-panel',
template: '#cx-vui-tabs-panel',
props: {
tab: {
type: String,
default: ''
},
name: {
type: String,
default: ''
},
label: {
type: String,
default: ''
},
},
data() {
return {
show: false,
};
},
methods: {
},
};
export default TabsPanel;

View File

@@ -0,0 +1,93 @@
import { checkConditions } from '../../mixins/check-conditions';
import { oneOf } from '../../utils/assist';
const Tabs = {
name: 'cx-vui-tabs',
template: '#cx-vui-tabs',
mixins: [ checkConditions ],
props: {
value: {
type: [ String, Number ],
default: ''
},
name: {
type: String,
default: ''
},
invert: {
type: Boolean,
default: false,
},
inPanel: {
type: Boolean,
default: false,
},
layout: {
validator( value ) {
return oneOf( value, [ 'horizontal', 'vertical' ] );
},
default: 'horizontal',
},
conditions: {
type: Array,
default() {
return [];
}
},
},
data() {
return {
navList: [],
activeTab: this.value,
}
},
mounted() {
const tabs = this.getTabs();
this.navList = tabs;
if ( ! this.activeTab ) {
this.activeTab = tabs[0].name;
}
this.updateState();
},
methods: {
isActive( name ) {
return ( name === this.activeTab );
},
onTabClick( tab ) {
this.activeTab = tab;
this.$emit( 'input', this.activeTab );
this.updateState();
},
updateState() {
const tabs = this.getTabs();
tabs.forEach( tab => {
tab.show = this.activeTab === tab.name;
} );
},
getTabs() {
const allTabs = this.$children.filter( item => {
return 'cx-vui-tabs-panel' === item.$options.name;
} );
const tabs = [];
allTabs.forEach( item => {
if ( item.tab && this.name ) {
if ( item.tab === this.name ) {
tabs.push( item );
}
} else {
tabs.push( item );
}
});
return tabs;
},
},
};
export default Tabs;

View File

@@ -0,0 +1,7 @@
const Title = {
name: 'cx-vui-title',
template: '#cx-vui-title',
props: {},
};
export default Title;

View File

@@ -0,0 +1,48 @@
import Title from './components/layout/title';
import Collapse from './components/layout/collapse';
import ComponentWrapper from './components/layout/component-wrapper';
import Button from './components/layout/button';
import Repeater from './components/layout/repeater';
import RepeaterItem from './components/layout/repeater-item';
import Popup from './components/layout/popup';
import ListTable from './components/layout/list-table';
import ListTableItem from './components/layout/list-table-item';
import ListTableHeading from './components/layout/list-table-heading';
import Tabs from './components/layout/tabs';
import TabsPanel from './components/layout/tabs-panel';
import CXNotice from './components/layout/notice';
import Input from './components/form/input';
import Textarea from './components/form/textarea';
import Switcher from './components/form/switcher';
import Iconpicker from './components/form/iconpicker';
import SelectPlain from './components/form/select';
import FilterableSelect from './components/form/f-select';
import Checkbox from './components/form/checkbox';
import Radio from './components/form/radio';
import './../scss/cx-vue-ui.scss';
Vue.component( Title.name, Title );
Vue.component( Collapse.name, Collapse );
Vue.component( ComponentWrapper.name, ComponentWrapper );
Vue.component( Button.name, Button );
Vue.component( Repeater.name, Repeater );
Vue.component( RepeaterItem.name, RepeaterItem );
Vue.component( Popup.name, Popup );
Vue.component( ListTable.name, ListTable );
Vue.component( ListTableItem.name, ListTableItem );
Vue.component( ListTableHeading.name, ListTableHeading );
Vue.component( Tabs.name, Tabs );
Vue.component( TabsPanel.name, TabsPanel );
Vue.component( Input.name, Input );
Vue.component( Textarea.name, Textarea );
Vue.component( Switcher.name, Switcher );
Vue.component( Iconpicker.name, Iconpicker );
Vue.component( SelectPlain.name, SelectPlain );
Vue.component( FilterableSelect.name, FilterableSelect );
Vue.component( Checkbox.name, Checkbox );
Vue.component( Radio.name, Radio );
Vue.prototype.$CXNotice = CXNotice;

View File

@@ -0,0 +1,91 @@
import { oneOf } from '../utils/assist';
export const checkConditions = {
methods: {
isVisible() {
if ( ! this.conditions.length ) {
return true
} else {
let conditionsMet = [];
let operator = 'AND';
let conditionsLength = this.conditions.length;
for ( var i = 0; i < this.conditions.length; i++) {
if ( this.conditions[ i ].operator ) {
operator = this.conditions[ i ].operator;
conditionsLength--;
continue;
}
switch ( this.conditions[ i ].compare ) {
case 'equal':
if ( this.conditions[ i ].input === this.conditions[ i ].value ) {
conditionsMet.push( this.conditions[ i ].value );
}
break;
case 'not_equal':
if ( this.conditions[ i ].input !== this.conditions[ i ].value ) {
conditionsMet.push( this.conditions[ i ].value );
}
break;
case 'in':
if ( oneOf( this.conditions[ i ].input, this.conditions[ i ].value ) ) {
conditionsMet.push( this.conditions[ i ].value );
}
break;
case 'not_in':
if ( ! oneOf( this.conditions[ i ].input, this.conditions[ i ].value ) ) {
conditionsMet.push( this.conditions[ i ].value );
}
break;
case 'contains':
if ( oneOf( this.conditions[ i ].value, this.conditions[ i ].input ) ) {
conditionsMet.push( this.conditions[ i ].value );
}
break;
case 'not_contains':
if ( ! oneOf( this.conditions[ i ].value, this.conditions[ i ].input ) ) {
conditionsMet.push( this.conditions[ i ].value );
}
break;
}
};
switch ( operator ) {
case 'AND':
return conditionsMet.length === conditionsLength;
case 'OR':
if ( conditionsMet.length ) {
return true;
} else {
return false;
}
}
}
},
}
}

View File

@@ -0,0 +1,17 @@
export const wrapperClasses = {
methods: {
wrapperClasses() {
var wrapperClassesList = [ 'cx-vui-component' ];
if ( this.wrapperCss.length ) {
this.wrapperCss.forEach( className => {
wrapperClassesList.push( 'cx-vui-component--' + className );
} );
}
return wrapperClassesList;
},
}
}

View File

@@ -0,0 +1,27 @@
export function oneOf ( value, validList ) {
for ( let i = 0; i < validList.length; i++ ) {
if ( value == validList[ i ] ) {
return true;
}
}
return false;
}
export function arraysEqual( arr1, arr2 ) {
if ( arr1.length !== arr2.length ) {
return false;
}
for ( var i = arr1.length; i--; ) {
if ( arr1[i] !== arr2[i] ) {
return false;
}
}
return true;
}

View File

@@ -0,0 +1,56 @@
.cx-vui-component {
display: flex;
padding: 20px;
font-family: $font_family;
+ .cx-vui-component {
border-top: 1px solid $color__border-in-panel;
}
&--equalwidth {
justify-content: space-between;
.cx-vui-component__meta {
max-width: 49%;
flex: 0 0 49%;
+ .cx-vui-component__control {
max-width: 49%;
flex: 0 0 49%;
}
}
}
&--vertical-fullwidth {
flex-direction: column;
padding-left: 0;
padding-right: 0;
.cx-vui-component__meta {
padding: 0 0 20px;
margin: 0 0 25px;
border-bottom: 1px solid $color__border-in-panel;
}
.cx-vui-component__label {
padding: 0 0 5px;
}
}
&--fullwidth-control {
.cx-vui-component__control {
max-width: 100%;
flex: 0 0 100%;
}
}
&__meta {
display: flex;
flex-direction: column;
align-items: flex-start;
}
&__label {
display: block;
font-size: 15px;
line-height: 20px;
color: $color__heading;
font-weight: 500;
}
&__desc {
font-size: 13px;
line-height: 17px;
color: $color__text;
padding: 0 0 4px;
}
}

View File

@@ -0,0 +1,38 @@
.cx-vui-text {
font-size: 13px;
line-height: 20px;
color: $color__text;
padding: 15px 0;
font-family: $font_family;
}
.cx-vui-hr {
display: block;
width: 100%;
height: 0;
border-top: 1px solid $color__border-off-panel;
margin: 30px 0;
}
.cx-vui-notice {
padding: 20px;
color: $color__text;
font-size: 15px;
line-height: 23px;
&--error {
background: $color__error-light;
}
&--success {
background: $color__success-light;
}
}
.cx-vui-inline-notice {
font-weight: bold;
&--error {
color: $color__error;
}
&--success {
color: $color__success;
}
}

View File

@@ -0,0 +1,13 @@
.cx-vui-panel {
background: $color__bg-panel;
box-shadow: 0px 2px 6px rgba( 35, 40, 45, 0.07 );
border-radius: 6px;
margin-bottom: 30px;
font-family: $font_family;
}
.cx-vui-inner-panel {
background: $color__bg-canvas;
border-radius: 4px;
padding: 30px;
}

View File

@@ -0,0 +1,67 @@
.cx-vui-popup {
position: fixed;
z-index: 999;
left: 0;
right: 0;
top: 0;
bottom: 0;
display: flex;
align-items: center;
justify-content: center;
&__overlay {
background: $color__heading;
opacity: .5;
position: absolute;
left: 0;
right: 0;
top: 0;
bottom: 0;
z-index: 1;
}
&__body {
background: $color__bg-panel;
box-shadow: 0px 2px 6px rgba( 35, 40, 45, 0.07 );
border-radius: 6px;
font-family: $font_family;
position: relative;
z-index: 2;
padding: 30px 40px 40px;
}
&__header {
padding: 0 0 10px;
}
&__content {
font-size: 13px;
line-height: 20px;
color: $color__text;
p {
font-size: 13px;
line-height: 20px;
color: $color__text;
margin: 0;
padding: 0 0 20px;
}
}
&__footer {
padding: 20px 0 0;
display: flex;
align-items: center;
.cx-vui-button + .cx-vui-button {
margin: 0 0 0 10px;
}
}
&__close {
position: absolute;
right: 12px;
top: 15px;
cursor: pointer;
path {
fill: $color__border-off-panel;
}
&:hover {
path {
fill: $color__text;
}
}
}
}

View File

@@ -0,0 +1,19 @@
.cs-vui-title,
.wrap .cs-vui-title {
font-weight: 500;
font-size: 24px;
line-height: 37px;
color: $color__heading;
padding: 0 0 20px;
margin: 0;
font-family: $font_family;
}
.cx-vui-subtitle {
font-weight: 500;
font-size: 18px;
line-height: 27px;
color: $color__heading;
padding: 0;
margin: 0;
font-family: $font_family;
}

View File

@@ -0,0 +1,25 @@
.cx-vui-tooltip {
background: $color__heading;
box-shadow: 0px 1px 4px rgba(35, 40, 45, 0.24);
border-radius: 3px;
padding: 5px 15px;
font-size: 12px;
line-height: 15px;
color: #fff;
bottom: 100%;
position: absolute;
margin: 0 0 10px;
text-align: center;
&:after {
top: 100%;
left: 50%;
margin: 0 0 0 -4px;
width: 0;
height: 0;
border-style: solid;
border-width: 4px 4px 0 4px;
border-color: $color__heading transparent transparent transparent;
content: "";
position: absolute;
}
}

View File

@@ -0,0 +1,145 @@
.cx-vui-button {
cursor: pointer;
display: inline-block;
padding: 0;
margin: 0;
border: none;
box-shadow: 0px 4px 4px rgba(35, 40, 45, 0.24);
border-radius: 4px;
transition: all 150ms linear;
font-weight: 500;
font-family: $font_family;
outline: none;
position: relative;
box-sizing: border-box;
text-decoration: none;
&__content {
display: flex;
justify-content: center;
align-items: center;
.cx-vui-button--loading & {
opacity: 0;
}
}
&--style {
&-default {
background: $color__bg-input;
color: $color__accent;
&:hover {
box-shadow: none;
color: $color__accent;
background: $color__bg-input-hover;
}
}
&-accent {
background: $color__accent;
color: #fff;
&:hover {
box-shadow: none;
color: #fff;
background: $color__accent-hover;
}
}
&-link-accent {
color: $color__accent;
background: none;
box-shadow: none;
path {
fill: $color__accent;
}
&:hover {
color: $color__accent-hover;
path {
fill: $color__accent-hover;
}
}
}
&-link-error {
color: $color__error;
background: none;
box-shadow: none;
path {
fill: $color__error;
}
&:hover {
color: $color__error;
}
}
}
&--size {
&-default {
font-size: 15px;
line-height: 21px;
padding: 12px 25px 13px;
.cx-vui-button__content {
.dashicons {
margin: 0 5px 0 -8px;
}
span + .dashicons {
margin: -8px 0 0 5px;
}
}
}
&-link {
font-size: 15px;
line-height: 18px;
.cx-vui-button__content {
svg {
margin: 0 5px 1px 0;
}
span + svg {
margin: 0 0 1px 5px;
}
}
}
&-mini {
font-size: 13px;
line-height: 19px;
padding: 6px 14px 7px;
.cx-vui-button__content {
.dashicons {
margin: 0 4px 0 -5px;
}
span + .dashicons {
margin: -5px 0 0 4px;
}
}
}
}
&--disabled {
cursor: default;
opacity: .3;
pointer-events: none;
}
&--loading {
cursor: default;
}
&__loader {
position: absolute;
right: 0;
top: 0;
bottom: 0;
left: 0;
display: flex;
align-items: center;
justify-content: center;
.loader-icon {
animation: spin 1200ms infinite linear;
path {
fill: currentColor;
}
}
@keyframes spin {
from {
transform:rotate(0deg);
}
to {
transform:rotate(360deg);
}
}
}
&.fullwidth {
width: 100%;
}
}

Some files were not shown because too many files have changed in this diff Show More