PluginProbe
SellKit – Funnel builder and checkout optimizer for WooCommerce to sell more, faster / 1.7.2
SellKit – Funnel builder and checkout optimizer for WooCommerce to sell more, faster v1.7.2
2.6.0 trunk 1.1.0 1.1.4 1.2.1 1.2.2 1.2.3 1.2.5 1.2.9 1.3.1 1.3.2 1.5.0 1.5.1 1.5.4 1.5.7 1.5.8 1.5.9 1.6.2 1.6.5 1.6.8 1.7.2 1.7.4 1.7.5 1.7.9 1.8.1 All 42 releases
sellkit / includes / elementor / modules / optin / module.php

module.php in SellKit – Funnel builder and checkout optimizer for WooCommerce to sell more, faster 1.7.2, at includes/elementor/modules/optin/module.php

316 lines 10.3 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 defined( 'ABSPATH' ) || die();
4
5 use Elementor\Plugin as Elementor;
6 use Elementor\Icons_Manager as Icon_Manager;
7
8 class Sellkit_Elementor_Optin_Module extends Sellkit_Elementor_Base_Module {
9
10 public static $field_types = [];
11
12 public static $action_types = [];
13
14 public static $messages = [];
15
16 public function __construct() {
17 parent::__construct();
18
19 $this->load_controls();
20 $this->register_field_types();
21 $this->register_action_types();
22 $this->set_messages();
23 $this->localize_editor_nonce();
24 $this->localize_validation_translations();
25
26 if ( is_admin() ) {
27 sellkit()->load_files( [
28 'elementor/controls/file-uploader',
29 ] );
30
31 add_action( 'wp_ajax_sellkit_control_file_upload', [ Sellkit_Elementor_Controls_File_Uploader::class, 'handle_file_upload' ] );
32 }
33 }
34
35 public function get_widgets() {
36 return [ 'optin' ];
37 }
38
39 /**
40 * Load files in "controls" directory which hold the control adding methods.
41 *
42 * @access private
43 * @since 1.5.0
44 */
45 private function load_controls() {
46 sellkit()->load_files( [
47 'elementor/modules/optin/controls/tab-content',
48 'elementor/modules/optin/controls/tab-style',
49 ] );
50 }
51
52 /**
53 * Get types of Optin form fields available.
54 *
55 * @return array
56 *
57 * @access public
58 * @static
59 * @since 1.5.0
60 */
61 public static function get_field_types() {
62 return [
63 'text' => esc_html__( 'Text', 'sellkit' ),
64 'number' => esc_html__( 'Number', 'sellkit' ),
65 'email' => esc_html__( 'Email', 'sellkit' ),
66 'tel' => esc_html__( 'Tel', 'sellkit' ),
67 'textarea' => esc_html__( 'Textarea', 'sellkit' ),
68 'date' => esc_html__( 'Date', 'sellkit' ),
69 'time' => esc_html__( 'Time', 'sellkit' ),
70 'checkbox' => esc_html__( 'Checkbox', 'sellkit' ),
71 'radio' => esc_html__( 'Radio', 'sellkit' ),
72 'select' => esc_html__( 'Select', 'sellkit' ),
73 'address' => esc_html__( 'Address', 'sellkit' ),
74 'acceptance' => esc_html__( 'Acceptance', 'sellkit' ),
75 'hidden' => esc_html__( 'Hidden', 'sellkit' ),
76 ];
77 }
78
79 /**
80 * Registers the field types defined in the get_field_types by creating
81 * instance from their classes.\
82 * Also loads Field_Base class.
83 *
84 * @access private
85 * @since 1.5.0
86 */
87 private function register_field_types() {
88 // Register base class of fields.
89 sellkit()->load_files( [ 'elementor/modules/optin/fields/field-base' ] );
90
91 // Register fields.
92 foreach ( self::get_field_types() as $field_key => $field_label ) {
93 $class_path = "elementor/modules/optin/fields/{$field_key}";
94 sellkit()->load_files( [ $class_path ] );
95
96 $class_name = 'Sellkit_Elementor_Optin_Field_' . ucfirst( $field_key );
97
98 self::$field_types[ $field_key ] = new $class_name();
99 }
100 }
101
102 /**
103 * Get types of available Optin actions.
104 *
105 * @return array
106 *
107 * @access public
108 * @static
109 * @since 1.5.0
110 */
111 public static function get_action_types() {
112 return [
113 'growmatik' => esc_html__( 'Growmatik', 'sellkit' ),
114 'activecampaign' => esc_html__( 'ActiveCampaign', 'sellkit' ),
115 'convertkit' => esc_html__( 'ConvertKit', 'sellkit' ),
116 'drip' => esc_html__( 'Drip', 'sellkit' ),
117 'getresponse' => esc_html__( 'GetResponse', 'sellkit' ),
118 'mailchimp' => esc_html__( 'MailChimp', 'sellkit' ),
119 'mailerlite' => esc_html__( 'MailerLite', 'sellkit' ),
120 'webhook' => esc_html__( 'WebHook', 'sellkit' ),
121 ];
122 }
123
124 /**
125 * Registers the actions defined in the get_action_types by creating
126 * instance from their classes.\
127 * Also loades of Action_Base class, CRM actions trait and creates instance of Download action.
128 *
129 * @access private
130 * @since 1.5.0
131 */
132 private function register_action_types() {
133 // Register base class of actions, AJAX handler and CRM integration trait.
134 sellkit()->load_files(
135 [
136 'elementor/modules/optin/actions/utils/action-base',
137 'elementor/modules/optin/actions/utils/ajax-handler',
138 'elementor/modules/optin/actions/utils/crm-trait',
139 ]
140 );
141
142 // Create AJAX handler instance to register its hooks.
143 new Sellkit_Elementor_Optin_Ajaxhandler();
144
145 // Register every single action.
146 foreach ( self::get_action_types() as $action_key => $action_label ) {
147 $class_path = "elementor/modules/optin/actions/{$action_key}";
148 sellkit()->load_files( [ $class_path ] );
149
150 $class_name = 'Sellkit_Elementor_Optin_Action_' . ucfirst( $action_key );
151
152 self::$action_types[ $action_key ] = new $class_name();
153 }
154
155 // Add Download and Redirect action separately as it should be always
156 // available and not be in the list above.
157 sellkit()->load_files( [ 'elementor/modules/optin/actions/download-redirect' ] );
158
159 new Sellkit_Elementor_Optin_Action_Download_Redirect();
160 }
161
162 /**
163 * Set $messages array propery.
164 *
165 * @access public
166 * @since 1.5.0
167 */
168 public function set_messages() {
169 self::$messages = [
170 'success' => esc_html__( 'The form was sent successfully!', 'sellkit' ),
171 'error' => esc_html__( 'Please check the errors.', 'sellkit' ),
172 'required' => esc_html__( 'Required', 'sellkit' ),
173 ];
174 }
175
176 /**
177 * Renders form field.
178 *
179 * Calls the "render_content" method in the corresponding field class.
180 *
181 * @param object $widget Widget instance.
182 * @param array $field Field settings.
183 *
184 * @access public
185 * @static
186 * @since 1.5.0
187 */
188 public static function render_field( $widget, $field ) {
189 self::$field_types[ $field['type'] ]->render( $widget, $field );
190 }
191
192 /**
193 * Render icon based on settings.
194 *
195 * @param Array $icon_data including "library" and "value".
196 *
197 * @access public
198 * @static
199 * @since 1.5.0
200 * @SuppressWarnings(PHPMD.NPathComplexity)
201 */
202 public static function render_icon( $icon_data ) {
203 // Scenario 1: if font icon experimental feature is activated, it's preferred.
204 if ( Elementor::$instance->experiments->is_feature_active( 'e_font_icon_svg' ) && $icon_data['value'] ) {
205 if ( 'svg' === $icon_data['library'] ) {
206 $font_icon = Icon_Manager::render_uploaded_svg_icon( $icon_data['value'] );
207 } else {
208 $font_icon = Icon_Manager::render_font_icon( $icon_data );
209 }
210
211 if ( ! empty( $font_icon ) ) {
212 echo $font_icon;
213 return;
214 }
215 }
216
217 // Scenario 2: Otherwise, when the user has used font awesome option.
218 if ( 'svg' !== $icon_data['library'] && ! empty( $icon_data['value'] ) ) {
219 echo '<i class="' . esc_attr( $icon_data['value'] ) . '"></i>';
220 return;
221 }
222
223 // Scenario 3: Otherwise, when the user has used upload svg option.
224 if ( 'svg' === $icon_data['library'] && $icon_data['value'] && ! empty( $icon_data['value']['url'] ) ) {
225 echo '<object type="image/svg+xml" data="' . esc_attr( $icon_data['value']['url'] ) . '"></object>';
226 }
227 }
228
229 /**
230 * Get active breakpoint of the Elementor.
231 *
232 * @return array Active Elementor breakpoints and their sizes.
233 * @access public
234 * @static
235 * @since 1.5.0
236 */
237 public static function get_active_breakpoints() {
238 $breakpoints = Elementor::$instance->breakpoints->get_breakpoints_config();
239 $result = [ 'desktop' => '' ];
240
241 foreach ( $breakpoints as $device => $config ) {
242 if ( $config['is_enabled'] ) {
243 $result[ $device ] = $config['value'];
244 }
245 }
246
247 return $result;
248 }
249
250 /**
251 * Localize a nonce for AJAX calls inside editor panel.
252 *
253 * @access private
254 * @since 1.5.0
255 */
256 private function localize_editor_nonce() {
257 add_action( 'elementor/editor/after_enqueue_scripts', function() {
258 wp_localize_script(
259 'sellkit-editor',
260 'sellkitNonceEditorOptin',
261 [ wp_create_nonce( 'sellkit_optin_editor' ) ]
262 );
263 }, 20 );
264 }
265
266 /**
267 * Localize the translation strings needed by JS to render validation errors
268 *
269 * @access private
270 * @since 1.5.0
271 */
272 private function localize_validation_translations() {
273 $translations = [
274 'general' => [
275 'errorExists' => self::$messages['error'],
276 'required' => self::$messages['required'],
277 'invalidEmail' => esc_html__( 'Invalid Email address.', 'sellkit' ),
278 'invalidPhone' => esc_html__( 'The value should only consist numbers and phone characters (-, +, (), etc).', 'sellkit' ),
279 'invalidNumber' => esc_html__( 'Invalid number.', 'sellkit' ),
280 'invalidMaxValue' => esc_html__( 'Value must be less than or equal to MAX_VALUE.', 'sellkit' ),
281 'invalidMinValue' => esc_html__( 'Value must be greater than or equal to MIN_VALUE.', 'sellkit' ),
282 ],
283 // Validation messages specific to Intelligent Tel Input plugin.
284 'itiValidation' => [
285 'invalidCountryCode' => esc_html__( 'Invalid country code.', 'sellkit' ),
286 'tooShort' => esc_html__( 'Phone number is too short.', 'sellkit' ),
287 'tooLong' => esc_html__( 'Phone number is too long.', 'sellkit' ),
288 'areaCodeMissing' => esc_html__( 'Area code is required..', 'sellkit' ),
289 'invalidLength' => esc_html__( 'Phone number has an invalid length.', 'sellkit' ),
290 'invalidGeneral' => esc_html__( 'Invalid phone number.', 'sellkit' ),
291 'typeMismatch' => [
292 '0' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'Fixed Line', 'sellkit' ) . '.',
293 '1' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'Mobile', 'sellkit' ) . '.',
294 '2' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'Fixed Line or Mobile', 'sellkit' ) . '.',
295 '3' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'Toll Free', 'sellkit' ) . '.',
296 '4' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'Premium Rate', 'sellkit' ) . '.',
297 '5' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'Shared Cost', 'sellkit' ) . '.',
298 '6' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'VOIP', 'sellkit' ) . '.',
299 '7' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'Personal Number', 'sellkit' ) . '.',
300 '8' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'Pager', 'sellkit' ) . '.',
301 '9' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'UAN', 'sellkit' ) . '.',
302 '10' => esc_html__( 'Phone number must be of type: ', 'sellkit' ) . esc_html__( 'Voicemail', 'sellkit' ) . '.',
303 ],
304 ],
305 ];
306
307 add_action( 'elementor/frontend/after_enqueue_scripts', function() use ( $translations ) {
308 wp_localize_script(
309 'sellkit-initialize-widgets',
310 'sellkitOptinValidationsTranslations',
311 $translations
312 );
313 }, 20 );
314 }
315 }
316