PluginProbe
UsersWP – Front-end login form, User Registration, User Profile & Members Directory plugin for WP / 1.2.70
UsersWP – Front-end login form, User Registration, User Profile & Members Directory plugin for WP v1.2.70
1.2.74 1.2.73 1.2.72 1.2.71 1.2.70 1.2.69 1.2.68 1.2.67 1.2.66 1.2.65 1.2.64 1.2.63 trunk 1.0.10 1.0.11 1.0.12 1.0.13 1.0.14 1.0.15 1.0.16 1.0.17 1.0.18 1.0.19 1.0.20 1.0.21 All 174 releases
userswp / vendor / ayecode / wp-super-duper / wp-super-duper.php

wp-super-duper.php in UsersWP – Front-end login form, User Registration, User Profile & Members Directory plugin for WP 1.2.70, at vendor/ayecode/wp-super-duper/wp-super-duper.php

5,529 lines 194.3 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 if ( ! defined( 'ABSPATH' ) ) {
3 exit;
4 }
5
6 if ( ! class_exists( 'WP_Super_Duper' ) ) {
7
8 define( 'SUPER_DUPER_VER', '1.2.34' );
9
10 /**
11 * A Class to be able to create a Widget, Shortcode or Block to be able to output content for WordPress.
12 *
13 * Should not be called direct but extended instead.
14 *
15 * Class WP_Super_Duper
16 * @since 1.0.16 change log moved to file change-log.txt - CHANGED
17 * @ver 1.1.1
18 */
19 class WP_Super_Duper extends WP_Widget {
20
21 public $version = SUPER_DUPER_VER;
22 public $font_awesome_icon_version = "5.11.2";
23 public $block_code;
24 public $options;
25 public $base_id;
26 public $settings_hash;
27 public $arguments = array();
28 public $instance = array();
29 private $class_name;
30
31 /**
32 * The relative url to the current folder.
33 *
34 * @var string
35 */
36 public $url = '';
37
38 /**
39 * Take the array options and use them to build.
40 */
41 public function __construct( $options ) {
42 global $sd_widgets;
43
44 $sd_widgets[ $options['base_id'] ] = array(
45 'name' => $options['name'],
46 'class_name' => $options['class_name'],
47 'output_types' => !empty($options['output_types']) ? $options['output_types'] : array()
48 );
49 $this->base_id = $options['base_id'];
50 // lets filter the options before we do anything
51 $options = apply_filters( "wp_super_duper_options", $options );
52 $options = apply_filters( "wp_super_duper_options_{$this->base_id}", $options );
53 $options = $this->add_name_from_key( $options );
54 $this->options = $options;
55
56 $this->base_id = $options['base_id'];
57 $this->arguments = isset( $options['arguments'] ) ? $options['arguments'] : array();
58
59 // nested blocks can't work as a widget
60 if(!empty($this->options['nested-block'])){
61 if(empty($this->options['output_types'])){
62 $this->options['output_types'] = array('shortcode','block');
63 }elseif (($key = array_search('widget', $this->options['output_types'])) !== false) {
64 unset($this->options['output_types'][$key]);
65 }
66 }
67
68 // init parent
69 if(empty($this->options['output_types']) || in_array('widget',$this->options['output_types'])){
70 parent::__construct( $options['base_id'], $options['name'], $options['widget_ops'] );
71 }
72
73
74 if ( isset( $options['class_name'] ) ) {
75 // register widget
76 $this->class_name = $options['class_name'];
77
78 // register shortcode, this needs to be done even for blocks and widgets
79 $this->register_shortcode();
80
81
82 // Fusion Builder (avada) support
83 if ( function_exists( 'fusion_builder_map' ) ) {
84 add_action( 'init', array( $this, 'register_fusion_element' ) );
85 }
86
87 // maybe load the Bricks transformer class
88 if( class_exists('\Bricks\Elements', false) ){
89 add_action( 'init', array( $this, 'load_bricks_element_class' ) );
90 }
91
92 // register block
93 if(empty($this->options['output_types']) || in_array('block',$this->options['output_types'])){
94 add_action( 'admin_enqueue_scripts', array( $this, 'register_block' ) );
95 }
96 }
97
98 // add the CSS and JS we need ONCE
99 global $sd_widget_scripts;
100
101 if ( ! $sd_widget_scripts ) {
102 wp_add_inline_script( 'admin-widgets', $this->widget_js() );
103 wp_add_inline_script( 'customize-controls', $this->widget_js() );
104 wp_add_inline_style( 'widgets', $this->widget_css() );
105
106 // maybe add elementor editor styles
107 add_action( 'elementor/editor/after_enqueue_styles', array( $this, 'elementor_editor_styles' ) );
108
109 $sd_widget_scripts = true;
110
111 // add shortcode insert button once
112 add_action( 'media_buttons', array( $this, 'wp_media_buttons' ), 1 );
113 add_action( 'media_buttons', array( $this, 'shortcode_insert_button' ) );
114 // generatepress theme sections compatibility
115 if ( function_exists( 'generate_sections_sections_metabox' ) ) {
116 add_action( 'generate_sections_metabox', array( $this, 'shortcode_insert_button_script' ) );
117 }
118
119 /* Load script on Divi theme builder page */
120 if ( ( function_exists( 'et_builder_is_tb_admin_screen' ) && et_builder_is_tb_admin_screen() ) || ( function_exists( 'et_builder_d5_enabled' ) && et_builder_d5_enabled() && isset( $_GET['et_fb'] ) && '1' === $_GET['et_fb'] && et_pb_is_allowed( 'use_visual_builder' ) ) ) {
121 add_thickbox();
122 add_action( 'admin_footer', array( $this, 'shortcode_insert_button_script' ) );
123 }
124
125 if ( $this->is_preview() ) {
126 add_action( 'wp_footer', array( $this, 'shortcode_insert_button_script' ) );
127 // this makes the insert button work for elementor
128 add_action( 'elementor/editor/after_enqueue_scripts', array(
129 $this,
130 'shortcode_insert_button_script'
131 ) ); // for elementor
132 }
133 // this makes the insert button work for cornerstone
134 add_action( 'wp_print_footer_scripts', array( __CLASS__, 'maybe_cornerstone_builder' ) );
135
136 add_action( 'wp_ajax_super_duper_get_widget_settings', array( __CLASS__, 'get_widget_settings' ) );
137 add_action( 'wp_ajax_super_duper_get_picker', array( __CLASS__, 'get_picker' ) );
138
139 // add generator text to head
140 add_action( 'admin_head', array( $this, 'generator' ), 99 );
141 add_action( 'wp_head', array( $this, 'generator' ), 99 );
142 }
143
144 do_action( 'wp_super_duper_widget_init', $options, $this );
145 }
146
147 /**
148 * Load the Bricks conversion class if we are running Bricks.
149 * @return void
150 */
151 public function load_bricks_element_class() {
152 include_once __DIR__ . '/includes/class-super-duper-bricks-element.php';
153 }
154
155 /**
156 * The register widget function
157 * @return void
158 */
159 public function _register() {
160 if(empty($this->options['output_types']) || in_array('widget',$this->options['output_types'])){
161 parent::_register();
162 }
163 }
164
165 /**
166 * Add our widget CSS to elementor editor.
167 */
168 public function elementor_editor_styles() {
169 wp_add_inline_style( 'elementor-editor', $this->widget_css( false ) );
170 }
171
172 public function register_fusion_element() {
173
174 $options = $this->options;
175
176 if ( $this->base_id ) {
177
178 $params = $this->get_fusion_params();
179
180 $args = array(
181 'name' => $options['name'],
182 'shortcode' => $this->base_id,
183 'icon' => $options['block-icon'] ? $options['block-icon'] : 'far fa-square',
184 'allow_generator' => true,
185 );
186
187 if ( ! empty( $params ) ) {
188 $args['params'] = $params;
189 }
190
191 fusion_builder_map( $args );
192 }
193
194 }
195
196 public function get_fusion_params() {
197 $params = array();
198 $arguments = $this->get_arguments();
199
200 if ( ! empty( $arguments ) ) {
201 foreach ( $arguments as $key => $val ) {
202 $param = array();
203 // type
204 $param['type'] = str_replace(
205 array(
206 "text",
207 "number",
208 "email",
209 "color",
210 "checkbox"
211 ),
212 array(
213 "textfield",
214 "textfield",
215 "textfield",
216 "colorpicker",
217 "select",
218
219 ),
220 $val['type'] );
221
222 // multiselect
223 if ( $val['type'] == 'multiselect' || ( ( $param['type'] == 'select' || $val['type'] == 'select' ) && ! empty( $val['multiple'] ) ) ) {
224 $param['type'] = 'multiple_select';
225 $param['multiple'] = true;
226 }
227
228 // heading
229 $param['heading'] = isset( $val['title'] ) ? $val['title'] : '';
230
231 // description
232 $param['description'] = isset( $val['desc'] ) ? $val['desc'] : '';
233
234 // param_name
235 $param['param_name'] = $key;
236
237 // Default
238 $param['default'] = isset( $val['default'] ) ? $val['default'] : '';
239
240 // Group
241 if ( isset( $val['group'] ) ) {
242 $param['group'] = $val['group'];
243
244 if ( ! empty( $param['group'] ) ) {
245 // Fusion Builder converts the group name into a tab ID without sanitization and assigns it to the href.
246 // Replace some punctuation symbols.
247 $param['group'] = preg_replace( '/[\&,\(\)\:\/\\\\]/u', ' ', $param['group'] );
248 // Remove ' ".
249 $param['group'] = preg_replace( '/[\'\"]/u', '', $param['group'] );
250 // Replace consecutive spaces with single space.
251 $param['group'] = preg_replace( '/\s+/', ' ', $param['group'] );
252 }
253 }
254
255 // value
256 if ( $val['type'] == 'checkbox' ) {
257 if ( isset( $val['default'] ) && $val['default'] == '0' ) {
258 unset( $param['default'] );
259 }
260 $param['value'] = array( '0' => __( "No", 'ayecode-connect' ), '1' => __( "Yes", 'ayecode-connect' ) );
261 } elseif ( $param['type'] == 'select' || $param['type'] == 'multiple_select' ) {
262 $param['value'] = isset( $val['options'] ) ? $val['options'] : array();
263 } else {
264 $param['value'] = isset( $val['default'] ) ? $val['default'] : '';
265 }
266
267 // setup the param
268 $params[] = $param;
269
270 }
271 }
272
273
274 return $params;
275 }
276
277 /**
278 * Maybe insert the shortcode inserter button in the footer if we are in the cornerstone builder
279 */
280 public static function maybe_cornerstone_builder() {
281 if ( did_action( 'cornerstone_before_boot_app' ) ) {
282 self::shortcode_insert_button_script();
283 }
284 }
285
286 /**
287 * A function to ge the shortcode builder picker html.
288 *
289 * @param string $editor_id
290 *
291 * @return string
292 */
293 public static function get_picker( $editor_id = '' ) {
294
295 ob_start();
296 if ( isset( $_POST['editor_id'] ) ) {
297 $editor_id = esc_attr( $_POST['editor_id'] );
298 } elseif ( isset( $_REQUEST['et_fb'] ) ) {
299 $editor_id = 'main_content_content_vb_tiny_mce';
300 }
301
302 global $sd_widgets;
303
304 // print_r($sd_widgets);exit;
305 ?>
306
307 <div class="sd-shortcode-left-wrap">
308 <?php
309 ksort( $sd_widgets );
310 // print_r($sd_widgets);exit;
311 if ( ! empty( $sd_widgets ) ) {
312 echo '<select class="widefat" onchange="sd_get_shortcode_options(this);">';
313 echo "<option>" . __( 'Select shortcode', 'ayecode-connect' ) . "</option>";
314 foreach ( $sd_widgets as $shortcode => $class ) {
315 if(!empty($class['output_types']) && !in_array('shortcode', $class['output_types'])){ continue; }
316 echo "<option value='" . esc_attr( $shortcode ) . "'>" . esc_attr( $shortcode ) . " (" . esc_attr( $class['name'] ) . ")</option>";
317 }
318 echo "</select>";
319
320 }
321 ?>
322 <div class="sd-shortcode-settings"></div>
323 </div>
324 <div class="sd-shortcode-right-wrap">
325 <textarea id='sd-shortcode-output' disabled></textarea>
326 <div id='sd-shortcode-output-actions'>
327 <?php if ( $editor_id != '' ) { ?>
328 <button class="button sd-insert-shortcode-button" onclick="sd_insert_shortcode(<?php if ( ! empty( $editor_id ) ) { echo "'" . $editor_id . "'"; } ?>)"><?php esc_html_e( 'Insert Shortcode', 'ayecode-connect' ); ?></button>
329 <?php } ?>
330 <button class="button" onclick="sd_copy_to_clipboard()"><?php esc_html_e( 'Copy Shortcode', 'ayecode-connect' ); ?></button>
331 </div>
332 </div>
333 <?php
334 $html = ob_get_clean();
335
336 if ( wp_doing_ajax() ) {
337 echo $html;
338 $should_die = true;
339
340 // some builder get the editor via ajax so we should not die on those occasions
341 $dont_die = array(
342 'parent_tag',// WP Bakery
343 'avia_request' // enfold
344 );
345
346 foreach ( $dont_die as $request ) {
347 if ( isset( $_REQUEST[ $request ] ) ) {
348 $should_die = false;
349 }
350 }
351
352 if ( $should_die ) {
353 wp_die();
354 }
355 } else {
356 return $html;
357 }
358
359 return '';
360 }
361
362 /**
363 * Output the version in the header.
364 */
365 public function generator() {
366 $file = str_replace( array( "/", "\\" ), "/", realpath( __FILE__ ) );
367 $plugins_dir = str_replace( array( "/", "\\" ), "/", realpath( WP_PLUGIN_DIR ) );
368
369 // Find source plugin/theme of SD
370 $source = array();
371 if ( strpos( $file, $plugins_dir ) !== false ) {
372 $source = explode( "/", plugin_basename( $file ) );
373 } else if ( function_exists( 'get_theme_root' ) ) {
374 $themes_dir = str_replace( array( "/", "\\" ), "/", realpath( get_theme_root() ) );
375
376 if ( strpos( $file, $themes_dir ) !== false ) {
377 $source = explode( "/", ltrim( str_replace( $themes_dir, "", $file ), "/" ) );
378 }
379 }
380
381 echo '<meta name="generator" content="WP Super Duper v' . esc_attr( $this->version ) . '"' . ( ! empty( $source[0] ) ? ' data-sd-source="' . esc_attr( $source[0] ) . '"' : '' ) . ' />';
382 }
383
384 /**
385 * Get widget settings.
386 *
387 * @since 1.0.0
388 */
389 public static function get_widget_settings() {
390 global $sd_widgets;
391
392 $shortcode = isset( $_REQUEST['shortcode'] ) && $_REQUEST['shortcode'] ? sanitize_title_with_dashes( $_REQUEST['shortcode'] ) : '';
393 if ( ! $shortcode ) {
394 wp_die();
395 }
396 $widget_args = isset( $sd_widgets[ $shortcode ] ) ? $sd_widgets[ $shortcode ] : '';
397 if ( ! $widget_args ) {
398 wp_die();
399 }
400 $class_name = isset( $widget_args['class_name'] ) && $widget_args['class_name'] ? $widget_args['class_name'] : '';
401 if ( ! $class_name ) {
402 wp_die();
403 }
404
405 // invoke an instance method
406 $widget = new $class_name;
407
408 ob_start();
409 $widget->form( array() );
410 $form = ob_get_clean();
411 echo "<form id='$shortcode'>" . $form . "<div class=\"widget-control-save\"></div></form>";
412 echo "<style>" . $widget->widget_css() . "</style>";
413 echo "<script>" . $widget->widget_js() . "</script>";
414 ?>
415 <?php
416 wp_die();
417 }
418
419 /**
420 * Insert shortcode builder button to classic editor (not inside Gutenberg, not needed).
421 *
422 * @param string $editor_id Optional. Shortcode editor id. Default null.
423 * @param string $insert_shortcode_function Optional. Insert shortcode function. Default null.
424 *
425 *@since 1.0.0
426 *
427 */
428 public static function shortcode_insert_button( $editor_id = '', $insert_shortcode_function = '' ) {
429 global $sd_widgets, $shortcode_insert_button_once;
430 if ( $shortcode_insert_button_once ) {
431 return;
432 }
433 add_thickbox();
434
435 /**
436 * Cornerstone makes us play dirty tricks :/
437 * All media_buttons are removed via JS unless they are two specific id's so we wrap our content in this ID so it is not removed.
438 */
439 if ( function_exists( 'cornerstone_plugin_init' ) && ! is_admin() ) {
440 echo '<span id="insert-media-button">';
441 }
442
443 echo self::shortcode_button( 'this', 'true' );
444
445 // see opening note
446 if ( function_exists( 'cornerstone_plugin_init' ) && ! is_admin() ) {
447 echo '</span>'; // end #insert-media-button
448 }
449
450 // Add separate script for generatepress theme sections
451 if ( function_exists( 'generate_sections_sections_metabox' ) && did_action( 'generate_sections_metabox' ) ) {
452 } else {
453 self::shortcode_insert_button_script( $editor_id, $insert_shortcode_function );
454 }
455
456 $shortcode_insert_button_once = true;
457 }
458
459 /**
460 * Gets the shortcode insert button html.
461 *
462 * @param string $id
463 * @param string $search_for_id
464 *
465 * @return mixed
466 */
467 public static function shortcode_button( $id = '', $search_for_id = '' ) {
468 ob_start();
469 ?>
470 <span class="sd-lable-shortcode-inserter">
471 <a onclick="sd_ajax_get_picker(<?php echo $id;
472 if ( $search_for_id ) {
473 echo "," . $search_for_id;
474 } ?>);" href="#TB_inline?width=100%&height=550&inlineId=super-duper-content-ajaxed"
475 class="thickbox button super-duper-content-open" title="Add Shortcode">
476 <span style="vertical-align: middle;line-height: 18px;font-size: 20px;"
477 class="dashicons dashicons-screenoptions"></span>
478 </a>
479 <div id="super-duper-content-ajaxed" style="display:none;">
480 <span>Loading</span>
481 </div>
482 </span>
483
484 <?php
485 $html = ob_get_clean();
486
487 // remove line breaks so we can use it in js
488 return preg_replace( "/\r|\n/", "", trim( $html ) );
489 }
490
491 /**
492 * Makes SD work with the siteOrigin page builder.
493 *
494 * @return mixed
495 *@since 1.0.6
496 */
497 public static function siteorigin_js() {
498 ob_start();
499 ?>
500 <script>
501 /**
502 * Check a form to see what items should be shown or hidden.
503 */
504 function sd_so_show_hide(form) {
505 jQuery(form).find(".sd-argument").each(function () {
506 var $element_require = jQuery(this).data('element_require');
507
508 if ($element_require) {
509 $element_require = $element_require.replace("&#039;", "'"); // replace single quotes
510 $element_require = $element_require.replace("&quot;", '"'); // replace double quotes
511
512 if (eval($element_require)) {
513 jQuery(this).removeClass('sd-require-hide');
514 } else {
515 jQuery(this).addClass('sd-require-hide');
516 }
517 }
518 });
519 }
520
521 /**
522 * Toggle advanced settings visibility.
523 */
524 function sd_so_toggle_advanced($this) {
525 var form = jQuery($this).parents('form,.form,.so-content');
526 form.find('.sd-advanced-setting').toggleClass('sd-adv-show');
527 return false;// prevent form submit
528 }
529
530 /**
531 * Initialise a individual widget.
532 */
533 function sd_so_init_widget($this, $selector) {
534 if (!$selector) {
535 $selector = 'form';
536 }
537 // only run once.
538 if (jQuery($this).data('sd-widget-enabled')) {
539 return;
540 } else {
541 jQuery($this).data('sd-widget-enabled', true);
542 }
543
544 var $button = '<button title="<?php _e( 'Advanced Settings', 'ayecode-connect' );?>" class="button button-primary right sd-advanced-button" onclick="sd_so_toggle_advanced(this);return false;"><i class="fas fa-sliders-h" aria-hidden="true"></i></button>';
545 var form = jQuery($this).parents('' + $selector + '');
546
547 if (jQuery($this).val() == '1' && jQuery(form).find('.sd-advanced-button').length == 0) {
548 jQuery(form).append($button);
549 }
550
551 // show hide on form change
552 jQuery(form).on("change", function () {
553 sd_so_show_hide(form);
554 });
555
556 // show hide on load
557 sd_so_show_hide(form);
558 }
559
560 jQuery(function () {
561 jQuery(document).on('open_dialog', function (w, e) {
562 setTimeout(function () {
563 if (jQuery('.so-panels-dialog-wrapper:visible .so-content.panel-dialog .sd-show-advanced').length) {
564 if (jQuery('.so-panels-dialog-wrapper:visible .so-content.panel-dialog .sd-show-advanced').val() == '1') {
565 sd_so_init_widget('.so-panels-dialog-wrapper:visible .so-content.panel-dialog .sd-show-advanced', 'div');
566 }
567 }
568 }, 200);
569 });
570 });
571 </script>
572 <?php
573 $output = ob_get_clean();
574
575 /*
576 * We only add the <script> tags for code highlighting, so we strip them from the output.
577 */
578
579 return str_replace( array(
580 '<script>',
581 '</script>'
582 ), '', $output );
583 }
584
585 /**
586 * Output the JS and CSS for the shortcode insert button.
587 *
588 * @param string $editor_id
589 * @param string $insert_shortcode_function
590 *
591 *@since 1.0.6
592 *
593 */
594 public static function shortcode_insert_button_script( $editor_id = '', $insert_shortcode_function = '' ) {
595 ?>
596 <style>
597 .sd-shortcode-left-wrap {
598 float: left;
599 width: calc(60% - .75rem);
600 padding-top: .75rem;
601 }
602
603 .sd-shortcode-left-wrap .gd-help-tip {
604 float: none;
605 }
606
607 .sd-shortcode-left-wrap .widefat {
608 border-spacing: 0;
609 width: 100%;
610 clear: both;
611 margin: 0;
612 border: 1px solid #ddd;
613 box-shadow: inset 0 1px 2px rgba(0, 0, 0, .07);
614 background-color: #fff;
615 color: #32373c;
616 outline: 0;
617 transition: 50ms border-color ease-in-out;
618 padding: 3px 5px;
619 }
620
621 .sd-shortcode-left-wrap input[type=checkbox].widefat {
622 border: 1px solid #b4b9be;
623 background: #fff;
624 color: #555;
625 clear: none;
626 cursor: pointer;
627 display: inline-block;
628 line-height: 0;
629 height: 16px;
630 margin: -4px 4px 0 0;
631 margin-top: 0;
632 outline: 0;
633 padding: 0 !important;
634 text-align: center;
635 vertical-align: middle;
636 width: 16px;
637 min-width: 16px;
638 -webkit-appearance: none;
639 box-shadow: inset 0 1px 2px rgba(0, 0, 0, .1);
640 transition: .05s border-color ease-in-out;
641 }
642
643 .sd-shortcode-left-wrap input[type=checkbox]:checked:before {
644 content: "\f147";
645 margin: -3px 0 0 -4px;
646 color: #1e8cbe;
647 float: left;
648 display: inline-block;
649 vertical-align: middle;
650 width: 16px;
651 font: normal 21px/1 dashicons;
652 speak: none;
653 -webkit-font-smoothing: antialiased;
654 -moz-osx-font-smoothing: grayscale;
655 }
656
657 #sd-shortcode-output-actions button,
658 .sd-advanced-button {
659 color: #555;
660 border-color: #ccc;
661 background: #f7f7f7;
662 box-shadow: 0 1px 0 #ccc;
663 vertical-align: top;
664 display: inline-block;
665 text-decoration: none;
666 font-size: 13px;
667 line-height: 26px;
668 height: 28px;
669 margin: 0;
670 padding: 0 10px 1px;
671 cursor: pointer;
672 border-width: 1px;
673 border-style: solid;
674 -webkit-appearance: none;
675 border-radius: 3px;
676 white-space: nowrap;
677 box-sizing: border-box;
678 }
679
680 button.sd-advanced-button {
681 background: #0073aa;
682 border-color: #006799;
683 box-shadow: inset 0 2px 0 #006799;
684 vertical-align: top;
685 color: #fff;
686 text-decoration: none;
687 text-shadow: 0 -1px 1px #006799, 1px 0 1px #006799, 0 1px 1px #006799, -1px 0 1px #006799;
688 float: right;
689 margin-right: 3px !important;
690 font-size: 20px !important;
691 }
692
693 .sd-shortcode-right-wrap {
694 float: right;
695 width: 40%;
696 padding-top: .75rem;
697 }
698
699 #sd-shortcode-output {
700 background: rgba(255, 255, 255, .5);
701 border-color: rgba(222, 222, 222, .75);
702 box-shadow: inset 0 1px 2px rgba(0, 0, 0, .04);
703 color: rgba(51, 51, 51, .5);
704 overflow: auto;
705 padding: 2px 6px;
706 line-height: 1.4;
707 resize: vertical;
708 height: 250px;
709 width: 100%;
710 margin-bottom: .75rem;
711 }
712
713 <?php if ( function_exists( 'generate_sections_sections_metabox' ) ) { ?>
714 .generate-sections-modal #custom-media-buttons > .sd-lable-shortcode-inserter {
715 display: inline;
716 }
717 <?php } ?>
718 <?php if ( function_exists( 'et_builder_is_tb_admin_screen' ) && et_builder_is_tb_admin_screen() ) { ?>
719 body.divi_page_et_theme_builder div#TB_window.gd-tb-window{z-index:9999999}
720 <?php } ?>
721 </style>
722 <?php
723 if ( class_exists( 'SiteOrigin_Panels' ) ) {
724 echo "<script>" . self::siteorigin_js() . "</script>";
725 }
726 ?>
727 <script>
728 <?php
729 if(! empty( $insert_shortcode_function )){
730 echo $insert_shortcode_function;
731 }else{
732
733 /**
734 * Function for super duper insert shortcode.
735 *
736 * @since 1.0.0
737 */
738 ?>
739 function sd_insert_shortcode($editor_id) {
740 $shortcode = jQuery('#TB_ajaxContent #sd-shortcode-output').val();
741 if ($shortcode) {
742 if (!$editor_id) {
743 <?php
744 if ( isset( $_REQUEST['et_fb'] ) ) {
745 echo '$editor_id = "#main_content_content_vb_tiny_mce";';
746 } elseif ( isset( $_REQUEST['action'] ) && $_REQUEST['action'] == 'elementor' ) {
747 echo '$editor_id = "#elementor-controls .wp-editor-container textarea";';
748 } else {
749 echo '$editor_id = "#wp-content-editor-container textarea";';
750 }
751 ?>
752 } else {
753 $editor_id = '#' + $editor_id;
754 }
755 tmceActive = jQuery($editor_id).attr("aria-hidden") == "true" ? true : false;
756 /* GeneratePress */
757 if (jQuery('#generate-sections-modal-dialog ' + $editor_id).length) {
758 $editor_id = '#generate-sections-modal-dialog ' + $editor_id;
759 tmceActive = jQuery($editor_id).closest('.wp-editor-wrap').hasClass('tmce-active') ? true : false;
760 }
761 if (typeof tinyMCE !== 'undefined' && tinyMCE.activeEditor && tmceActive) {
762 tinyMCE.execCommand('mceInsertContent', false, $shortcode);
763 } else {
764 var $txt = jQuery($editor_id);
765 var caretPos = $txt[0].selectionStart;
766 var textAreaTxt = $txt.val();
767 var txtToAdd = $shortcode;
768 var textareaValue = textAreaTxt.substring(0, caretPos) + txtToAdd + textAreaTxt.substring(caretPos);
769 $txt.focus().val(textareaValue).change().keydown().blur().keyup().keypress().trigger('input').trigger('change');
770
771 // set Divi react input value
772 var input = document.getElementById("main_content_content_vb_tiny_mce");
773 if (input) {
774 sd_setNativeValue(input, textareaValue);
775 }
776 }
777 tb_remove();
778 }
779 }
780
781 /*
782 Set the value of elements controlled via react.
783 */
784 function sd_setNativeValue(element, value) {
785 let lastValue = element.value;
786 element.value = value;
787 let event = new Event("input", {target: element, bubbles: true});
788 // React 15
789 event.simulated = true;
790 // React 16
791 let tracker = element._valueTracker;
792 if (tracker) {
793 tracker.setValue(lastValue);
794 }
795 element.dispatchEvent(event);
796 }
797 <?php } ?>
798
799 /*
800 Copies the shortcode to the clipboard.
801 */
802 function sd_copy_to_clipboard() {
803 /* Get the text field */
804 var copyText = document.querySelector("#TB_ajaxContent #sd-shortcode-output");
805 //un-disable the field
806 copyText.disabled = false;
807 /* Select the text field */
808 copyText.select();
809 /* Copy the text inside the text field */
810 document.execCommand("Copy");
811 //re-disable the field
812 copyText.disabled = true;
813 /* Alert the copied text */
814 alert("Copied the text: " + copyText.value);
815 }
816
817 /*
818 Gets the shortcode options.
819 */
820 function sd_get_shortcode_options($this) {
821 $short_code = jQuery($this).val();
822 if ($short_code) {
823 var data = {
824 'action': 'super_duper_get_widget_settings',
825 'shortcode': $short_code,
826 'attributes': 123,
827 'post_id': 321,
828 '_ajax_nonce': '<?php echo wp_create_nonce( 'super_duper_output_shortcode' );?>'
829 };
830
831 if (typeof ajaxurl === 'undefined') {
832 var ajaxurl = "<?php echo admin_url( 'admin-ajax.php' );?>";
833 }
834
835 jQuery.post(ajaxurl, data, function (response) {
836 jQuery('#TB_ajaxContent .sd-shortcode-settings').html(response);
837
838 jQuery('#' + $short_code).on('change', 'select', function () {
839 sd_build_shortcode($short_code);
840 }); // take care of select tags
841
842 jQuery('#' + $short_code).on('change keypress keyup', 'input,textarea', function () {
843 sd_build_shortcode($short_code);
844 });
845
846 sd_build_shortcode($short_code);
847
848 // resize the window to fit
849 setTimeout(function () {
850 jQuery('#TB_ajaxContent').css('width', 'auto').css('height', '75vh');
851 }, 200);
852
853 return response;
854 });
855 }
856 }
857
858 /*
859 Builds and inserts the shortcode into the viewer.
860 */
861 function sd_build_shortcode($id) {
862 var multiSelects = {};
863 var multiSelectsRemove = [];
864
865 $output = "[" + $id;
866
867 $form_data = jQuery("#" + $id).serializeArray();
868
869 // run checks for multiselects
870 jQuery.each($form_data, function (index, element) {
871 if (element && element.value) {
872 $field_name = element.name.substr(element.name.indexOf("][") + 2);
873 $field_name = $field_name.replace("]", "");
874 // check if its a multiple
875 if ($field_name.includes("[]")) {
876 multiSelectsRemove[multiSelectsRemove.length] = index;
877 $field_name = $field_name.replace("[]", "");
878 if ($field_name in multiSelects) {
879 multiSelects[$field_name] = multiSelects[$field_name] + "," + element.value;
880 } else {
881 multiSelects[$field_name] = element.value;
882 }
883 }
884 }
885 });
886
887 // fix multiselects if any are found
888 if (multiSelectsRemove.length) {
889
890 // remove all multiselects
891 multiSelectsRemove.reverse();
892 multiSelectsRemove.forEach(function (index) {
893 $form_data.splice(index, 1);
894 });
895
896 $ms_arr = [];
897 // add multiselets back
898 jQuery.each(multiSelects, function (index, value) {
899 $ms_arr[$ms_arr.length] = {"name": "[][" + index + "]", "value": value};
900 });
901 $form_data = $form_data.concat($ms_arr);
902 }
903
904 if ($form_data) {
905 $content = '';
906 $form_data.forEach(function (element) {
907 if (element.value) {
908 $field_name = element.name.substr(element.name.indexOf("][") + 2);
909 $field_name = $field_name.replace("]", "");
910 if ($field_name == 'html') {
911 $content = element.value;
912 } else {
913 $output = $output + " " + $field_name + '="' + element.value + '"';
914 }
915 }
916 });
917 }
918 $output = $output + "]";
919
920 // check for content field
921 if ($content) {
922 $output = $output + $content + "[/" + $id + "]";
923 }
924
925 jQuery('#TB_ajaxContent #sd-shortcode-output').html($output);
926 }
927
928 /*
929 Delay the init of the textareas for 1 second.
930 */
931 (function () {
932 setTimeout(function () {
933 sd_init_textareas();
934 }, 1000);
935 })();
936
937 /*
938 Init the textareas to be able to show the shortcode builder button.
939 */
940 function sd_init_textareas() {
941 // General textareas
942 jQuery(document).on('focus', 'textarea', function () {
943 if (jQuery(this).hasClass('wp-editor-area')) {
944 // insert the shortcode button to the textarea lable if not there already
945 if (!(jQuery(this).parent().find('.sd-lable-shortcode-inserter').length || (jQuery(this).closest('.wp-editor-wrap').length && jQuery(this).closest('.wp-editor-wrap').find('.sd-lable-shortcode-inserter').length))) {
946 jQuery(this).parent().find('.quicktags-toolbar').append(sd_shortcode_button(jQuery(this).attr('id')));
947 }
948 } else {
949 // insert the shortcode button to the textarea lable if not there already
950 if (!jQuery("label[for='" + jQuery(this).attr('id') + "']").find('.sd-lable-shortcode-inserter').length) {
951 jQuery("label[for='" + jQuery(this).attr('id') + "']").append(sd_shortcode_button(jQuery(this).attr('id')));
952 }
953 }
954 });
955
956 // The below tries to add the shortcode builder button to the builders own raw/shortcode sections.
957 <?php if ( function_exists( 'et_setup_theme' ) ) { ?>
958 // DIVI
959 jQuery(document).on('focusin', '.et-fb-codemirror', function () {
960 // insert the shortcode button to the textarea lable if not there already
961 if (!jQuery(this).closest('.et-fb-form__group').find('.sd-lable-shortcode-inserter').length) {
962 jQuery(this).closest('.et-fb-form__group').find('.et-fb-form__label-text').append(sd_shortcode_button());
963 }
964 });
965 /* Divi 5 */
966 jQuery(document).on('focusin', '.et-vb-tinymce-html-input', function () {
967 var $etEl = jQuery(this).closest('.et-vb-field-richtext').find('.et-vb-field-richtext-buttons');
968 if (!$etEl.find('.sd-lable-shortcode-inserter').length) {
969 if ($etEl.find('.et-vb-switch-editor-mode').length) {
970 $etEl.find('.et-vb-switch-editor-mode').before(sd_shortcode_button());
971 } else {
972 $etEl.append(sd_shortcode_button());
973 }
974 }
975 });
976 jQuery(document).on('focusin', '.et-vb-code', function() {
977 var $etEl = jQuery(this).closest('.et-vb-field').find('.et-vb-field-label .et-vb-field-label-buttons');
978 if (!$etEl.find('.sd-lable-shortcode-inserter').length) {
979 $etEl.prepend(sd_shortcode_button());
980 $etEl.find('.sd-lable-shortcode-inserter').addClass('et-vb-field-button');
981 }
982 });
983 <?php } ?>
984
985 // Beaver
986 jQuery(document).on('focusin', '.fl-code-field', function () {
987 // insert the shortcode button to the textarea lable if not there already
988 if (!jQuery(this).closest('.fl-field-control-wrapper').find('.sd-lable-shortcode-inserter').length) {
989 jQuery(this).closest('.fl-field-control-wrapper').prepend(sd_shortcode_button());
990 }
991 });
992
993 // Fusion builder (avada)
994 jQuery(document).on('focusin', '.CodeMirror.cm-s-default', function () {
995 // insert the shortcode button to the textarea lable if not there already
996 if (!jQuery(this).parent().find('.sd-lable-shortcode-inserter').length) {
997 jQuery(sd_shortcode_button()).insertBefore(this);
998 }
999 });
1000
1001 // Avia builder (enfold)
1002 jQuery(document).on('focusin', '#aviaTBcontent', function () {
1003 // insert the shortcode button to the textarea lable if not there already
1004 if (!jQuery(this).parent().parent().find('.avia-name-description ').find('.sd-lable-shortcode-inserter').length) {
1005 jQuery(this).parent().parent().find('.avia-name-description strong').append(sd_shortcode_button(jQuery(this).attr('id')));
1006 }
1007 });
1008
1009 // Cornerstone textareas
1010 jQuery(document).on('focusin', '.cs-control.cs-control-textarea', function () {
1011 // insert the shortcode button to the textarea lable if not there already
1012 if (!jQuery(this).find('.cs-control-header label').find('.sd-lable-shortcode-inserter').length) {
1013 jQuery(this).find('.cs-control-header label').append(sd_shortcode_button());
1014 }
1015 });
1016
1017 // Cornerstone main bar
1018 setTimeout(function () {
1019 // insert the shortcode button to the textarea lable if not there already
1020 if (!jQuery('.cs-bar-btns').find('.sd-lable-shortcode-inserter').length) {
1021 jQuery('<li style="text-align: center;padding: 5px;list-style: none;">' + sd_shortcode_button() + '</li>').insertBefore('.cs-action-toggle-custom-css');
1022 }
1023 }, 2000);
1024
1025 // WP Bakery, code editor does not render shortcodes.
1026 // jQuery(document).on('focusin', '.wpb-textarea_raw_html', function () {
1027 // // insert the shortcode button to the textarea lable if not there already
1028 // if(!jQuery(this).parent().parent().find('.wpb_element_label').find('.sd-lable-shortcode-inserter').length){
1029 // jQuery(this).parent().parent().find('.wpb_element_label').append(sd_shortcode_button());
1030 // }
1031 // });
1032 }
1033
1034 /**
1035 * Gets the html for the picker via ajax and updates it on the fly.
1036 *
1037 * @param $id
1038 * @param $search
1039 */
1040 function sd_ajax_get_picker($id, $search) {
1041 if ($search) {
1042 $this = $id;
1043 $id = jQuery($this).closest('.wp-editor-wrap').find('.wp-editor-container textarea').attr('id');
1044 }
1045
1046 var data = {
1047 'action': 'super_duper_get_picker',
1048 'editor_id': $id,
1049 '_ajax_nonce': '<?php echo wp_create_nonce( 'super_duper_picker' );?>'
1050 };
1051
1052 if (!ajaxurl) {
1053 var ajaxurl = "<?php echo admin_url( 'admin-ajax.php' ); ?>";
1054 }
1055
1056 jQuery.post(ajaxurl, data, function (response) {
1057 jQuery('#TB_ajaxContent').closest('#TB_window').addClass('gd-tb-window');
1058 jQuery('#TB_ajaxContent').html(response);
1059 //return response;
1060 }).then(function (env) {
1061 jQuery('body').on('thickbox:removed', function () {
1062 jQuery('#super-duper-content-ajaxed').html('');
1063 });
1064 });
1065 }
1066
1067 /**
1068 * Get the html for the shortcode inserter button depending on if a textarea id is available.
1069 *
1070 * @param $id string The textarea id.
1071 * @returns {string}
1072 */
1073 function sd_shortcode_button($id) {
1074 if ($id) {
1075 return '<?php echo self::shortcode_button( "\\''+\$id+'\\'" );?>';
1076 } else {
1077 return '<?php echo self::shortcode_button();?>';
1078 }
1079 }
1080 </script>
1081 <?php
1082 }
1083
1084 /**
1085 * Gets some CSS for the widgets screen.
1086 *
1087 * @param bool $advanced If we should include advanced CSS.
1088 *
1089 * @return mixed
1090 */
1091 public function widget_css( $advanced = true ) {
1092 ob_start();
1093 ?>
1094 <style>
1095 <?php if( $advanced ){ ?>
1096 .sd-advanced-setting {
1097 display: none;
1098 }
1099
1100 .sd-advanced-setting.sd-adv-show {
1101 display: block;
1102 }
1103
1104 .sd-argument.sd-require-hide,
1105 .sd-advanced-setting.sd-require-hide {
1106 display: none;
1107 }
1108
1109 button.sd-advanced-button {
1110 margin-right: 3px !important;
1111 font-size: 20px !important;
1112 }
1113
1114 <?php } ?>
1115
1116 button.sd-toggle-group-button {
1117 background-color: #f3f3f3;
1118 color: #23282d;
1119 cursor: pointer;
1120 padding: 10px;
1121 width: 100%;
1122 border: none;
1123 text-align: left;
1124 outline: none;
1125 font-size: 13px;
1126 font-weight: bold;
1127 margin-bottom: 1px;
1128 }
1129 .elementor-control .sd-argument select[multiple]{height:100px}
1130 .elementor-control .sd-argument select[multiple] option{padding:3px}
1131 </style>
1132 <?php
1133 $output = ob_get_clean();
1134
1135 /*
1136 * We only add the <script> tags for code highlighting, so we strip them from the output.
1137 */
1138
1139 return str_replace( array(
1140 '<style>',
1141 '</style>'
1142 ), '', $output );
1143 }
1144
1145 /**
1146 * Gets some JS for the widgets screen.
1147 *
1148 * @return mixed
1149 */
1150 public function widget_js() {
1151 ob_start();
1152 ?>
1153 <script>
1154
1155 /**
1156 * Toggle advanced settings visibility.
1157 */
1158 function sd_toggle_advanced($this) {
1159 var form = jQuery($this).parents('form,.form');
1160 form.find('.sd-advanced-setting').toggleClass('sd-adv-show');
1161 return false;// prevent form submit
1162 }
1163
1164 /**
1165 * Check a form to see what items should be shown or hidden.
1166 */
1167 function sd_show_hide(form) {
1168 jQuery(form).find(".sd-argument").each(function () {
1169
1170 var $element_require = jQuery(this).data('element_require');
1171
1172 if ($element_require) {
1173
1174 $element_require = $element_require.replace("&#039;", "'"); // replace single quotes
1175 $element_require = $element_require.replace("&quot;", '"'); // replace double quotes
1176
1177 if (eval($element_require)) {
1178 jQuery(this).removeClass('sd-require-hide');
1179 } else {
1180 jQuery(this).addClass('sd-require-hide');
1181 }
1182 }
1183 });
1184 }
1185
1186 /**
1187 * Initialise widgets from the widgets screen.
1188 */
1189 function sd_init_widgets($selector) {
1190 jQuery(".sd-show-advanced").each(function (index) {
1191 sd_init_widget(this, $selector);
1192 });
1193 }
1194
1195 /**
1196 * Initialise a individual widget.
1197 */
1198 function sd_init_widget($this, $selector, $form) {
1199 if (!$selector) {
1200 $selector = 'form';
1201 }
1202 // Only run once.
1203 if (jQuery($this).data('sd-widget-enabled')) {
1204 return;
1205 } else {
1206 jQuery($this).data('sd-widget-enabled', true);
1207 }
1208
1209 var $button = '<button title="<?php esc_attr_e( 'Advanced Settings', 'ayecode-connect' );?>" style="line-height:1.5rem;margin:.5rem 0 0 0!important;" class="button button-primary right sd-advanced-button" onclick="sd_toggle_advanced(this);return false;"><span class="dashicons dashicons-admin-settings" style="width:1.5rem;font-size:1.5rem;height:1.5rem;line-height:1.5rem;margin:0;padding:0"></span></button>';
1210 var form = $form ? $form : jQuery($this).parents('' + $selector + '');
1211
1212 if (jQuery($this).val() == '1' && jQuery(form).find('.sd-advanced-button').length == 0) {
1213 console.log('add advanced button');
1214 if (jQuery(form).find('.widget-control-save').length > 0) {
1215 jQuery(form).find('.widget-control-save').after($button);
1216 } else {
1217 jQuery(form).find('.sd-show-advanced').after($button);
1218 }
1219 } else {
1220 console.log('no advanced button, ' + jQuery($this).val() + ', ' + jQuery(form).find('.sd-advanced-button').length);
1221 }
1222
1223 /* Show hide on form change */
1224 jQuery(form).on("change", function() {
1225 sd_show_hide(form);
1226 });
1227
1228 /* Show hide on load */
1229 sd_show_hide(form);
1230 }
1231
1232 /**
1233 * Init a customizer widget.
1234 */
1235 function sd_init_customizer_widget(section) {
1236 if (section.expanded) {
1237 section.expanded.bind(function (isExpanding) {
1238 if (isExpanding) {
1239 // is it a SD widget?
1240 if (jQuery(section.container).find('.sd-show-advanced').length) {
1241 // init the widget
1242 sd_init_widget(jQuery(section.container).find('.sd-show-advanced'), ".form");
1243 }
1244 }
1245 });
1246 }
1247 }
1248
1249 /**
1250 * If on widgets screen.
1251 */
1252 jQuery(function () {
1253 // if not in customizer.
1254 if (!wp.customize) {
1255 sd_init_widgets("form");
1256 }
1257
1258 /* Init on widget added */
1259 jQuery(document).on('widget-added', function (e, widget) {
1260 /* Is it a SD widget? */
1261 if (jQuery(widget).find('.sd-show-advanced').length) {
1262 var widgetId = jQuery(widget).find('[name="widget-id"]').length ? ': ' + jQuery(widget).find('[name="widget-id"]').val() : '';
1263 console.log('widget added' + widgetId);
1264 /* Init the widget */
1265 sd_init_widget(jQuery(widget).find('.sd-show-advanced'), "form", jQuery(widget).find('.sd-show-advanced').closest('form'));
1266 }
1267 });
1268
1269 /* Init on widget updated */
1270 jQuery(document).on('widget-updated', function (e, widget) {
1271 /* Is it a SD widget? */
1272 if (jQuery(widget).find('.sd-show-advanced').length) {
1273 var widgetId = jQuery(widget).find('[name="widget-id"]').length ? ': ' + jQuery(widget).find('[name="widget-id"]').val() : '';
1274 console.log('widget updated' + widgetId);
1275 /* Init the widget */
1276 sd_init_widget(jQuery(widget).find('.sd-show-advanced'), "form", jQuery(widget).find('.sd-show-advanced').closest('form'));
1277 }
1278 });
1279 });
1280
1281 /**
1282 * We need to run this before jQuery is ready
1283 */
1284 if (wp.customize) {
1285 wp.customize.bind('ready', function () {
1286
1287 // init widgets on load
1288 wp.customize.control.each(function (section) {
1289 sd_init_customizer_widget(section);
1290 });
1291
1292 // init widgets on add
1293 wp.customize.control.bind('add', function (section) {
1294 sd_init_customizer_widget(section);
1295 });
1296
1297 });
1298
1299 }
1300 <?php do_action( 'wp_super_duper_widget_js', $this ); ?>
1301 </script>
1302 <?php
1303 $output = ob_get_clean();
1304
1305 /*
1306 * We only add the <script> tags for code highlighting, so we strip them from the output.
1307 */
1308
1309 return str_replace( array(
1310 '<script>',
1311 '</script>'
1312 ), '', $output );
1313 }
1314
1315
1316 /**
1317 * Set the name from the argument key.
1318 *
1319 * @param $options
1320 *
1321 * @return mixed
1322 */
1323 private function add_name_from_key( $options, $arguments = false ) {
1324 if ( ! empty( $options['arguments'] ) ) {
1325 foreach ( $options['arguments'] as $key => $val ) {
1326 $options['arguments'][ $key ]['name'] = $key;
1327 }
1328 } elseif ( $arguments && is_array( $options ) && ! empty( $options ) ) {
1329 foreach ( $options as $key => $val ) {
1330 $options[ $key ]['name'] = $key;
1331 }
1332 }
1333
1334 return $options;
1335 }
1336
1337 /**
1338 * Register the parent shortcode.
1339 *
1340 * @since 1.0.0
1341 */
1342 public function register_shortcode() {
1343 add_shortcode( $this->base_id, array( $this, 'shortcode_output' ) );
1344 add_action( 'wp_ajax_super_duper_output_shortcode', array( $this, 'render_shortcode' ) );
1345 }
1346
1347 /**
1348 * Render the shortcode via ajax so we can return it to Gutenberg.
1349 *
1350 * @since 1.0.0
1351 */
1352 public function render_shortcode() {
1353 check_ajax_referer( 'super_duper_output_shortcode', '_ajax_nonce', true );
1354 if ( ! current_user_can( 'manage_options' ) ) {
1355 wp_die();
1356 }
1357
1358 // we might need the $post value here so lets set it.
1359 if ( isset( $_POST['post_id'] ) && $_POST['post_id'] ) {
1360 $post_obj = get_post( absint( $_POST['post_id'] ) );
1361 if ( ! empty( $post_obj ) && empty( $post ) ) {
1362 global $post;
1363 $post = $post_obj;
1364 }
1365 }
1366
1367 if ( isset( $_POST['shortcode'] ) && $_POST['shortcode'] ) {
1368 $is_preview = $this->is_preview();
1369 $shortcode_name = sanitize_title_with_dashes( $_POST['shortcode'] );
1370 $attributes_array = isset( $_POST['attributes'] ) && $_POST['attributes'] ? $_POST['attributes'] : array();
1371 $attributes = '';
1372 if ( ! empty( $attributes_array ) ) {
1373 foreach ( $attributes_array as $key => $value ) {
1374 if ( is_array( $value ) ) {
1375 $value = implode( ",", $value );
1376 }
1377
1378 if ( ! empty( $value ) ) {
1379 $value = wp_unslash( $value );
1380
1381 // Encode [ and ].
1382 if ( $is_preview ) {
1383 $value = $this->encode_shortcodes( $value );
1384 }
1385 }
1386 $attributes .= " " . esc_attr( sanitize_title_with_dashes( $key ) ) . "='" . esc_attr( $value ) . "' ";
1387 }
1388 }
1389
1390 $shortcode = "[" . esc_attr( $shortcode_name ) . " " . $attributes . "]";
1391
1392 $content = do_shortcode( $shortcode );
1393
1394 // Decode [ and ].
1395 if ( ! empty( $content ) && $is_preview ) {
1396 $content = $this->decode_shortcodes( $content );
1397 }
1398
1399 echo $content;
1400 }
1401 wp_die();
1402 }
1403
1404 /**
1405 * Output the shortcode.
1406 *
1407 * @param array $args
1408 * @param string $content
1409 *
1410 * @return string
1411 */
1412 public function shortcode_output( $args = array(), $content = '' ) {
1413 $_instance = $args;
1414
1415 $args = $this->argument_values( $args );
1416
1417 // add extra argument so we know its a output to gutenberg
1418 //$args
1419 $args = $this->string_to_bool( $args );
1420
1421 // if we have a enclosed shortcode we add it to the special `html` argument
1422 if ( ! empty( $content ) ) {
1423 $args['html'] = $content;
1424 }
1425
1426 if ( ! $this->is_preview() ) {
1427 /**
1428 * Filters the settings for a particular widget args.
1429 *
1430 * @param array $args The current widget instance's settings.
1431 * @param WP_Super_Duper $widget The current widget settings.
1432 * @param array $_instance An array of default widget arguments.
1433 *
1434 *@since 1.0.28
1435 *
1436 */
1437 $args = apply_filters( 'wp_super_duper_widget_display_callback', $args, $this, $_instance );
1438
1439 if ( ! is_array( $args ) ) {
1440 return $args;
1441 }
1442 }
1443
1444 $class = isset( $this->options['widget_ops']['classname'] ) ? esc_attr( $this->options['widget_ops']['classname'] ) : '';
1445 $class .= " sdel-".$this->get_instance_hash();
1446
1447 $class = apply_filters( 'wp_super_duper_div_classname', $class, $args, $this );
1448 $class = apply_filters( 'wp_super_duper_div_classname_' . $this->base_id, $class, $args, $this );
1449
1450 $attrs = apply_filters( 'wp_super_duper_div_attrs', '', $args, $this );
1451 $attrs = apply_filters( 'wp_super_duper_div_attrs_' . $this->base_id, '', $args, $this );
1452
1453 $shortcode_args = array();
1454 $output = '';
1455 $no_wrap = isset( $this->options['no_wrap'] ) && $this->options['no_wrap'] ? true : false;
1456 if ( isset( $args['no_wrap'] ) && $args['no_wrap'] ) {
1457 $no_wrap = true;
1458 }
1459 $main_content = $this->output( $args, $shortcode_args, $content );
1460 if ( $main_content && ! $no_wrap ) {
1461 // wrap the shortcode in a div with the same class as the widget
1462 $output .= '<div class="' . $class . '" ' . $attrs . '>';
1463 if ( ! empty( $args['title'] ) ) {
1464 // if its a shortcode and there is a title try to grab the title wrappers
1465 $shortcode_args = array( 'before_title' => '', 'after_title' => '' );
1466 if ( empty( $instance ) ) {
1467 global $wp_registered_sidebars;
1468 if ( ! empty( $wp_registered_sidebars ) ) {
1469 foreach ( $wp_registered_sidebars as $sidebar ) {
1470 if ( ! empty( $sidebar['before_title'] ) ) {
1471 $shortcode_args['before_title'] = $sidebar['before_title'];
1472 $shortcode_args['after_title'] = $sidebar['after_title'];
1473 break;
1474 }
1475 }
1476 }
1477 }
1478 $output .= $this->output_title( $shortcode_args, $args );
1479 }
1480 $output .= $main_content;
1481 $output .= '</div>';
1482 } elseif ( $main_content && $no_wrap ) {
1483 $output .= $main_content;
1484 }
1485
1486 // if preview show a placeholder if empty
1487 if ( $this->is_preview() && $output == '' ) {
1488 $output = $this->preview_placeholder_text( "{{" . $this->base_id . "}}" );
1489 }
1490
1491 return apply_filters( 'wp_super_duper_widget_output', $output, $args, $shortcode_args, $this );
1492 }
1493
1494 /**
1495 * Placeholder text to show if output is empty and we are on a preview/builder page.
1496 *
1497 * @param string $name
1498 *
1499 * @return string
1500 */
1501 public function preview_placeholder_text( $name = '' ) {
1502 return "<div style='background:#0185ba33;padding: 10px;border: 4px #ccc dashed;'>" . wp_sprintf( __( 'Placeholder for: %s', 'ayecode-connect' ), $name ) . "</div>";
1503 }
1504
1505 /**
1506 * Sometimes booleans values can be turned to strings, so we fix that.
1507 *
1508 * @param $options
1509 *
1510 * @return mixed
1511 */
1512 public function string_to_bool( $options ) {
1513 // convert bool strings to booleans
1514 foreach ( $options as $key => $val ) {
1515 if ( $val == 'false' ) {
1516 $options[ $key ] = false;
1517 } elseif ( $val == 'true' ) {
1518 $options[ $key ] = true;
1519 }
1520 }
1521
1522 return $options;
1523 }
1524
1525 /**
1526 * Get the argument values that are also filterable.
1527 *
1528 * @param $instance
1529 *
1530 * @return array
1531 *@since 1.0.12 Don't set checkbox default value if the value is empty.
1532 *
1533 */
1534 public function argument_values( $instance ) {
1535 $argument_values = array();
1536
1537 // set widget instance
1538 $this->instance = $instance;
1539
1540 if ( empty( $this->arguments ) ) {
1541 $this->arguments = $this->get_arguments();
1542 }
1543
1544 if ( ! empty( $this->arguments ) ) {
1545 foreach ( $this->arguments as $key => $args ) {
1546 // set the input name from the key
1547 $args['name'] = $key;
1548 //
1549 $argument_values[ $key ] = isset( $instance[ $key ] ) ? $instance[ $key ] : '';
1550 if ( $args['type'] == 'checkbox' && $argument_values[ $key ] == '' ) {
1551 // don't set default for an empty checkbox
1552 } elseif ( $argument_values[ $key ] == '' && isset( $args['default'] ) ) {
1553 $argument_values[ $key ] = $args['default'];
1554 }
1555 }
1556 }
1557
1558 return $argument_values;
1559 }
1560
1561 /**
1562 * Set arguments in super duper.
1563 *
1564 * @return array Set arguments.
1565 *@since 1.0.0
1566 *
1567 */
1568 public function set_arguments() {
1569 return $this->arguments;
1570 }
1571
1572 /**
1573 * Get arguments in super duper.
1574 *
1575 * @return array Get arguments.
1576 *@since 1.0.0
1577 *
1578 */
1579 public function get_arguments() {
1580 if ( empty( $this->arguments ) ) {
1581 $this->arguments = $this->set_arguments();
1582 }
1583
1584 $this->arguments = apply_filters( 'wp_super_duper_arguments', $this->arguments, $this->options, $this->instance );
1585 $this->arguments = $this->add_name_from_key( $this->arguments, true );
1586
1587 if( !empty( $this->arguments['title']['value'] ) ){
1588 $this->arguments['title']['value'] = wp_kses_post( $this->arguments['title']['value'] );
1589 }
1590
1591 return $this->arguments;
1592 }
1593
1594 /**
1595 * This is the main output class for all 3 items, widget, shortcode and block, it is extended in the calling class.
1596 *
1597 * @param array $args
1598 * @param array $widget_args
1599 * @param string $content
1600 */
1601 public function output( $args = array(), $widget_args = array(), $content = '' ) {
1602
1603 }
1604
1605 /**
1606 * Add the dynamic block code inline when the wp-block in enqueued.
1607 */
1608 public function register_block() {
1609 wp_add_inline_script( 'wp-blocks', $this->block() );
1610 if ( class_exists( 'SiteOrigin_Panels' ) ) {
1611 wp_add_inline_script( 'wp-blocks', $this->siteorigin_js() );
1612 }
1613 }
1614
1615 /**
1616 * Check if we need to show advanced options.
1617 *
1618 * @return bool
1619 */
1620 public function block_show_advanced() {
1621
1622 $show = false;
1623 $arguments = $this->get_arguments();
1624
1625 if ( ! empty( $arguments ) ) {
1626 foreach ( $arguments as $argument ) {
1627 if ( isset( $argument['advanced'] ) && $argument['advanced'] ) {
1628 $show = true;
1629 break; // no need to continue if we know we have it
1630 }
1631 }
1632 }
1633
1634 return $show;
1635 }
1636
1637 /**
1638 * Get the url path to the current folder.
1639 *
1640 * @return string
1641 */
1642 public function get_url() {
1643 $url = $this->url;
1644
1645 if ( ! $url ) {
1646 $content_dir = wp_normalize_path( untrailingslashit( WP_CONTENT_DIR ) );
1647 $content_url = untrailingslashit( WP_CONTENT_URL );
1648
1649 // Replace http:// to https://.
1650 if ( strpos( $content_url, 'http://' ) === 0 && strpos( plugins_url(), 'https://' ) === 0 ) {
1651 $content_url = str_replace( 'http://', 'https://', $content_url );
1652 }
1653
1654 // Check if we are inside a plugin
1655 $file_dir = str_replace( "/includes", "", wp_normalize_path( dirname( __FILE__ ) ) );
1656 $url = str_replace( $content_dir, $content_url, $file_dir );
1657 $url = trailingslashit( $url );
1658 $this->url = $url;
1659 }
1660
1661 return $url;
1662 }
1663
1664 /**
1665 * Get the url path to the current folder.
1666 *
1667 * @return string
1668 */
1669 public function get_url_old() {
1670
1671 $url = $this->url;
1672
1673 if ( ! $url ) {
1674 // check if we are inside a plugin
1675 $file_dir = str_replace( "/includes", "", dirname( __FILE__ ) );
1676
1677 $dir_parts = explode( "/wp-content/", $file_dir );
1678 $url_parts = explode( "/wp-content/", plugins_url() );
1679
1680 if ( ! empty( $url_parts[0] ) && ! empty( $dir_parts[1] ) ) {
1681 $url = trailingslashit( $url_parts[0] . "/wp-content/" . $dir_parts[1] );
1682 $this->url = $url;
1683 }
1684 }
1685
1686
1687 return $url;
1688 }
1689
1690 /**
1691 * Generate the block icon.
1692 *
1693 * Enables the use of Font Awesome icons.
1694 *
1695 * @note xlink:href is actually deprecated but href is not supported by all so we use both.
1696 *
1697 * @param $icon
1698 *
1699 * @return string
1700 *@since 1.1.0
1701 */
1702 public function get_block_icon( $icon ) {
1703
1704 // check if we have a Font Awesome icon
1705 $fa_type = '';
1706 if ( substr( $icon, 0, 7 ) === "fas fa-" ) {
1707 $fa_type = 'solid';
1708 } elseif ( substr( $icon, 0, 7 ) === "far fa-" ) {
1709 $fa_type = 'regular';
1710 } elseif ( substr( $icon, 0, 7 ) === "fab fa-" ) {
1711 $fa_type = 'brands';
1712 } else {
1713 $icon = "'" . $icon . "'";
1714 }
1715
1716 // set the icon if we found one
1717 if ( $fa_type ) {
1718 $fa_icon = str_replace( array( "fas fa-", "far fa-", "fab fa-" ), "", $icon );
1719 $icon = "el('svg',{width: 20, height: 20, viewBox: '0 0 20 20'},el('use', {'xlink:href': '" . $this->get_url() . "icons/" . $fa_type . ".svg#" . $fa_icon . "','href': '" . $this->get_url() . "icons/" . $fa_type . ".svg#" . $fa_icon . "'}))";
1720 }
1721
1722 return $icon;
1723 }
1724
1725 public function group_arguments( $arguments ) {
1726 if ( ! empty( $arguments ) ) {
1727 $temp_arguments = array();
1728 $general = __( "General", 'ayecode-connect' );
1729 $add_sections = false;
1730 foreach ( $arguments as $key => $args ) {
1731 if ( isset( $args['group'] ) ) {
1732 $temp_arguments[ $args['group'] ][ $key ] = $args;
1733 $add_sections = true;
1734 } else {
1735 $temp_arguments[ $general ][ $key ] = $args;
1736 }
1737 }
1738
1739 // only add sections if more than one
1740 if ( $add_sections ) {
1741 $arguments = $temp_arguments;
1742 }
1743 }
1744
1745 return $arguments;
1746 }
1747
1748 /**
1749 * Parse used group tabs.
1750 *
1751 * @since 1.1.17
1752 */
1753 public function group_block_tabs( $tabs, $arguments ) {
1754 if ( ! empty( $tabs ) && ! empty( $arguments ) ) {
1755 $has_sections = false;
1756
1757 foreach ( $this->arguments as $key => $args ) {
1758 if ( isset( $args['group'] ) ) {
1759 $has_sections = true;
1760 break;
1761 }
1762 }
1763
1764 if ( ! $has_sections ) {
1765 return $tabs;
1766 }
1767
1768 $new_tabs = array();
1769
1770 foreach ( $tabs as $tab_key => $tab ) {
1771 $new_groups = array();
1772
1773 if ( ! empty( $tab['groups'] ) && is_array( $tab['groups'] ) ) {
1774 foreach ( $tab['groups'] as $group ) {
1775 if ( isset( $arguments[ $group ] ) ) {
1776 $new_groups[] = $group;
1777 }
1778 }
1779 }
1780
1781 if ( ! empty( $new_groups ) ) {
1782 $tab['groups'] = $new_groups;
1783
1784 $new_tabs[ $tab_key ] = $tab;
1785 }
1786 }
1787
1788 $tabs = $new_tabs;
1789 }
1790
1791 return $tabs;
1792 }
1793
1794 /**
1795 * Output the JS for building the dynamic Guntenberg block.
1796 *
1797 * @return mixed
1798 *@since 1.0.9 Save numbers as numbers and not strings.
1799 * @since 1.1.0 Font Awesome classes can be used for icons.
1800 * @since 1.0.4 Added block_wrap property which will set the block wrapping output element ie: div, span, p or empty for no wrap.
1801 */
1802 public function block() {
1803 global $sd_is_js_functions_loaded, $aui_bs5;
1804
1805 $show_advanced = $this->block_show_advanced();
1806
1807 ob_start();
1808 ?>
1809 <script>
1810 <?php
1811 if ( ! $sd_is_js_functions_loaded ) {
1812 $sd_is_js_functions_loaded = true;
1813 ?>
1814 function sd_show_view_options($this){
1815 if(jQuery($this).html().length){
1816 jQuery($this).html('');
1817 }else{
1818 jQuery($this).html('<div class="position-absolute d-flex flex-column bg-white p-1 rounded border shadow-lg " style="top:-80px;left:-5px;"><div class="dashicons dashicons-desktop mb-1" onclick="sd_set_view_type(\'Desktop\');"></div><div class="dashicons dashicons-tablet mb-1" onclick="sd_set_view_type(\'Tablet\');"></div><div class="dashicons dashicons-smartphone" onclick="sd_set_view_type(\'Mobile\');"></div></div>');
1819 }
1820 }
1821
1822 function sd_set_view_type($device){
1823 const wpVersion = '<?php global $wp_version; echo esc_attr($wp_version); ?>';
1824 if (parseFloat(wpVersion) < 6.5) {
1825 wp.data.dispatch('core/edit-site') ? wp.data.dispatch('core/edit-site').__experimentalSetPreviewDeviceType($device) : wp.data.dispatch('core/edit-post').__experimentalSetPreviewDeviceType($device);
1826 } else {
1827 const editorDispatch = wp.data.dispatch('core/editor');
1828 if (editorDispatch) {
1829 editorDispatch.setDeviceType($device);
1830 }
1831 }
1832 }
1833
1834 jQuery(function(){
1835 sd_block_visibility_init();
1836 });
1837 function sd_block_visibility_init() {
1838 jQuery(document).off('change', '.bs-vc-modal-form').on('change', '.bs-vc-modal-form', function() {
1839 try {
1840 aui_conditional_fields('.bs-vc-modal-form');
1841 } catch(err) {
1842 console.log(err.message);
1843 }
1844 });
1845
1846 jQuery(document).off('click', '.bs-vc-save').on('click', '.bs-vc-save', function() {
1847 var $bsvcModal = jQuery(this).closest('.bs-vc-modal'), $bsvcForm = $bsvcModal.find('.bs-vc-modal-form'), vOutput = jQuery('#bsvc_output', $bsvcForm).val(), vOutputN = jQuery('#bsvc_output_n', $bsvcForm).val(), rawValue = '', oVal = {}, oOut = {}, oOutN = {}, iRule = 0;
1848 jQuery(this).addClass('disabled');
1849 jQuery('.bs-vc-modal-form .bs-vc-rule-sets .bs-vc-rule').each(function(){
1850 vRule = jQuery(this).find('.bsvc_rule').val(), oRule = {};
1851 if (vRule == 'logged_in' || vRule == 'logged_out' || vRule == 'post_author') {
1852 oRule.type = vRule;
1853 } else if (vRule == 'user_roles') {
1854 oRule.type = vRule;
1855 if (jQuery(this).find('.bsvc_user_roles:checked').length) {
1856 var user_roles = jQuery(this).find('.bsvc_user_roles:checked').map(function() {
1857 return jQuery(this).val();
1858 }).get();
1859 if (user_roles && user_roles.length) {
1860 oRule.user_roles = user_roles.join(",");
1861 }
1862 }
1863 } else if (vRule == 'gd_field') {
1864 if (jQuery(this).find('.bsvc_gd_field ').val() && jQuery(this).find('.bsvc_gd_field_condition').val()) {
1865 oRule.type = vRule;
1866 oRule.field = jQuery(this).find('.bsvc_gd_field ').val();
1867 oRule.condition = jQuery(this).find('.bsvc_gd_field_condition').val();
1868 if (oRule.condition != 'is_empty' && oRule.condition != 'is_not_empty') {
1869 oRule.search = jQuery(this).find('.bsvc_gd_field_search').val();
1870 }
1871 }
1872 } else {
1873 oRule = jQuery(document).triggerHandler('sd_block_visibility_init', [vRule, oRule, jQuery(this)]);
1874 }
1875
1876 if (Object.keys(oRule).length > 0) {
1877 iRule++;
1878 oVal['rule'+iRule] = oRule;
1879 }
1880 });
1881 if (vOutput == 'hide') {
1882 oOut.type = vOutput;
1883 } else if (vOutput == 'message') {
1884 if (jQuery('#bsvc_message', $bsvcForm).val()) {
1885 oOut.type = vOutput;
1886 oOut.message = jQuery('#bsvc_message', $bsvcForm).val();
1887 if (jQuery('#bsvc_message_type', $bsvcForm).val()) {
1888 oOut.message_type = jQuery('#bsvc_message_type', $bsvcForm).val();
1889 }
1890 }
1891 } else if (vOutput == 'page') {
1892 if (jQuery('#bsvc_page', $bsvcForm).val()) {
1893 oOut.type = vOutput;
1894 oOut.page = jQuery('#bsvc_page', $bsvcForm).val();
1895 }
1896 } else if (vOutput == 'template_part') {
1897 if (jQuery('#bsvc_tmpl_part', $bsvcForm).val()) {
1898 oOut.type = vOutput;
1899 oOut.template_part = jQuery('#bsvc_tmpl_part', $bsvcForm).val();
1900 }
1901 }
1902 if (Object.keys(oOut).length > 0) {
1903 oVal.output = oOut;
1904 }
1905 if (vOutputN == 'hide') {
1906 oOutN.type = vOutputN;
1907 } else if (vOutputN == 'message') {
1908 if (jQuery('#bsvc_message_n', $bsvcForm).val()) {
1909 oOutN.type = vOutputN;
1910 oOutN.message = jQuery('#bsvc_message_n', $bsvcForm).val();
1911 if (jQuery('#bsvc_message_type_n', $bsvcForm).val()) {
1912 oOutN.message_type = jQuery('#bsvc_message_type_n', $bsvcForm).val();
1913 }
1914 }
1915 } else if (vOutputN == 'page') {
1916 if (jQuery('#bsvc_page_n', $bsvcForm).val()) {
1917 oOutN.type = vOutputN;
1918 oOutN.page = jQuery('#bsvc_page_n', $bsvcForm).val();
1919 }
1920 } else if (vOutputN == 'template_part') {
1921 if (jQuery('#bsvc_tmpl_part_n', $bsvcForm).val()) {
1922 oOutN.type = vOutputN;
1923 oOutN.template_part = jQuery('#bsvc_tmpl_part_n', $bsvcForm).val();
1924 }
1925 }
1926 if (Object.keys(oOutN).length > 0) {
1927 oVal.outputN = oOutN;
1928 }
1929 if (Object.keys(oVal).length > 0) {
1930 rawValue = JSON.stringify(oVal);
1931 }
1932 $bsvcModal.find('[name="bsvc_raw_value"]').val(rawValue).trigger('change');
1933 $bsvcModal.find('.bs-vc-close').trigger('click');
1934 });
1935 jQuery(document).off('click', '.bs-vc-add-rule').on('click', '.bs-vc-add-rule', function() {
1936 var bsvcTmpl = jQuery('.bs-vc-rule-template').html();
1937 var c = parseInt(jQuery('.bs-vc-modal-form .bs-vc-rule-sets .bs-vc-rule:last').data('bs-index'));
1938 if (c > 0) {
1939 c++;
1940 } else {
1941 c = 1;
1942 }
1943 bsvcTmpl = bsvcTmpl.replace(/BSVCINDEX/g, c);
1944 jQuery('.bs-vc-modal-form .bs-vc-rule-sets').append(bsvcTmpl);
1945 jQuery('.bs-vc-modal-form .bs-vc-rule-sets .bs-vc-rule .bs-vc-sep-wrap').removeClass('d-none');
1946 jQuery('.bs-vc-modal-form .bs-vc-rule-sets .bs-vc-rule:first .bs-vc-sep-wrap').addClass('d-none');
1947 jQuery('.bs-vc-modal-form .bs-vc-rule-sets .bs-vc-rule:last').find('select').each(function(){
1948 if (!jQuery(this).hasClass('no-select2')) {
1949 jQuery(this).addClass('aui-select2');
1950 }
1951 });
1952 if (!jQuery(this).hasClass('bs-vc-rendering')) {
1953 if(typeof aui_init_select2 == 'function') {
1954 aui_init_select2();
1955 }
1956 if(typeof aui_conditional_fields == 'function') {
1957 aui_conditional_fields('.bs-vc-modal-form');
1958 }
1959 }
1960 });
1961 jQuery(document).off('click', '.bs-vc-remove-rule').on('click', '.bs-vc-remove-rule', function() {
1962 jQuery(this).closest('.bs-vc-rule').remove();
1963 });
1964 }
1965 function sd_block_visibility_render_fields(oValue) {
1966 if (typeof oValue == 'object' && oValue.rule1 && typeof oValue.rule1 == 'object') {
1967 for(k = 1; k <= Object.keys(oValue).length; k++) {
1968 if (oValue['rule' + k] && oValue['rule' + k].type) {
1969 var oRule = oValue['rule' + k];
1970 jQuery('.bs-vc-modal-form .bs-vc-add-rule').addClass('bs-vc-rendering').trigger('click');
1971 var elRule = jQuery('.bs-vc-modal-form .bs-vc-rule-sets .bs-vc-rule:last');
1972 jQuery('select.bsvc_rule', elRule).val(oRule.type);
1973 if (oRule.type == 'user_roles' && oRule.user_roles) {
1974 var user_roles = oRule.user_roles;
1975 if (typeof user_roles == 'string') {
1976 user_roles = user_roles.split(",");
1977 }
1978 if (user_roles.length) {
1979 jQuery.each(user_roles, function(i, role){
1980 elRule.find("input[value='" + role + "']").prop('checked', true);
1981 });
1982 }
1983 jQuery('select.bsvc_user_roles', elRule).val(oRule.user_roles);
1984 } else if (oRule.type == 'gd_field') {
1985 if (oRule.field) {
1986 jQuery('select.bsvc_gd_field', elRule).val(oRule.field);
1987 if (oRule.condition) {
1988 jQuery('select.bsvc_gd_field_condition', elRule).val(oRule.condition);
1989 if (typeof oRule.search != 'undefined' && oRule.condition != 'is_empty' && oRule.condition != 'is_not_empty') {
1990 jQuery('input.bsvc_gd_field_search', elRule).val(oRule.search);
1991 }
1992 }
1993 }
1994 } else {
1995 jQuery(document).trigger('sd_block_visibility_render_fields', [oRule, elRule]);
1996 }
1997
1998 jQuery('.bs-vc-modal-form .bs-vc-add-rule').removeClass('bs-vc-rendering');
1999 }
2000 }
2001
2002 if (oValue.output && oValue.output.type) {
2003 jQuery('.bs-vc-modal-form #bsvc_output').val(oValue.output.type);
2004 if (oValue.output.type == 'message' && typeof oValue.output.message != 'undefined') {
2005 jQuery('.bs-vc-modal-form #bsvc_message').val(oValue.output.message);
2006 if (typeof oValue.output.message_type != 'undefined') {
2007 jQuery('.bs-vc-modal-form #bsvc_message_type').val(oValue.output.message_type);
2008 }
2009 } else if (oValue.output.type == 'page' && typeof oValue.output.page != 'undefined') {
2010 jQuery('.bs-vc-modal-form #bsvc_page').val(oValue.output.page);
2011 } else if (oValue.output.type == 'template_part' && typeof oValue.output.template_part != 'undefined') {
2012 jQuery('.bs-vc-modal-form #bsvc_template_part').val(oValue.output.template_part);
2013 }
2014 }
2015
2016 if (oValue.outputN && oValue.outputN.type) {
2017 jQuery('.bs-vc-modal-form #bsvc_output_n').val(oValue.outputN.type);
2018 if (oValue.outputN.type == 'message' && typeof oValue.outputN.message != 'undefined') {
2019 jQuery('.bs-vc-modal-form #bsvc_message_n').val(oValue.outputN.message);
2020 if (typeof oValue.outputN.message_type != 'undefined') {
2021 jQuery('.bs-vc-modal-form #bsvc_message_type_n').val(oValue.outputN.message_type);
2022 }
2023 } else if (oValue.outputN.type == 'page' && typeof oValue.outputN.page != 'undefined') {
2024 jQuery('.bs-vc-modal-form #bsvc_page_n').val(oValue.outputN.page);
2025 } else if (oValue.outputN.type == 'template_part' && typeof oValue.outputN.template_part != 'undefined') {
2026 jQuery('.bs-vc-modal-form #bsvc_template_part_n').val(oValue.outputN.template_part);
2027 }
2028 }
2029 }
2030 }
2031 /**
2032 * Try to auto-recover blocks.
2033 */
2034 function sd_auto_recover_blocks() {
2035 var recursivelyRecoverInvalidBlockList = blocks => {
2036 const _blocks = [...blocks]
2037 let recoveryCalled = false
2038 const recursivelyRecoverBlocks = willRecoverBlocks => {
2039 willRecoverBlocks.forEach(_block => {
2040 if (!_block.isValid) {
2041 recoveryCalled = true
2042 const newBlock = recoverBlock(_block)
2043 for (const key in newBlock) {
2044 _block[key] = newBlock[key]
2045 }
2046 }
2047 if (_block.innerBlocks.length) {
2048 recursivelyRecoverBlocks(_block.innerBlocks)
2049 }
2050 })
2051 }
2052 recursivelyRecoverBlocks(_blocks)
2053 return [_blocks, recoveryCalled]
2054 }
2055 var recoverBlock = ({ name, attributes, innerBlocks }) => wp.blocks.createBlock(name, attributes, innerBlocks);
2056 var recoverBlocks = blocks => {
2057 return blocks.map(_block => {
2058 const block = _block;
2059 // If the block is a reusable block, recover the Stackable blocks inside it.
2060 if (_block.name === 'core/block') {
2061 const { attributes: { ref } } = _block
2062 const parsedBlocks = wp.blocks.parse(wp.data.select('core').getEntityRecords('postType', 'wp_block', { include: [ref] })?.[0]?.content?.raw) || []
2063 const [recoveredBlocks, recoveryCalled] = recursivelyRecoverInvalidBlockList(parsedBlocks)
2064 if (recoveryCalled) {
2065 console.log('Stackable notice: block ' + block.name + ' (' + block.clientId + ') was auto-recovered, you should not see this after saving your page.');
2066 return { blocks: recoveredBlocks, isReusable: true, ref }
2067 }
2068 } else if (_block.name === 'core/template-part' && _block.attributes && _block.attributes.theme) {
2069 var tmplPart = wp.data.select('core').getEntityRecord('postType', 'wp_template_part', _block.attributes.theme + '//' + _block.attributes.slug);
2070 var tmplPartBlocks = block.innerBlocks && block.innerBlocks.length ? block.innerBlocks : wp.blocks.parse(tmplPart?.content?.raw) || [];
2071 if (tmplPartBlocks && tmplPartBlocks.length && tmplPartBlocks.some(block => !block.isValid)) {
2072 block.innerBlocks = tmplPartBlocks;
2073 block.tmplPartId = _block.attributes.theme + '//' + _block.attributes.slug;
2074 }
2075 }
2076 if (block.innerBlocks && block.innerBlocks.length) {
2077 if (block.tmplPartId) {
2078 console.log('Template part ' + block.tmplPartId + ' block ' + block.name + ' (' + block.clientId + ') starts');
2079 }
2080 const newInnerBlocks = recoverBlocks(block.innerBlocks)
2081 if (newInnerBlocks.some(block => block.recovered)) {
2082 block.innerBlocks = newInnerBlocks
2083 block.replacedClientId = block.clientId
2084 block.recovered = true
2085 }
2086 if (block.tmplPartId) {
2087 console.log('Template part ' + block.tmplPartId + ' block ' + block.name + ' (' + block.clientId + ') ends');
2088 }
2089 }
2090 if (!block.isValid) {
2091 const newBlock = recoverBlock(block)
2092 newBlock.replacedClientId = block.clientId
2093 newBlock.recovered = true
2094 console.log('Stackable notice: block ' + block.name + ' (' + block.clientId + ') was auto-recovered, you should not see this after saving your page.');
2095 return newBlock
2096 }
2097 return block
2098 })
2099 }
2100 // Recover all the blocks that we can find.
2101 var sdBlockEditor = wp.data.select('core/block-editor');
2102 var mainBlocks = sdBlockEditor ? recoverBlocks(sdBlockEditor.getBlocks()) : null;
2103 // Replace the recovered blocks with the new ones.
2104 if (mainBlocks) {
2105 mainBlocks.forEach(block => {
2106 if (block.isReusable && block.ref) {
2107 // Update the reusable blocks.
2108 wp.data.dispatch('core').editEntityRecord('postType', 'wp_block', block.ref, {
2109 content: wp.blocks.serialize(block.blocks)
2110 }).then(() => {
2111 // But don't save them, let the user do the saving themselves. Our goal is to get rid of the block error visually.
2112 })
2113 }
2114 if (block.recovered && block.replacedClientId) {
2115 wp.data.dispatch('core/block-editor').replaceBlock(block.replacedClientId, block)
2116 }
2117 })
2118 }
2119 }
2120
2121 /**
2122 * Try to auto-recover OUR blocks if traditional way fails.
2123 */
2124 function sd_auto_recover_blocks_fallback(editTmpl) {
2125 console.log('sd_auto_recover_blocks_fallback()');
2126 var $bsRecoverBtn = jQuery(".edit-site-visual-editor__editor-canvas").contents().find('div[class*=" wp-block-blockstrap-"] .block-editor-warning__actions .block-editor-warning__action .components-button.is-primary').not(":contains('Keep as HTML')");
2127 if ($bsRecoverBtn.length) {
2128 if(jQuery('.edit-site-layout.is-full-canvas').length || jQuery('.edit-site-layout.is-edit-mode').length){
2129 $bsRecoverBtn.removeAttr('disabled').trigger('click');
2130 }
2131 }
2132 }
2133
2134 <?php if( !isset( $_REQUEST['sd-block-recover-debug'] ) ){ ?>
2135 // Wait will window is loaded before calling.
2136 window.onload = function() {
2137 sd_auto_recover_blocks();
2138 // fire a second time incase of load delays.
2139 setTimeout(function() {
2140 sd_auto_recover_blocks();
2141 }, 5000);
2142
2143 setTimeout(function() {
2144 sd_auto_recover_blocks_fallback();
2145 }, 6000);
2146
2147 setTimeout(function() {
2148 sd_auto_recover_blocks_fallback();
2149 }, 10000);
2150
2151 setTimeout(function() {
2152 sd_auto_recover_blocks_fallback();
2153 }, 15000);
2154
2155 setTimeout(function() {
2156 sd_auto_recover_blocks_fallback();
2157 }, 20000);
2158
2159 setTimeout(function() {
2160 sd_auto_recover_blocks_fallback();
2161 }, 30000);
2162
2163 setTimeout(function() {
2164 sd_auto_recover_blocks_fallback();
2165 }, 60000);
2166
2167 jQuery('.edit-site-page-panels__edit-template-button, .edit-site-visual-editor__editor-canvas').on('click', function() {
2168 setTimeout(function() {
2169 sd_auto_recover_blocks_fallback(true);
2170 jQuery('.edit-site-page-panels__edit-template-button, .edit-site-visual-editor__editor-canvas').addClass('bs-edit-tmpl-clicked');
2171 }, 100);
2172 });
2173 };
2174 <?php } ?>
2175
2176 // fire when URL changes also.
2177 let lastUrl = location.href;
2178 new MutationObserver(() => {
2179 const url = location.href;
2180 if (url !== lastUrl) {
2181 lastUrl = url;
2182 sd_auto_recover_blocks();
2183 // fire a second time incase of load delays.
2184 setTimeout(function() {
2185 sd_auto_recover_blocks();
2186 sd_auto_recover_blocks_fallback();
2187 }, 2000);
2188
2189 setTimeout(function() {
2190 sd_auto_recover_blocks_fallback();
2191 }, 10000);
2192
2193 setTimeout(function() {
2194 sd_auto_recover_blocks_fallback();
2195 }, 15000);
2196
2197 setTimeout(function() {
2198 sd_auto_recover_blocks_fallback();
2199 }, 20000);
2200
2201 }
2202 }).observe(document, {
2203 subtree: true,
2204 childList: true
2205 });
2206
2207
2208 /**
2209 *
2210 * @param $args
2211 * @returns {*|{}}
2212 */
2213 function sd_build_aui_styles($args){
2214
2215 $styles = {};
2216 // background color
2217 if ( $args['bg'] !== undefined && $args['bg'] !== '' ) {
2218 if( $args['bg'] == 'custom-color' ){
2219 $styles['background-color']= $args['bg_color'];
2220 }else if( $args['bg'] == 'custom-gradient' ){
2221 $styles['background-image']= $args['bg_gradient'];
2222
2223 // use background on text
2224 if( $args['bg_on_text'] !== undefined && $args['bg_on_text'] ){
2225 $styles['backgroundClip'] = "text";
2226 $styles['WebkitBackgroundClip'] = "text";
2227 $styles['text-fill-color'] = "transparent";
2228 $styles['WebkitTextFillColor'] = "transparent";
2229 }
2230 }
2231
2232 }
2233
2234 let $bg_image = $args['bg_image'] !== undefined && $args['bg_image'] !== '' ? $args['bg_image'] : '';
2235
2236 // maybe use featured image.
2237 if( $args['bg_image_use_featured'] !== undefined && $args['bg_image_use_featured'] ){
2238 $bg_image = 'data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0idXRmLTgiID8+CjxzdmcgYmFzZVByb2ZpbGU9InRpbnkiIGhlaWdodD0iNDAwIiB2ZXJzaW9uPSIxLjIiIHdpZHRoPSI0MDAiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgeG1sbnM6ZXY9Imh0dHA6Ly93d3cudzMub3JnLzIwMDEveG1sLWV2ZW50cyIgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiPjxkZWZzIC8+PHJlY3QgZmlsbD0iI2QzZDNkMyIgaGVpZ2h0PSI0MDAiIHdpZHRoPSI0MDAiIHg9IjAiIHk9IjAiIC8+PGxpbmUgc3Ryb2tlPSJ3aGl0ZSIgc3Ryb2tlLXdpZHRoPSIxMCIgeDE9IjAiIHgyPSI0MDAiIHkxPSIwIiB5Mj0iNDAwIiAvPjxsaW5lIHN0cm9rZT0id2hpdGUiIHN0cm9rZS13aWR0aD0iMTAiIHgxPSIwIiB4Mj0iNDAwIiB5MT0iNDAwIiB5Mj0iMCIgLz48cmVjdCBmaWxsPSIjZDNkM2QzIiBoZWlnaHQ9IjUwIiB3aWR0aD0iMjE4LjAiIHg9IjkxLjAiIHk9IjE3NS4wIiAvPjx0ZXh0IGZpbGw9IndoaXRlIiBmb250LXNpemU9IjMwIiBmb250LXdlaWdodD0iYm9sZCIgdGV4dC1hbmNob3I9Im1pZGRsZSIgeD0iMjAwLjAiIHk9IjIwNy41Ij5QTEFDRUhPTERFUjwvdGV4dD48L3N2Zz4=';
2239 }
2240
2241 if( $bg_image !== undefined && $bg_image !== '' ){
2242 var hasImage = true
2243 if($styles['background-color'] !== undefined && $args['bg'] == 'custom-color'){
2244 $styles['background-image'] = "url("+$bg_image+")";
2245 $styles['background-blend-mode'] = "overlay";
2246 }else if($styles['background-image'] !== undefined && $args['bg'] == 'custom-gradient'){
2247 $styles['background-image'] += ",url("+$bg_image+")";
2248 }else if($args['bg'] !== undefined && $args['bg'] != '' && $args['bg'] != 'transparent' ){
2249 // do nothing as we already have a preset
2250 hasImage = false;
2251 }else{
2252 $styles['background-image'] = "url("+$bg_image+")";
2253 }
2254
2255 if( hasImage){
2256 $styles['background-size'] = "cover";
2257
2258 if( $args['bg_image_fixed'] !== undefined && $args['bg_image_fixed'] ){
2259 $styles['background-attachment'] = "fixed";
2260 }
2261 }
2262
2263 if( hasImage && $args['bg_image_xy'].x !== undefined && $args['bg_image_xy'].x >=0 ){
2264 $styles['background-position'] = ($args['bg_image_xy'].x * 100 ) + "% " + ( $args['bg_image_xy'].y * 100) + "%";
2265 }
2266 }
2267
2268
2269
2270 // sticky offset top
2271 if( $args['sticky_offset_top'] !== undefined && $args['sticky_offset_top'] !== '' ){
2272 $styles['top'] = $args['sticky_offset_top'];
2273 }
2274
2275 // sticky offset bottom
2276 if( $args['sticky_offset_bottom'] !== undefined && $args['sticky_offset_bottom'] !== '' ){
2277 $styles['bottom'] = $args['sticky_offset_bottom'];
2278 }
2279
2280 // font size
2281 if( $args['font_size'] === undefined || $args['font_size'] === 'custom' ){
2282 if( $args['font_size_custom'] !== undefined && $args['font_size_custom'] !== '' ){
2283 $styles['fontSize'] = $args['font_size_custom'] + "rem";
2284 }
2285 }
2286
2287 // font color
2288 if( $args['text_color'] === undefined || $args['text_color'] === 'custom' ){
2289 if( $args['text_color_custom'] !== undefined && $args['text_color_custom'] !== '' ){
2290 $styles['color'] = $args['text_color_custom'];
2291 }
2292 }
2293
2294 // font line height
2295 if( $args['font_line_height'] !== undefined && $args['font_line_height'] !== '' ){
2296 $styles['lineHeight'] = $args['font_line_height'];
2297 }
2298
2299 // max height
2300 if( $args['max_height'] !== undefined && $args['max_height'] !== '' ){
2301 $styles['maxHeight'] = $args['max_height'];
2302 }
2303
2304 return $styles;
2305
2306 }
2307
2308 function sd_build_aui_class($args){
2309
2310 $classes = [];
2311
2312 <?php
2313 if($aui_bs5){
2314 ?>
2315 $aui_bs5 = true;
2316 $p_ml = 'ms-';
2317 $p_mr = 'me-';
2318
2319 $p_pl = 'ps-';
2320 $p_pr = 'pe-';
2321 <?php
2322 }else{
2323 ?>
2324 $aui_bs5 = false;
2325 $p_ml = 'ml-';
2326 $p_mr = 'mr-';
2327
2328 $p_pl = 'pl-';
2329 $p_pr = 'pr-';
2330 <?php
2331 }
2332 ?>
2333
2334 // margins
2335 if ( $args['mt'] !== undefined && $args['mt'] !== '' ) { $classes.push( "mt-" + $args['mt'] ); $mt = $args['mt']; }else{$mt = null;}
2336 if ( $args['mr'] !== undefined && $args['mr'] !== '' ) { $classes.push( $p_mr + $args['mr'] ); $mr = $args['mr']; }else{$mr = null;}
2337 if ( $args['mb'] !== undefined && $args['mb'] !== '' ) { $classes.push( "mb-" + $args['mb'] ); $mb = $args['mb']; }else{$mb = null;}
2338 if ( $args['ml'] !== undefined && $args['ml'] !== '' ) { $classes.push( $p_ml + $args['ml'] ); $ml = $args['ml']; }else{$ml = null;}
2339
2340 // margins tablet
2341 if ( $args['mt_md'] !== undefined && $args['mt_md'] !== '' ) { $classes.push( "mt-md-" + $args['mt_md'] ); $mt_md = $args['mt_md']; }else{$mt_md = null;}
2342 if ( $args['mr_md'] !== undefined && $args['mr_md'] !== '' ) { $classes.push( $p_mr + "md-" + $args['mr_md'] ); $mt_md = $args['mr_md']; }else{$mr_md = null;}
2343 if ( $args['mb_md'] !== undefined && $args['mb_md'] !== '' ) { $classes.push( "mb-md-" + $args['mb_md'] ); $mt_md = $args['mb_md']; }else{$mb_md = null;}
2344 if ( $args['ml_md'] !== undefined && $args['ml_md'] !== '' ) { $classes.push( $p_ml + "md-" + $args['ml_md'] ); $mt_md = $args['ml_md']; }else{$ml_md = null;}
2345
2346 // margins desktop
2347 if ( $args['mt_lg'] !== undefined && $args['mt_lg'] !== '' ) { if($mt == null && $mt_md == null){ $classes.push( "mt-" + $args['mt_lg'] ); }else{$classes.push( "mt-lg-" + $args['mt_lg'] ); } }
2348 if ( $args['mr_lg'] !== undefined && $args['mr_lg'] !== '' ) { if($mr == null && $mr_md == null){ $classes.push( $p_mr + $args['mr_lg'] ); }else{$classes.push( $p_mr + "lg-" + $args['mr_lg'] ); } }
2349 if ( $args['mb_lg'] !== undefined && $args['mb_lg'] !== '' ) { if($mb == null && $mb_md == null){ $classes.push( "mb-" + $args['mb_lg'] ); }else{$classes.push( "mb-lg-" + $args['mb_lg'] ); } }
2350 if ( $args['ml_lg'] !== undefined && $args['ml_lg'] !== '' ) { if($ml == null && $ml_md == null){ $classes.push( $p_ml + $args['ml_lg'] ); }else{$classes.push( $p_ml + "lg-" + $args['ml_lg'] ); } }
2351
2352 // padding
2353 if ( $args['pt'] !== undefined && $args['pt'] !== '' ) { $classes.push( "pt-" + $args['pt'] ); $pt = $args['pt']; }else{$pt = null;}
2354 if ( $args['pr'] !== undefined && $args['pr'] !== '' ) { $classes.push( $p_pr + $args['pr'] ); $pr = $args['pt']; }else{$pr = null;}
2355 if ( $args['pb'] !== undefined && $args['pb'] !== '' ) { $classes.push( "pb-" + $args['pb'] ); $pb = $args['pt']; }else{$pb = null;}
2356 if ( $args['pl'] !== undefined && $args['pl'] !== '' ) { $classes.push( $p_pl + $args['pl'] ); $pl = $args['pt']; }else{$pl = null;}
2357
2358 // padding tablet
2359 if ( $args['pt_md'] !== undefined && $args['pt_md'] !== '' ) { $classes.push( "pt-md-" + $args['pt_md'] ); $pt_md = $args['pt_md']; }else{$pt_md = null;}
2360 if ( $args['pr_md'] !== undefined && $args['pr_md'] !== '' ) { $classes.push( $p_pr + "md-" + $args['pr_md'] ); $pr_md = $args['pt_md']; }else{$pr_md = null;}
2361 if ( $args['pb_md'] !== undefined && $args['pb_md'] !== '' ) { $classes.push( "pb-md-" + $args['pb_md'] ); $pb_md = $args['pt_md']; }else{$pb_md = null;}
2362 if ( $args['pl_md'] !== undefined && $args['pl_md'] !== '' ) { $classes.push( $p_pl + "md-" + $args['pl_md'] ); $pl_md = $args['pt_md']; }else{$pl_md = null;}
2363
2364 // padding desktop
2365 if ( $args['pt_lg'] !== undefined && $args['pt_lg'] !== '' ) { if($pt == null && $pt_md == null){ $classes.push( "pt-" + $args['pt_lg'] ); }else{$classes.push( "pt-lg-" + $args['pt_lg'] ); } }
2366 if ( $args['pr_lg'] !== undefined && $args['pr_lg'] !== '' ) { if($pr == null && $pr_md == null){ $classes.push( $p_pr + $args['pr_lg'] ); }else{$classes.push( $p_pr + "lg-" + $args['pr_lg'] ); } }
2367 if ( $args['pb_lg'] !== undefined && $args['pb_lg'] !== '' ) { if($pb == null && $pb_md == null){ $classes.push( "pb-" + $args['pb_lg'] ); }else{$classes.push( "pb-lg-" + $args['pb_lg'] ); } }
2368 if ( $args['pl_lg'] !== undefined && $args['pl_lg'] !== '' ) { if($pl == null && $pl_md == null){ $classes.push( $p_pl + $args['pl_lg'] ); }else{$classes.push( $p_pl + "lg-" + $args['pl_lg'] ); } }
2369
2370 // row cols, mobile, tablet, desktop
2371 if ( $args['row_cols'] !== undefined && $args['row_cols'] !== '' ) { $classes.push( "row-cols-" + $args['row_cols'] ); $row_cols = $args['row_cols']; }else{$row_cols = null;}
2372 if ( $args['row_cols_md'] !== undefined && $args['row_cols_md'] !== '' ) { $classes.push( "row-cols-md-" + $args['row_cols_md'] ); $row_cols_md = $args['row_cols_md']; }else{$row_cols_md = null;}
2373 if ( $args['row_cols_lg'] !== undefined && $args['row_cols_lg'] !== '' ) { if($row_cols == null && $row_cols_md == null){ $classes.push( "row-cols-" + $args['row_cols_lg'] ); }else{$classes.push( "row-cols-lg-" + $args['row_cols_lg'] ); } }
2374
2375 // columns , mobile, tablet, desktop
2376 if ( $args['col'] !== undefined && $args['col'] !== '' ) { $classes.push( "col-" + $args['col'] ); $col = $args['col']; }else{$col = null;}
2377 if ( $args['col_md'] !== undefined && $args['col_md'] !== '' ) { $classes.push( "col-md-" + $args['col_md'] ); $col_md = $args['col_md']; }else{$col_md = null;}
2378 if ( $args['col_lg'] !== undefined && $args['col_lg'] !== '' ) { if($col == null && $col_md == null){ $classes.push( "col-" + $args['col_lg'] ); }else{$classes.push( "col-lg-" + $args['col_lg'] ); } }
2379
2380
2381 // border
2382 if ( $args['border'] === undefined || $args['border']=='') { }
2383 else if ( $args['border'] !== undefined && ( $args['border']=='none' || $args['border']==='0') ) { $classes.push( "border-0" ); }
2384 else if ( $args['border'] !== undefined ) {
2385 if($aui_bs5 && $args['border_type'] !== undefined){
2386 $args['border_type'] = $args['border_type'].replace('-left','-start').replace('-right','-end');
2387 }
2388 $border_class = 'border';
2389 if ( $args['border_type'] !== undefined && ! $args['border_type'].includes( '-0' ) ) {
2390 $border_class = '';
2391 }
2392 $classes.push( $border_class + " border-" + $args['border'] );
2393 }
2394
2395 // border radius type
2396 // if ( $args['rounded'] !== undefined && $args['rounded'] !== '' ) { $classes.push($args['rounded']); }
2397
2398 // border radius size
2399 if( $args['rounded_size'] !== undefined && ( $args['rounded_size']==='sm' || $args['rounded_size']==='lg' ) ){
2400 if ( $args['rounded_size'] !== undefined && $args['rounded_size'] !== '' ) {
2401 $classes.push("rounded-" + $args['rounded_size']);
2402 // if we set a size then we need to remove "rounded" if set
2403 var index = $classes.indexOf("rounded");
2404 if (index !== -1) {
2405 $classes.splice(index, 1);
2406 }
2407 }
2408 }else{
2409 // rounded_size , mobile, tablet, desktop
2410 if ( $args['rounded_size'] !== undefined && $args['rounded_size'] !== '' ) { $classes.push( "rounded-" + $args['rounded_size'] ); $rounded_size = $args['rounded_size']; }else{$rounded_size = null;}
2411 if ( $args['rounded_size_md'] !== undefined && $args['rounded_size_md'] !== '' ) { $classes.push( "rounded-md-" + $args['rounded_size_md'] ); $rounded_size_md = $args['rounded_size_md']; }else{$rounded_size_md = null;}
2412 if ( $args['rounded_size_lg'] !== undefined && $args['rounded_size_lg'] !== '' ) { if($rounded_size == null && $rounded_size_md == null){ $classes.push( "rounded-" + $args['rounded_size_lg'] ); }else{$classes.push( "rounded-lg-" + $args['rounded_size_lg'] ); } }
2413 }
2414
2415
2416 // shadow
2417 // if ( $args['shadow'] !== undefined && $args['shadow'] !== '' ) { $classes.push($args['shadow']); }
2418
2419 // background
2420 if ( $args['bg'] !== undefined && $args['bg'] !== '' ) { $classes.push("bg-" + $args['bg']); }
2421
2422 // background image fixed bg_image_fixed
2423 if ( $args['bg_image_fixed'] !== undefined && $args['bg_image_fixed'] !== '' ) { $classes.push("bg-image-fixed"); }
2424
2425 // text_color
2426 if ( $args['text_color'] !== undefined && $args['text_color'] !== '' ) { $classes.push( "text-" + $args['text_color']); }
2427
2428 // text_align
2429 if ( $args['text_justify'] !== undefined && $args['text_justify'] ) { $classes.push('text-justify'); }
2430 else{
2431 if ( $args['text_align'] !== undefined && $args['text_align'] !== '' ) {
2432 if($aui_bs5){ $args['text_align'] = $args['text_align'].replace('-left','-start').replace('-right','-end'); }
2433 $classes.push($args['text_align']); $text_align = $args['text_align'];
2434 }else{$text_align = null;}
2435 if ( $args['text_align_md'] !== undefined && $args['text_align_md'] !== '' ) {
2436 if($aui_bs5){ $args['text_align_md'] = $args['text_align_md'].replace('-left','-start').replace('-right','-end'); }
2437 $classes.push($args['text_align_md']); $text_align_md = $args['text_align_md'];
2438 }else{$text_align_md = null;}
2439 if ( $args['text_align_lg'] !== undefined && $args['text_align_lg'] !== '' ) {
2440 if($aui_bs5){ $args['text_align_lg'] = $args['text_align_lg'].replace('-left','-start').replace('-right','-end'); }
2441 if($text_align == null && $text_align_md == null){ $classes.push($args['text_align_lg'].replace("-lg", ""));
2442 }else{$classes.push($args['text_align_lg']);} }
2443 }
2444
2445 // display
2446 if ( $args['display'] !== undefined && $args['display'] !== '' ) { $classes.push($args['display']); $display = $args['display']; }else{$display = null;}
2447 if ( $args['display_md'] !== undefined && $args['display_md'] !== '' ) { $classes.push($args['display_md']); $display_md = $args['display_md']; }else{$display_md = null;}
2448 if ( $args['display_lg'] !== undefined && $args['display_lg'] !== '' ) { if($display == null && $display_md == null){ $classes.push($args['display_lg'].replace("-lg", "")); }else{$classes.push($args['display_lg']);} }
2449
2450 // bgtus - background transparent until scroll
2451 if ( $args['bgtus'] !== undefined && $args['bgtus'] ) { $classes.push("bg-transparent-until-scroll"); }
2452
2453 // cscos - change color scheme on scroll
2454 if ( $args['bgtus'] !== undefined && $args['bgtus'] && $args['cscos'] !== undefined && $args['cscos'] ) { $classes.push("color-scheme-flip-on-scroll"); }
2455
2456 // hover animations
2457 if ( $args['hover_animations'] !== undefined && $args['hover_animations'] ) { $classes.push($args['hover_animations'].toString().replace(',',' ')); }
2458
2459 // absolute_position
2460 if ( $args['absolute_position'] !== undefined ) {
2461 if ( 'top-left' === $args['absolute_position'] ) {
2462 $classes.push('start-0 top-0');
2463 } else if ( 'top-center' === $args['absolute_position'] ) {
2464 $classes.push('start-50 top-0 translate-middle');
2465 } else if ( 'top-right' === $args['absolute_position'] ) {
2466 $classes.push('end-0 top-0');
2467 } else if ( 'center-left' === $args['absolute_position'] ) {
2468 $classes.push('start-0 bottom-50');
2469 } else if ( 'center' === $args['absolute_position'] ) {
2470 $classes.push('start-50 top-50 translate-middle');
2471 } else if ( 'center-right' === $args['absolute_position'] ) {
2472 $classes.push('end-0 top-50');
2473 } else if ( 'bottom-left' === $args['absolute_position'] ) {
2474 $classes.push('start-0 bottom-0');
2475 } else if ( 'bottom-center' === $args['absolute_position'] ) {
2476 $classes.push('start-50 bottom-0 translate-middle');
2477 } else if ( 'bottom-right' === $args['absolute_position'] ) {
2478 $classes.push('end-0 bottom-0');
2479 }
2480 }
2481
2482 // build classes from build keys
2483 $build_keys = sd_get_class_build_keys();
2484 if ( $build_keys.length ) {
2485 $build_keys.forEach($key => {
2486
2487 if($key.endsWith("-MTD")){
2488
2489 $k = $key.replace("-MTD","");
2490
2491 // Mobile, Tablet, Desktop
2492 if ( $args[$k] !== undefined && $args[$k] !== '' ) { $classes.push( $args[$k] ); $v = $args[$k]; }else{$v = null;}
2493 if ( $args[$k + '_md'] !== undefined && $args[$k + '_md'] !== '' ) { $classes.push( $args[$k + '_md'] ); $v_md = $args[$k + '_md']; }else{$v_md = null;}
2494 if ( $args[$k + '_lg'] !== undefined && $args[$k + '_lg'] !== '' ) { if($v == null && $v_md == null){ $classes.push( $args[$k + '_lg'].replace('-lg','') ); }else{$classes.push( $args[$k + '_lg'] ); } }
2495
2496 }else{
2497 if ( $key == 'font_size' && ( $args[ $key ] == 'custom' || $args[ $key ] === '0' ) ) {
2498 return;
2499 }
2500 if ( $args[$key] !== undefined && $args[$key] !== '' ) { $classes.push($args[$key]); }
2501 }
2502
2503 });
2504 }
2505
2506 return $classes.join(" ");
2507 }
2508
2509 function sd_get_class_build_keys(){
2510 return <?php echo json_encode(sd_get_class_build_keys());?>;
2511 }
2512
2513 <?php
2514
2515
2516 }
2517
2518 if(method_exists($this,'block_global_js')){
2519 echo $this->block_global_js();
2520 }
2521 ?>
2522
2523 jQuery(function() {
2524
2525 /**
2526 * BLOCK: Basic
2527 *
2528 * Registering a basic block with Gutenberg.
2529 * Simple block, renders and saves the same content without any interactivity.
2530 *
2531 * Styles:
2532 * editor.css — Editor styles for the block.
2533 * style.css — Editor & Front end styles for the block.
2534 */
2535 (function (blocksx, elementx, blockEditor) {
2536 if (typeof blockEditor === 'undefined') {
2537 return;<?php /* Yoast SEO load blocks.js without block-editor.js on post edit pages */ ?>
2538 }
2539 var __ = wp.i18n.__; // The __() for internationalization.
2540 var el = wp.element.createElement; // The wp.element.createElement() function to create elements.
2541 var editable = wp.blocks.Editable;
2542 var blocks = wp.blocks;
2543 var registerBlockType = wp.blocks.registerBlockType; // The registerBlockType() to register blocks.
2544 var is_fetching = false;
2545 var prev_attributes = [];
2546
2547 var InnerBlocks = blockEditor.InnerBlocks;
2548
2549 var term_query_type = '';
2550 var post_type_rest_slugs = <?php if(! empty( $this->arguments ) && isset($this->arguments['post_type']['onchange_rest']['values'])){echo "[".json_encode($this->arguments['post_type']['onchange_rest']['values'])."]";}else{echo "[]";} ?>;
2551 const taxonomies_<?php echo str_replace("-","_", $this->id);?> = [{label: "Please wait", value: 0}];
2552 const sort_by_<?php echo str_replace("-","_", $this->id);?> = [{label: "Please wait", value: 0}];
2553 const MediaUpload = wp.blockEditor.MediaUpload;
2554
2555 /**
2556 * Register Basic Block.
2557 *
2558 * Registers a new block provided a unique name and an object defining its
2559 * behavior. Once registered, the block is made available as an option to any
2560 * editor interface where blocks are implemented.
2561 *
2562 * @param {string} name Block name.
2563 * @param {Object} settings Block settings.
2564 * @return {?WPBlock} The block, if it has been successfully
2565 * registered; otherwise `undefined`.
2566 */
2567 registerBlockType('<?php echo str_replace( "_", "-", sanitize_title_with_dashes( $this->options['textdomain'] ) . '/' . sanitize_title_with_dashes( $this->options['class_name'] ) ); ?>', { // Block name. Block names must be string that contains a namespace prefix. Example: my-plugin/my-custom-block.
2568 apiVersion: <?php echo isset($this->options['block-api-version']) ? absint($this->options['block-api-version']) : 2 ; ?>,
2569 title: '<?php echo addslashes( $this->options['name'] ); ?>', // Block title.
2570 description: '<?php echo addslashes( $this->options['widget_ops']['description'] )?>', // Block title.
2571 icon: <?php echo $this->get_block_icon( $this->options['block-icon'] );?>,//'<?php echo isset( $this->options['block-icon'] ) ? esc_attr( $this->options['block-icon'] ) : 'shield-alt';?>', // Block icon from Dashicons → https://developer.wordpress.org/resource/dashicons/.
2572 supports: {
2573 <?php
2574 if(!isset($this->options['block-supports']['renaming'])){
2575 $this->options['block-supports']['renaming'] = false;
2576 }
2577 if ( isset( $this->options['block-supports'] ) ) {
2578 echo $this->array_to_attributes( $this->options['block-supports'] );
2579 }
2580 ?>
2581 },
2582 __experimentalLabel( attributes, { context } ) {
2583 var visibility_html = attributes && attributes.visibility_conditions ? ' &#128065;' : '';
2584 var metadata_name = attributes && attributes.metadata && attributes.metadata.name ? attributes.metadata.name : '';
2585 var label_name = <?php echo !empty($this->options['block-label']) ? $this->options['block-label'] : "'" . esc_attr( addslashes( $this->options['name'] ) ) . "'"; ?>;
2586 return metadata_name ? metadata_name + visibility_html : label_name + visibility_html;
2587 },
2588 category: '<?php echo isset( $this->options['block-category'] ) ? esc_attr( $this->options['block-category'] ) : 'common';?>', // Block category — Group blocks together based on common traits E.g. common, formatting, layout widgets, embed.
2589 <?php if ( isset( $this->options['block-keywords'] ) ) {
2590 echo "keywords : " . $this->options['block-keywords'] . ",";
2591 }
2592
2593
2594 // block hover preview.
2595 $example_args = array();
2596 if(!empty($this->arguments)){
2597 foreach($this->arguments as $key => $a_args){
2598 if(isset($a_args['example'])){
2599 $example_args[$key] = $a_args['example'];
2600 }
2601 }
2602 }
2603 $viewport_width = isset($this->options['example']['viewportWidth']) ? 'viewportWidth: '.absint($this->options['example']['viewportWidth']) : '';
2604 $example_inner_blocks = !empty($this->options['example']['innerBlocks']) && is_array($this->options['example']['innerBlocks']) ? 'innerBlocks: ' . wp_json_encode($this->options['example']['innerBlocks']) : '';
2605 if( isset( $this->options['example'] ) && $this->options['example'] === false ){
2606 // no preview if set to false
2607 }elseif( !empty( $example_args ) ){
2608 echo "example : {attributes:{".$this->array_to_attributes( $example_args )."},$viewport_width},";
2609 }elseif( !empty( $this->options['example'] ) ){
2610 unset($this->options['example']['viewportWidth']);
2611 unset($this->options['example']['innerBlocks']);
2612 $example_atts = $this->array_to_attributes( $this->options['example'] );
2613 $example_parts = array();
2614 if($example_atts){
2615 $example_parts[] = rtrim($example_atts,",");
2616 }
2617 if($viewport_width){
2618 $example_parts[] = $viewport_width;
2619 }
2620 if($example_inner_blocks){
2621 $example_parts[] = $example_inner_blocks;
2622 }
2623 if(!empty($example_parts)){
2624 echo "example : {".implode(',', $example_parts)."},";
2625 }
2626 }else{
2627 echo 'example : {viewportWidth: 500},';
2628 }
2629
2630
2631
2632 // limit to parent
2633 if( !empty( $this->options['parent'] ) ){
2634 echo "parent : " . wp_json_encode( $this->options['parent'] ) . ",";
2635 }
2636
2637 // limit allowed blocks
2638 if( !empty( $this->options['allowed-blocks'] ) ){
2639 echo "allowedBlocks : " . wp_json_encode( $this->options['allowed-blocks'] ) . ",";
2640 }
2641
2642 // maybe set no_wrap
2643 $no_wrap = isset( $this->options['no_wrap'] ) && $this->options['no_wrap'] ? true : false;
2644 if ( isset( $this->arguments['no_wrap'] ) && $this->arguments['no_wrap'] ) {
2645 $no_wrap = true;
2646 }
2647 if ( $no_wrap ) {
2648 $this->options['block-wrap'] = '';
2649 }
2650
2651 // Maybe load the drag/drop functions.
2652 $img_drag_drop = false;
2653 $show_alignment = false;
2654
2655 echo "attributes : {";
2656
2657 if ( $show_advanced ) {
2658 echo "show_advanced: {";
2659 echo " type: 'boolean',";
2660 echo " default: false";
2661 echo "},";
2662 }
2663
2664 // Block wrap element
2665 if ( ! empty( $this->options['block-wrap'] ) ) { //@todo we should validate this?
2666 echo "block_wrap: {";
2667 echo " type: 'string',";
2668 echo " default: '" . esc_attr( $this->options['block-wrap'] ) . "'";
2669 echo "},";
2670 }
2671
2672 if ( ! empty( $this->arguments ) ) {
2673 foreach ( $this->arguments as $key => $args ) {
2674 if ( $args['type'] == 'image' || $args['type'] == 'images' ) {
2675 $img_drag_drop = true;
2676 }
2677
2678 // Set if we should show alignment.
2679 if ( $key == 'alignment' ) {
2680 $show_alignment = true;
2681 }
2682
2683 $extra = '';
2684 $_default = isset( $args['default'] ) && ! is_null( $args['default'] ) ? $args['default'] : '';
2685
2686 if ( ! empty( $_default ) ) {
2687 $_default = wp_slash( $_default );
2688 }
2689
2690 if ( $args['type'] == 'notice' || $args['type'] == 'tab' ) {
2691 continue;
2692 } else if ( $args['type'] == 'checkbox' ) {
2693 $type = 'boolean';
2694 $default = $_default ? 'true' : 'false';
2695 } else if ( $args['type'] == 'number' ) {
2696 $type = 'number';
2697 $default = "'" . $_default . "'";
2698 } else if ( $args['type'] == 'select' && ! empty( $args['multiple'] ) ) {
2699 $type = 'array';
2700 if ( isset( $args['default'] ) && is_array( $args['default'] ) ) {
2701 $default = ! empty( $_default ) ? "['" . implode( "','", $_default ) . "']" : "[]";
2702 } else {
2703 $default = "'" . $_default . "'";
2704 }
2705 } else if ( $args['type'] == 'tagselect' ) {
2706 $type = 'array';
2707 $default = "'" . $_default . "'";
2708 } else if ( $args['type'] == 'multiselect' ) {
2709 $type = 'array';
2710 $default = "'" . $_default . "'";
2711 } else if ( $args['type'] == 'image_xy' ) {
2712 $type = 'object';
2713 $default = "'" . $_default . "'";
2714 } else if ( $args['type'] == 'image' ) {
2715 $type = 'string';
2716 $default = "'" . $_default . "'";
2717 } else {
2718 $type = ! empty( $args['hidden_type'] ) ? esc_attr( $args['hidden_type'] ) : 'string';
2719 $default = "'" . $_default . "'";
2720 }
2721
2722 echo $key . " : {";
2723 echo "type : '$type',";
2724 echo "default : $default";
2725 echo "},";
2726 }
2727 }
2728
2729 echo "content : {type : 'string',default: 'Please select the attributes in the block settings'},";
2730 echo "sd_shortcode : {type : 'string',default: ''},";
2731
2732 if ( ! empty( $this->options['nested-block'] ) || ! empty( $this->arguments['html'] ) ) {
2733 echo "sd_shortcode_close : {type : 'string',default: ''},";
2734 }
2735
2736 echo "className: { type: 'string', default: '' }";
2737 echo "},";
2738 ?>
2739 // The "edit" property must be a valid function.
2740 edit: function (props) {
2741 const selectedBlock = wp.data.select('core/block-editor').getSelectedBlock();
2742 <?php
2743 // only include the drag/drop functions if required.
2744 if ( $img_drag_drop ) {
2745 ?>
2746
2747 function enableDragSort(listClass) {
2748 setTimeout(function(){
2749 const sortableLists = document.getElementsByClassName(listClass);
2750 Array.prototype.map.call(sortableLists, (list) => {enableDragList(list)});
2751 }, 300);
2752 }
2753
2754 function enableDragList(list) {
2755 Array.prototype.map.call(list.children, (item) => {enableDragItem(item)});
2756 }
2757
2758 function enableDragItem(item) {
2759 item.setAttribute('draggable', true)
2760 item.ondrag = handleDrag;
2761 item.ondragend = handleDrop;
2762 }
2763
2764 function handleDrag(item) {
2765 const selectedItem = item.target,
2766 list = selectedItem.parentNode,
2767 x = event.clientX,
2768 y = event.clientY;
2769
2770 selectedItem.classList.add('drag-sort-active');
2771 let swapItem = document.elementFromPoint(x, y) === null ? selectedItem : document.elementFromPoint(x, y);
2772
2773 if (list === swapItem.parentNode) {
2774 swapItem = swapItem !== selectedItem.nextSibling ? swapItem : swapItem.nextSibling;
2775 list.insertBefore(selectedItem, swapItem);
2776 }
2777 }
2778
2779 function handleDrop(item) {
2780
2781 item.target.classList.remove('drag-sort-active');
2782
2783 const newOrder = [];
2784 let $parent = item.target.parentNode;
2785 let $field = $parent.dataset.field;
2786 let $imgs = JSON.parse('[' + props.attributes[$field] + ']');
2787 item.target.parentNode.classList.add('xxx');
2788 $children = $parent.children;
2789
2790 Object.keys($children).forEach(function(key) {
2791 let $nKey = $children[key].dataset.index
2792 newOrder.push($imgs[$nKey]);
2793 });
2794
2795 // @todo find out why we need to empty the value first otherwise the order is wrong.
2796 props.setAttributes({ [$field]: '' });
2797 setTimeout(function(){
2798 props.setAttributes({ [$field]: JSON.stringify(newOrder).replace('[','').replace(']','') });
2799 }, 100);
2800
2801 }
2802 <?php } ?>
2803
2804 if (typeof(props.attributes.styleid) !== 'undefined') {
2805 var _styleId = props.attributes.styleid, setStyleId;
2806 if (!window.sdStyleId) {
2807 window.sdStyleId = [];
2808 }
2809 if (_styleId) {
2810 if (window.sdStyleId && window.sdStyleId[_styleId] && window.sdStyleId[_styleId] != props.clientId) {
2811 setStyleId = true;
2812 }
2813 } else {
2814 setStyleId = true;
2815 }
2816 if (setStyleId) {
2817 _styleId = 'block-' + (Math.random() + 1).toString(36).substring(2);
2818 }
2819 window.sdStyleId[_styleId] = props.clientId;
2820 if (setStyleId) {
2821 props.setAttributes({'styleid': _styleId});
2822 }
2823 }
2824
2825 <?php
2826 if(!empty($this->options['block-edit-raw'])) {
2827 echo $this->options['block-edit-raw']; // strings have to be in single quotes, may cause issues
2828 }else{
2829 ?>
2830
2831 function hasSelectedInnerBlock(props) {
2832 const select = wp.data.select('core/editor');
2833 const selected = select.getBlockSelectionStart();
2834 const inner = select.getBlock(props.clientId).innerBlocks;
2835 for (let i = 0; i < inner.length; i++) {
2836 if (inner[i].clientId === selected || inner[i].innerBlocks.length && hasSelectedInnerBlock(inner[i])) {
2837 return true;
2838 }
2839 }
2840 return false;
2841 };
2842
2843 const parentBlocksIDs = wp.data.select( 'core/block-editor' ).getBlockParents(props.clientId);
2844 const parentBlocks = wp.data.select('core/block-editor').getBlocksByClientId(parentBlocksIDs);
2845 // const isParentOfSelectedBlock = useSelect( ( select ) => wp.data.select( 'core/block-editor' ).hasSelectedInnerBlock( props.clientId, true ) ):
2846 const block = wp.data.select('core/block-editor').getBlocksByClientId(props.clientId);//.[0].innerBlocks;
2847 const childBlocks = block[0] == null ? '' : block[0].innerBlocks;
2848
2849 var $value = '';
2850 <?php
2851 // if we have a post_type and a category then link them
2852 if( isset($this->arguments['post_type']) && isset($this->arguments['category']) && !empty($this->arguments['category']['post_type_linked']) ){
2853 ?>
2854 if(typeof(prev_attributes[props.clientId]) != 'undefined' && selectedBlock && selectedBlock.clientId === props.clientId){
2855 $pt = props.attributes.post_type;
2856 if(post_type_rest_slugs.length){
2857 $value = post_type_rest_slugs[0][$pt];
2858 }
2859 var run = false;
2860
2861 if($pt != term_query_type){
2862 run = true;
2863 term_query_type = $pt;
2864 }
2865 <?php
2866 $cat_path = '';
2867 if ( ! empty( $this->arguments['post_type']['onchange_rest']['path'] ) ) {
2868 $cat_path = esc_js( strip_tags( $this->arguments['post_type']['onchange_rest']['path'] ) );
2869 $cat_path = str_replace( array( '&quot;', '&#039;' ), array( '"', "'" ), $cat_path );
2870 }
2871 ?>
2872 /* taxonomies */
2873 if($value && 'post_type' in prev_attributes[props.clientId] && 'category' in prev_attributes[props.clientId] && run){
2874 if (!window.gdCPTCats) {
2875 window.gdCPTCats = [];
2876 }
2877 var gdCatPath = "<?php echo ( ! empty( $cat_path ) ? $cat_path : "/wp/v2/" + $value + "/categories/?per_page=100" ); ?>";
2878 if (window.gdCPTCats[gdCatPath]) {
2879 terms = window.gdCPTCats[gdCatPath];
2880 while (taxonomies_<?php echo str_replace("-","_", $this->id);?>.length) {
2881 taxonomies_<?php echo str_replace("-","_", $this->id);?>.pop();
2882 }
2883 taxonomies_<?php echo str_replace("-","_", $this->id);?>.push({label: "All", value: 0});
2884 jQuery.each( terms, function( key, val ) {
2885 taxonomies_<?php echo str_replace("-","_", $this->id);?>.push({label: val.name, value: val.id});
2886 });
2887
2888 /* Setting the value back and fourth fixes the no update issue that sometimes happens where it won't update the options. */
2889 var $old_cat_value = props.attributes.category
2890 props.setAttributes({category: [0] });
2891 props.setAttributes({category: $old_cat_value });
2892 } else {
2893 wp.apiFetch({path: gdCatPath}).then(terms => {
2894 window.gdCPTCats[gdCatPath] = terms;
2895 while (taxonomies_<?php echo str_replace("-","_", $this->id);?>.length) {
2896 taxonomies_<?php echo str_replace("-","_", $this->id);?>.pop();
2897 }
2898 taxonomies_<?php echo str_replace("-","_", $this->id);?>.push({label: "All", value: 0});
2899 jQuery.each( terms, function( key, val ) {
2900 taxonomies_<?php echo str_replace("-","_", $this->id);?>.push({label: val.name, value: val.id});
2901 });
2902
2903 /* Setting the value back and fourth fixes the no update issue that sometimes happens where it won't update the options. */
2904 var $old_cat_value = props.attributes.category
2905 props.setAttributes({category: [0] });
2906 props.setAttributes({category: $old_cat_value });
2907
2908 return taxonomies_<?php echo str_replace("-","_", $this->id);?>;
2909 });
2910 }
2911 }
2912
2913 /* sort_by */
2914 if($value && 'post_type' in prev_attributes[props.clientId] && 'sort_by' in prev_attributes[props.clientId] && run){
2915 if (!window.gdCPTSort) {
2916 window.gdCPTSort = [];
2917 }
2918 if (window.gdCPTSort[$pt]) {
2919 response = window.gdCPTSort[$pt];
2920 while (sort_by_<?php echo str_replace("-","_", $this->id);?>.length) {
2921 sort_by_<?php echo str_replace("-","_", $this->id);?>.pop();
2922 }
2923
2924 jQuery.each( response, function( key, val ) {
2925 sort_by_<?php echo str_replace("-","_", $this->id);?>.push({label: val, value: key});
2926 });
2927
2928 // setting the value back and fourth fixes the no update issue that sometimes happens where it won't update the options.
2929 var $old_sort_by_value = props.attributes.sort_by
2930 props.setAttributes({sort_by: [0] });
2931 props.setAttributes({sort_by: $old_sort_by_value });
2932 } else {
2933 var data = {
2934 'action': 'geodir_get_sort_options',
2935 'post_type': $pt
2936 };
2937 jQuery.post(ajaxurl, data, function(response) {
2938 response = JSON.parse(response);
2939 window.gdCPTSort[$pt] = response;
2940 while (sort_by_<?php echo str_replace("-","_", $this->id);?>.length) {
2941 sort_by_<?php echo str_replace("-","_", $this->id);?>.pop();
2942 }
2943
2944 jQuery.each( response, function( key, val ) {
2945 sort_by_<?php echo str_replace("-","_", $this->id);?>.push({label: val, value: key});
2946 });
2947
2948 // setting the value back and fourth fixes the no update issue that sometimes happens where it won't update the options.
2949 var $old_sort_by_value = props.attributes.sort_by
2950 props.setAttributes({sort_by: [0] });
2951 props.setAttributes({sort_by: $old_sort_by_value });
2952
2953 return sort_by_<?php echo str_replace("-","_", $this->id);?>;
2954 });
2955 }
2956 }
2957 }
2958 <?php } ?>
2959 <?php
2960 $current_screen = function_exists('get_current_screen') ? get_current_screen() : '';
2961 if(!empty($current_screen->base) && $current_screen->base==='widgets'){
2962 echo 'const { deviceType } = "";';
2963 }else{
2964 ?>
2965 /** Get device type const. */
2966 const wpVersion = '<?php global $wp_version; echo esc_attr($wp_version); ?>';
2967 const { deviceType } = typeof wp.data.useSelect !== 'undefined' ? wp.data.useSelect(select => {
2968 if (parseFloat(wpVersion) < 6.5) {
2969 const { __experimentalGetPreviewDeviceType } = select('core/edit-site') ? select('core/edit-site') : select('core/edit-post') ? select('core/edit-post') : '';
2970 return {
2971 deviceType: __experimentalGetPreviewDeviceType(),
2972 };
2973 } else {
2974 const editorSelect = select('core/editor');
2975 if (editorSelect) {
2976 return {
2977 deviceType: editorSelect.getDeviceType(),
2978 };
2979 } else {
2980 return {
2981 deviceType: 'Desktop', // Default value if device type is not available
2982 };
2983 }
2984 }
2985 }, []) : '';
2986 <?php } ?>
2987 var content = props.attributes.content, shortcode = '';
2988
2989 function onChangeContent($type) {
2990 $refresh = false;
2991 // Set the old content the same as the new one so we only compare all other attributes
2992 if(typeof(prev_attributes[props.clientId]) != 'undefined'){
2993 prev_attributes[props.clientId].content = props.attributes.content;
2994
2995 // don't compare the sd_shortcode as it is changed later
2996 prev_attributes[props.clientId].sd_shortcode = props.attributes.sd_shortcode;
2997 }else if(props.attributes.content === ""){
2998 // if first load and content empty then refresh
2999 $refresh = true;
3000 } else {
3001 // if not new and has content then set it so we dont go fetch it
3002 if(props.attributes.content && props.attributes.content !== 'Please select the attributes in the block settings'){
3003 prev_attributes[props.clientId] = props.attributes;
3004 }
3005 }
3006
3007 if ( ( !is_fetching && JSON.stringify(prev_attributes[props.clientId]) != JSON.stringify(props.attributes) ) || $refresh ) {
3008 is_fetching = true;
3009
3010 var data = {
3011 'action': 'super_duper_output_shortcode',
3012 'shortcode': '<?php echo $this->options['base_id'];?>',
3013 'attributes': props.attributes,
3014 'block_parent_name': parentBlocks.length ? parentBlocks[parentBlocks.length - 1].name : '',
3015 'post_id': <?php global $post; if ( isset( $post->ID ) ) {
3016 echo $post->ID;
3017 }else{echo '0';}?>,
3018 '_ajax_nonce': '<?php echo wp_create_nonce( 'super_duper_output_shortcode' );?>'
3019 };
3020
3021 jQuery.post(ajaxurl, data, function (response) {
3022 return response;
3023 }).then(function (env) {
3024 // if the content is empty then we place some placeholder text
3025 if (env == '') {
3026 env = "<div style='background:#0185ba33;padding: 10px;border: 4px #ccc dashed;'>" + "<?php _e( 'Placeholder for:', 'ayecode-connect' );?> " + props.name + "</div>";
3027 }
3028
3029 <?php
3030 if(!empty($this->options['nested-block'])){
3031 ?>
3032 // props.setAttributes({content: env});
3033 is_fetching = false;
3034 prev_attributes[props.clientId] = props.attributes;
3035 <?php
3036 }else{
3037 ?>
3038 props.setAttributes({content: env});
3039 is_fetching = false;
3040 prev_attributes[props.clientId] = props.attributes;
3041 <?php
3042 }
3043 ?>
3044
3045 // if AUI is active call the js init function
3046 if (typeof aui_init === "function") {
3047 aui_init();
3048 }
3049 });
3050 }
3051
3052 return props.attributes.content;
3053 }
3054
3055 <?php
3056 if(!empty($this->options['block-edit-js'])) {
3057 echo $this->options['block-edit-js'] ; // strings have to be in single quotes, may cause issues
3058 }
3059
3060 if(empty($this->options['block-save-return'])){
3061 ?>
3062 ///////////////////////////////////////////////////////////////////////
3063
3064 // build the shortcode.
3065 shortcode = "[<?php echo $this->options['base_id'];?>";
3066 <?php
3067
3068 if(! empty( $this->arguments )){
3069
3070 foreach($this->arguments as $key => $args){
3071 // if($args['type']=='tabs'){continue;}
3072
3073 // don't add metadata arguments
3074 if (substr($key, 0, 9 ) === 'metadata_') {
3075 continue;
3076 }
3077 ?>
3078 if (props.attributes.hasOwnProperty("<?php echo esc_attr( $key );?>")) {
3079 if ('<?php echo esc_attr( $key );?>' == 'html') {
3080 } else if ('<?php echo esc_attr( $args['type'] );?>' == 'image_xy') {
3081 shortcode += props.attributes.<?php echo esc_attr( $key );?>.length && ( props.attributes.<?php echo esc_attr( $key );?>.x.length || props.attributes.<?php echo esc_attr( $key );?>.y.length ) ? " <?php echo esc_attr( $key );?>='{x:" + props.attributes.<?php echo esc_attr( $key );?>.x + ",y:"+props.attributes.<?php echo esc_attr( $key );?>.y +"}' " : "";
3082 } else {
3083 //shortcode += props.attributes.<?php echo esc_attr( $key );?>.length ? " <?php echo esc_attr( $key );?>='" + props.attributes.<?php echo esc_attr( $key );?>.toString().replace('\'','&#39;') + "' " : "";
3084 shortcode += " <?php echo esc_attr( $key );?>='" + props.attributes.<?php echo esc_attr( $key );?>.toString().replace('\'','&#39;') + "' ";
3085 }
3086 }
3087 <?php
3088 }
3089 }
3090
3091 ?>
3092 shortcode += "]";
3093
3094 if(shortcode){
3095
3096 // can cause a react exception when selecting multile blocks of the same type when the settings are not the same
3097 if (props.attributes.sd_shortcode !== shortcode) {
3098 props.setAttributes({ sd_shortcode: shortcode });
3099 }
3100
3101
3102 <?php
3103 if(!empty($this->options['nested-block']) || !empty($this->arguments['html']) ){
3104 echo "props.setAttributes({sd_shortcode_close: '[/".esc_attr( $this->options['base_id'] )."]'});";
3105 }
3106 ?>
3107 }
3108
3109
3110 ///////////////////////////////////////////////////////////////////////
3111 <?php
3112 } // end nested block check
3113 ?>
3114
3115 return [
3116
3117 el(wp.blockEditor.BlockControls, {key: 'controls'},
3118
3119 <?php if($show_alignment){?>
3120 el(
3121 wp.blockEditor.AlignmentToolbar,
3122 {
3123 value: props.attributes.alignment,
3124 onChange: function (alignment) {
3125 props.setAttributes({alignment: alignment})
3126 }
3127 }
3128 )
3129 <?php }?>
3130
3131 ),
3132
3133 el(wp.blockEditor.InspectorControls, {key: 'inspector'},
3134
3135 <?php
3136
3137 if(! empty( $this->arguments )){
3138
3139 if ( $show_advanced ) {
3140 ?>
3141 el('div', {
3142 style: {'padding-left': '16px','padding-right': '16px'}
3143 },
3144 el(
3145 wp.components.ToggleControl,
3146 {
3147 label: 'Show Advanced Settings?',
3148 checked: props.attributes.show_advanced,
3149 onChange: function (show_advanced) {
3150 props.setAttributes({show_advanced: !props.attributes.show_advanced})
3151 }
3152 }
3153 )
3154 )
3155 ,
3156 <?php
3157 }
3158
3159 $arguments = $this->group_arguments( $this->arguments );
3160 $block_group_tabs = ! empty( $this->options['block_group_tabs'] ) ? $this->group_block_tabs( $this->options['block_group_tabs'], $arguments ) : array();
3161
3162 // Do we have sections?
3163 $has_sections = $arguments == $this->arguments ? false : true;
3164
3165 if($has_sections){
3166 $panel_count = 0;
3167 $open_tab = '';
3168
3169 $open_tab_groups = array();
3170 $used_tabs = array();
3171
3172 foreach ( $arguments as $key => $args ) {
3173 $close_tab = false;
3174 $close_tabs = false;
3175
3176 if ( ! empty( $block_group_tabs ) ) {
3177 foreach ( $block_group_tabs as $tab_name => $tab_args ) {
3178 if ( in_array( $key, $tab_args['groups'] ) ) {
3179 $open_tab_groups[] = $key;
3180
3181 if ( $open_tab != $tab_name ) {
3182 $tab_args['tab']['tabs_open'] = $open_tab == '' ? true : false;
3183 $tab_args['tab']['open'] = true;
3184
3185 $this->block_tab_start( '', $tab_args );
3186 $open_tab = $tab_name;
3187 $used_tabs[] = $tab_name;
3188 }
3189
3190 if ( $open_tab_groups == $tab_args['groups'] ) {
3191 $close_tab = true;
3192 $open_tab_groups = array();
3193
3194 if ( $used_tabs == array_keys( $block_group_tabs ) ) {
3195 $close_tabs = true;
3196 }
3197 }
3198 }
3199 }
3200 }
3201 ?>
3202 el(wp.components.PanelBody, {
3203 title: '<?php esc_attr_e( $key ); ?>',
3204 initialOpen: <?php if ( $panel_count ) {
3205 echo "false";
3206 } else {
3207 echo "true";
3208 }?>
3209 },
3210 <?php
3211 foreach ( $args as $k => $a ) {
3212 $this->block_tab_start( $k, $a );
3213 $this->block_row_start( $k, $a );
3214 $this->build_block_arguments( $k, $a );
3215 $this->block_row_end( $k, $a );
3216 $this->block_tab_end( $k, $a );
3217 }
3218 ?>
3219 ),
3220 <?php
3221 $panel_count ++;
3222
3223 if($close_tab || $close_tabs){
3224 $tab_args = array(
3225 'tab' => array(
3226 'tabs_close' => $close_tabs,
3227 'close' => true,
3228 )
3229
3230 );
3231 $this->block_tab_end( '', $tab_args );
3232 // echo '###close'; print_r($tab_args);
3233 $panel_count = 0;
3234 }
3235 //
3236
3237 }
3238 }else {
3239 ?>
3240 el(wp.components.PanelBody, {
3241 title: '<?php esc_attr_e( "Settings", 'ayecode-connect' ); ?>',
3242 initialOpen: true
3243 },
3244 <?php
3245 foreach ( $this->arguments as $key => $args ) {
3246 $this->block_row_start( $key, $args );
3247 $this->build_block_arguments( $key, $args );
3248 $this->block_row_end( $key, $args );
3249 }
3250 ?>
3251 ),
3252 <?php
3253 }
3254
3255 }
3256 ?>
3257
3258 ),
3259
3260 <?php
3261 // If the user sets block-output array then build it
3262 if ( ! empty( $this->options['block-output'] ) ) {
3263 $this->block_element( $this->options['block-output'] );
3264 }elseif(!empty($this->options['block-edit-return'])){
3265 echo $this->options['block-edit-return'];
3266 }else{
3267 // if no block-output is set then we try and get the shortcode html output via ajax.
3268 $block_edit_wrap_tag = !empty($this->options['block_edit_wrap_tag']) ? esc_attr($this->options['block_edit_wrap_tag']) : 'div';
3269 ?>
3270 el('<?php echo esc_attr($block_edit_wrap_tag); ?>', wp.blockEditor.useBlockProps({
3271 dangerouslySetInnerHTML: {__html: onChangeContent()},
3272 className: props.className,
3273 <?php //if(isset($this->arguments['visibility_conditions'])){ echo 'dataVisibilityConditionSD: props.visibility_conditions ? true : false,';} //@todo we need to implement this in the other outputs also ?>
3274 style: {'minHeight': '30px'}
3275 }))
3276 <?php
3277 }
3278 ?>
3279 ]; // end return
3280
3281 <?php
3282 } // end block-edit-raw else
3283 ?>
3284 },
3285
3286 // The "save" property must be specified and must be a valid function.
3287 save: function (props) {
3288
3289 var attr = props.attributes;
3290 var align = '';
3291
3292 // build the shortcode.
3293 var content = "[<?php echo $this->options['base_id'];?>";
3294 $html = '';
3295 <?php
3296
3297 if(! empty( $this->arguments )){
3298
3299 foreach($this->arguments as $key => $args){
3300 // if($args['type']=='tabs'){continue;}
3301
3302 // don't add metadata arguments
3303 if (substr($key, 0, 9 ) === 'metadata_') {
3304 continue;
3305 }
3306 ?>
3307 if (attr.hasOwnProperty("<?php echo esc_attr( $key );?>")) {
3308 if ('<?php echo esc_attr( $key );?>' == 'html') {
3309 $html = attr.<?php echo esc_attr( $key );?>;
3310 } else if ('<?php echo esc_attr( $args['type'] );?>' == 'image_xy') {
3311 content += " <?php echo esc_attr( $key );?>='{x:" + attr.<?php echo esc_attr( $key );?>.x + ",y:"+attr.<?php echo esc_attr( $key );?>.y +"}' ";
3312 } else {
3313 content += " <?php echo esc_attr( $key );?>='" + attr.<?php echo esc_attr( $key );?>.toString().replace('\'','&#39;') + "' ";
3314 }
3315 }
3316 <?php
3317 }
3318 }
3319
3320 ?>
3321 content += "]";
3322 content = '';
3323
3324 <?php
3325 // if(!empty($this->options['nested-block'])){
3326 // ?>
3327 // $html = 'el( InnerBlocks.Content )';
3328 // <?php
3329 // }
3330 ?>
3331 // if has html element
3332 if ($html) {
3333 //content += $html + "[/<?php echo $this->options['base_id'];?>]";
3334 }
3335
3336 // @todo should we add inline style here or just css classes?
3337 if (attr.alignment) {
3338 if (attr.alignment == 'left') {
3339 align = 'alignleft';
3340 }
3341 if (attr.alignment == 'center') {
3342 align = 'aligncenter';
3343 }
3344 if (attr.alignment == 'right') {
3345 align = 'alignright';
3346 }
3347 }
3348
3349 <?php
3350 // if(!empty($this->options['nested-block'])){
3351 // ?x>
3352 // return el(
3353 // 'div',
3354 // { className: props.className,
3355 // style: {'minHeight': '300px','position':'relative','overflow':'hidden','backgroundImage': 'url(https://s.w.org/images/core/5.5/don-quixote-06.jpg)'}
3356 // },
3357 // el( InnerBlocks.Content ),
3358 // el('div', {dangerouslySetInnerHTML: {__html: content}, className: align})
3359 // );
3360 // <x?php
3361 // }else
3362
3363 if(!empty($this->options['block-output'])){
3364 // echo "return";
3365 // $this->block_element( $this->options['block-output'], true );
3366 // echo ";";
3367
3368 ?>
3369 return el(
3370 '',
3371 {},
3372 // el('', {dangerouslySetInnerHTML: {__html: content}}),
3373 <?php $this->block_element( $this->options['block-output'], true ); ?>
3374 // el('', {dangerouslySetInnerHTML: {__html: "[/<?php echo $this->options['base_id'];?>]"}})
3375 );
3376 <?php
3377
3378 }elseif(!empty($this->options['block-save-return'])){
3379 echo 'return ' . $this->options['block-save-return'];
3380 }elseif(!empty($this->options['nested-block'])){
3381 ?>
3382 return el(
3383 '',
3384 {},
3385 el('', {dangerouslySetInnerHTML: {__html: content+"\n"}}),
3386 InnerBlocks.Content ? el( InnerBlocks.Content ) : '', // @todo i think we need a comma here
3387 // el('', {dangerouslySetInnerHTML: {__html: "[/<?php echo $this->options['base_id'];?>]"}})
3388 );
3389 <?php
3390 }elseif(!empty( $this->options['block-save-return'] ) ){
3391 echo "return ". $this->options['block-edit-return'].";";
3392 }elseif(isset( $this->options['block-wrap'] ) && $this->options['block-wrap'] == ''){
3393 ?>
3394 return content;
3395 <?php
3396 }else{
3397 ?>
3398 var block_wrap = 'div';
3399 if (attr.hasOwnProperty("block_wrap")) {
3400 block_wrap = attr.block_wrap;
3401 }
3402 return el(block_wrap, wp.blockEditor.useBlockProps.save( {dangerouslySetInnerHTML: {__html: content}, className: align} ));
3403 <?php
3404 }
3405 ?>
3406
3407
3408 }
3409 });
3410 })(
3411 window.wp.blocks,
3412 window.wp.element,
3413 window.wp.blockEditor
3414 );
3415
3416 });
3417 </script>
3418 <?php
3419 $output = ob_get_clean();
3420
3421 /*
3422 * We only add the <script> tags for code highlighting, so we strip them from the output.
3423 */
3424
3425 return str_replace( array(
3426 '<script>',
3427 '</script>'
3428 ), '', $output );
3429 }
3430
3431
3432
3433 public function block_row_start($key, $args){
3434
3435 // check for row
3436 if(!empty($args['row'])){
3437
3438 if(!empty($args['row']['open'])){
3439
3440 // element require
3441 $element_require = ! empty( $args['element_require'] ) ? $this->block_props_replace( $args['element_require'], true ) . " && " : "";
3442 $device_type = ! empty( $args['device_type'] ) ? esc_attr($args['device_type']) : '';
3443 $device_type_require = ! empty( $args['device_type'] ) ? " deviceType == '" . esc_attr($device_type) . "' && " : '';
3444 $device_type_icon = '';
3445 if($device_type=='Desktop'){
3446 $device_type_icon = '<span class="dashicons dashicons-desktop" style="font-size: 18px;" onclick="sd_show_view_options(this);"></span>';
3447 }elseif($device_type=='Tablet'){
3448 $device_type_icon = '<span class="dashicons dashicons-tablet" style="font-size: 18px;" onclick="sd_show_view_options(this);"></span>';
3449 }elseif($device_type=='Mobile'){
3450 $device_type_icon = '<span class="dashicons dashicons-smartphone" style="font-size: 18px;" onclick="sd_show_view_options(this);"></span>';
3451 }
3452 echo $element_require;
3453 echo $device_type_require;
3454
3455 if(false){?><script><?php }?>
3456 el('div', {
3457 className: 'bsui components-base-control',
3458 },
3459 <?php if(!empty($args['row']['title'])){ ?>
3460 el('label', {
3461 className: 'components-base-control__label position-relative',
3462 style: {width:"100%"}
3463 },
3464 el('span',{dangerouslySetInnerHTML: {__html: '<?php echo addslashes( $args['row']['title'] ) ?>'}}),
3465 <?php if($device_type_icon){ ?>
3466 deviceType == '<?php echo $device_type;?>' && el('span',{dangerouslySetInnerHTML: {__html: '<?php echo $device_type_icon; ?>'},title: deviceType + ": Set preview mode to change",style: {right:"0",position:"absolute",color:"var(--wp-admin-theme-color)"}})
3467 <?php
3468 }
3469 ?>
3470
3471
3472 ),
3473 <?php }?>
3474 <?php if(!empty($args['row']['desc'])){ ?>
3475 el('p', {
3476 className: 'components-base-control__help mb-0',
3477 },
3478 '<?php echo addslashes( $args['row']['desc'] ); ?>'
3479 ),
3480 <?php }?>
3481 el(
3482 'div',
3483 {
3484 className: 'row mb-n2 <?php if(!empty($args['row']['class'])){ echo esc_attr($args['row']['class']);} ?>',
3485 },
3486 el(
3487 'div',
3488 {
3489 className: 'col pr-2 pe-2',
3490 },
3491
3492 <?php
3493 if(false){?></script><?php }
3494 }elseif(!empty($args['row']['close'])){
3495 if(false){?><script><?php }?>
3496 el(
3497 'div',
3498 {
3499 className: 'col pl-0 ps-0',
3500 },
3501 <?php
3502 if(false){?></script><?php }
3503 }else{
3504 if(false){?><script><?php }?>
3505 el(
3506 'div',
3507 {
3508 className: 'col pl-0 ps-0 pr-2 pe-2',
3509 },
3510 <?php
3511 if(false){?></script><?php }
3512 }
3513
3514 }
3515
3516 }
3517
3518 public function block_row_end($key, $args){
3519
3520 if(!empty($args['row'])){
3521 // maybe close
3522 if(!empty($args['row']['close'])){
3523 echo "))";
3524 }
3525
3526 echo "),";
3527 }
3528 }
3529
3530 public function block_tab_start($key, $args){
3531
3532 // check for row
3533 if(!empty($args['tab'])){
3534
3535 if(!empty($args['tab']['tabs_open'])){
3536
3537 if(false){?><script><?php }?>
3538
3539 el('div',{className: 'bsui'},
3540
3541 el('hr', {className: 'm-0'}), el(
3542 wp.components.TabPanel,
3543 {
3544 activeClass: 'is-active',
3545 className: 'btn-groupx',
3546 initialTabName: '<?php echo addslashes( esc_attr( $args['tab']['key']) ); ?>',
3547 tabs: [
3548
3549 <?php
3550 if(false){?></script><?php }
3551 }
3552
3553 if(!empty($args['tab']['open'])){
3554
3555 if(false){?><script><?php }?>
3556 {
3557 name: '<?php echo addslashes( esc_attr( $args['tab']['key']) ); ?>',
3558 title: el('div', {dangerouslySetInnerHTML: {__html: '<?php echo addslashes( esc_attr( $args['tab']['title']) ); ?>'}}),
3559 className: '<?php echo addslashes( esc_attr( $args['tab']['class']) ); ?>',
3560 content: el('div',{}, <?php if(!empty($args['tab']['desc'])){ ?>el('p', {
3561 className: 'components-base-control__help mb-0',
3562 dangerouslySetInnerHTML: {__html:'<?php echo addslashes( $args['tab']['desc'] ); ?>'}
3563 }),<?php }
3564 if(false){?></script><?php }
3565 }
3566
3567 }
3568
3569 }
3570
3571 public function block_tab_end($key, $args){
3572
3573 if(!empty($args['tab'])){
3574 // maybe close
3575 if(!empty($args['tab']['close'])){
3576 echo ")}, /* tab close */";
3577 }
3578
3579 if(!empty($args['tab']['tabs_close'])){
3580 if(false){?><script><?php }?>
3581 ]}, ( tab ) => {
3582 return tab.content;
3583 }
3584 )), /* tabs close */
3585 <?php if(false){ ?></script><?php }
3586 }
3587 }
3588 }
3589
3590 public function build_block_arguments( $key, $args ) {
3591 global $aui_bs5;
3592
3593 $custom_attributes = ! empty( $args['custom_attributes'] ) ? $this->array_to_attributes( $args['custom_attributes'] ) : '';
3594 $options = '';
3595 $extra = '';
3596 $require = '';
3597 $inside_elements = '';
3598 $after_elements = '';
3599
3600 // `content` is a protected and special argument
3601 if ( $key == 'content' ) {
3602 return;
3603 }
3604
3605 $device_type = ! empty( $args['device_type'] ) ? esc_attr($args['device_type']) : '';
3606 $device_type_require = ! empty( $args['device_type'] ) ? " deviceType == '" . esc_attr($device_type) . "' && " : '';
3607 $device_type_icon = '';
3608 if($device_type=='Desktop'){
3609 $device_type_icon = '<span class="dashicons dashicons-desktop" style="font-size: 18px;" onclick="sd_show_view_options(this);"></span>';
3610 }elseif($device_type=='Tablet'){
3611 $device_type_icon = '<span class="dashicons dashicons-tablet" style="font-size: 18px;" onclick="sd_show_view_options(this);"></span>';
3612 }elseif($device_type=='Mobile'){
3613 $device_type_icon = '<span class="dashicons dashicons-smartphone" style="font-size: 18px;" onclick="sd_show_view_options(this);"></span>';
3614 }
3615
3616 // icon
3617 $icon = '';
3618 if( !empty( $args['icon'] ) ){
3619 $icon .= "el('div', {";
3620 $icon .= "dangerouslySetInnerHTML: {__html: '".self::get_widget_icon( esc_attr($args['icon']))."'},";
3621 $icon .= "className: 'text-center',";
3622 $icon .= "title: '".addslashes( $args['title'] )."',";
3623 $icon .= "}),";
3624
3625 // blank title as its added to the icon.
3626 $args['title'] = '';
3627 }
3628
3629 // require advanced
3630 $require_advanced = ! empty( $args['advanced'] ) ? "props.attributes.show_advanced && " : "";
3631
3632 // element require
3633 $element_require = ! empty( $args['element_require'] ) ? $this->block_props_replace( $args['element_require'], true ) . " && " : "";
3634
3635
3636 $onchange = "props.setAttributes({ $key: $key } )";
3637 $onchangecomplete = "";
3638 $value = "props.attributes.$key";
3639 $text_type = array( 'text', 'password', 'number', 'email', 'tel', 'url', 'colorx','range' );
3640 if ( in_array( $args['type'], $text_type ) ) {
3641 $type = 'TextControl';
3642 // Save numbers as numbers and not strings
3643 if ( $args['type'] == 'number' ) {
3644 $onchange = "props.setAttributes({ $key: $key ? Number($key) : '' } )";
3645 }
3646
3647 if (substr($key, 0, 9 ) === 'metadata_') {
3648 $real_key = str_replace('metadata_','', $key );
3649 $onchange = "props.setAttributes({ metadata: { $real_key: $key } } )";
3650 $value = "props.attributes.metadata && props.attributes.metadata.$real_key ? props.attributes.metadata.$real_key : ''";
3651 }
3652 }
3653 // else if ( $args['type'] == 'popup' ) {
3654 // $type = 'TextControl';
3655 // $args['type'] == 'text';
3656 // $after_elements .= "el( wp.components.Button, {
3657 // className: 'components-button components-circular-option-picker__clear is-primary is-smallx',
3658 // onClick: function(){
3659 // aui_modal('','<input id=\'zzz\' value= />');
3660 // const source = document.getElementById('zzz');
3661 // source.value = props.attributes.$key;
3662 // source.addEventListener('input', function(e){props.setAttributes({ $key: e.target.value });});
3663 // }
3664 // },
3665 // 'test'
3666 // ),";
3667 //
3668 // $value = "props.attributes.$key ? props.attributes.$key : ''";
3669 // }
3670 else if ( $args['type'] == 'styleid' ) {
3671 $type = 'TextControl';
3672 $args['type'] == 'text';
3673 // Save numbers as numbers and not strings
3674 $value = "props.attributes.$key ? props.attributes.$key : ''";
3675 }else if ( $args['type'] == 'notice' ) {
3676
3677 $notice_message = !empty($args['desc']) ? addslashes($args['desc']) : '';
3678 $notice_status = !empty($args['status']) ? esc_attr($args['status']) : 'info';
3679
3680 $notice = "el('div',{className:'bsui'},el(wp.components.Notice, {status: '$notice_status',isDismissible: false,className: 'm-0 pr-0 pe-0 mb-3'},el('div',{dangerouslySetInnerHTML: {__html: '$notice_message'}}))),";
3681 echo $notice_message ? $element_require . $notice : '';
3682 return;
3683 }
3684 /*
3685 * https://www.wptricks.com/question/set-current-tab-on-a-gutenberg-tabpanel-component-from-outside-that-component/ es5 layout
3686 elseif($args['type']=='tabs'){
3687 ?>
3688 el(
3689 wp.components.TabPanel,
3690 {
3691 activeClass: 'active-tab',
3692 initialTabName: deviceType,
3693 tabs: [
3694 {
3695 name: 'Desktop',
3696 title: el('div', {dangerouslySetInnerHTML: {__html: '<i class="fas fa-desktop"></i>'}}),
3697 className: 'tab-one' + deviceType == 'Desktop' ? ' active-tab' : '',
3698 content: el('div', {dangerouslySetInnerHTML: {__html: 'ddd'}})
3699 },
3700 {
3701 name: 'Tablet',
3702 title: el('div', {dangerouslySetInnerHTML: {__html: '<i class="fas fa-tablet-alt"></i>'}}),
3703 className: 'tab-two' + deviceType == 'Tablet' ? ' active-tab' : '',
3704 content: el('div', {dangerouslySetInnerHTML: {__html: 'ttt'}})
3705 },
3706 {
3707 name: 'Mobile',
3708 title: el('div', {dangerouslySetInnerHTML: {__html: '<i class="fas fa-mobile-alt"></i>'}}),
3709 className: 'tab-two' + deviceType == 'Mobile' ? ' active-tab' : '',
3710 content: el('div', {dangerouslySetInnerHTML: {__html: 'mmm'}})
3711 },
3712 ],
3713 },
3714 ( tab ) => {
3715
3716 // @todo https://github.com/WordPress/gutenberg/issues/39248
3717 if(tab.name=='Desktop'){
3718 wp.data.dispatch('core/edit-post').__experimentalSetPreviewDeviceType('Desktop');
3719 wp.data.select('core/edit-post').__experimentalGetPreviewDeviceType();
3720 }else if(tab.name=='Tablet'){
3721 wp.data.dispatch('core/edit-post').__experimentalSetPreviewDeviceType('Tablet');
3722 wp.data.select('core/edit-post').__experimentalGetPreviewDeviceType();
3723 }else if(tab.name=='Mobile'){
3724 wp.data.dispatch('core/edit-post').__experimentalSetPreviewDeviceType('Mobile');
3725 wp.data.select('core/edit-post').__experimentalGetPreviewDeviceType();
3726 }
3727
3728 return tab.content;
3729
3730 }
3731 ),
3732
3733 <?php
3734 return;
3735 }
3736 */
3737 elseif ( $args['type'] == 'color' ) {
3738 $type = 'ColorPicker';
3739 $onchange = "";
3740 $extra = "color: $value,";
3741 if(!empty($args['disable_alpha'])){
3742 $extra .= "disableAlpha: true,";
3743 }
3744 $onchangecomplete = "onChangeComplete: function($key) {
3745 value = $key.rgb.a && $key.rgb.a < 1 ? \"rgba(\"+$key.rgb.r+\",\"+$key.rgb.g+\",\"+$key.rgb.b+\",\"+$key.rgb.a+\")\" : $key.hex;
3746 props.setAttributes({
3747 $key: value
3748 });
3749 },";
3750 }elseif ( $args['type'] == 'gradient' ) {
3751 $type = 'GradientPicker';
3752 $extra .= "gradients: [{
3753 name: 'Vivid cyan blue to vivid purple',
3754 gradient:
3755 'linear-gradient(135deg,rgba(6,147,227,1) 0%,rgb(155,81,224) 100%)',
3756 slug: 'vivid-cyan-blue-to-vivid-purple',
3757 },
3758 {
3759 name: 'Light green cyan to vivid green cyan',
3760 gradient:
3761 'linear-gradient(135deg,rgb(122,220,180) 0%,rgb(0,208,130) 100%)',
3762 slug: 'light-green-cyan-to-vivid-green-cyan',
3763 },
3764 {
3765 name: 'Luminous vivid amber to luminous vivid orange',
3766 gradient:
3767 'linear-gradient(135deg,rgba(252,185,0,1) 0%,rgba(255,105,0,1) 100%)',
3768 slug: 'luminous-vivid-amber-to-luminous-vivid-orange',
3769 },
3770 {
3771 name: 'Luminous vivid orange to vivid red',
3772 gradient:
3773 'linear-gradient(135deg,rgba(255,105,0,1) 0%,rgb(207,46,46) 100%)',
3774 slug: 'luminous-vivid-orange-to-vivid-red',
3775 },
3776 {
3777 name: 'Very light gray to cyan bluish gray',
3778 gradient:
3779 'linear-gradient(135deg,rgb(238,238,238) 0%,rgb(169,184,195) 100%)',
3780 slug: 'very-light-gray-to-cyan-bluish-gray',
3781 },
3782 {
3783 name: 'Cool to warm spectrum',
3784 gradient:
3785 'linear-gradient(135deg,rgb(74,234,220) 0%,rgb(151,120,209) 20%,rgb(207,42,186) 40%,rgb(238,44,130) 60%,rgb(251,105,98) 80%,rgb(254,248,76) 100%)',
3786 slug: 'cool-to-warm-spectrum',
3787 }],";
3788
3789 }elseif ( $args['type'] == 'image' ) {
3790 // print_r($args);
3791
3792 $img_preview = isset($args['focalpoint']) && !$args['focalpoint'] ? " props.attributes.$key && el('img', { src: props.attributes.$key,style: {maxWidth:'100%',background: '#ccc'}})," : " ( props.attributes.$key || props.attributes.{$key}_use_featured ) && el(wp.components.FocalPointPicker,{
3793 url: props.attributes.{$key}_use_featured === true ? 'data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0idXRmLTgiID8+CjxzdmcgYmFzZVByb2ZpbGU9InRpbnkiIGhlaWdodD0iNDAwIiB2ZXJzaW9uPSIxLjIiIHdpZHRoPSI0MDAiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgeG1sbnM6ZXY9Imh0dHA6Ly93d3cudzMub3JnLzIwMDEveG1sLWV2ZW50cyIgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiPjxkZWZzIC8+PHJlY3QgZmlsbD0iI2QzZDNkMyIgaGVpZ2h0PSI0MDAiIHdpZHRoPSI0MDAiIHg9IjAiIHk9IjAiIC8+PGxpbmUgc3Ryb2tlPSJ3aGl0ZSIgc3Ryb2tlLXdpZHRoPSIxMCIgeDE9IjAiIHgyPSI0MDAiIHkxPSIwIiB5Mj0iNDAwIiAvPjxsaW5lIHN0cm9rZT0id2hpdGUiIHN0cm9rZS13aWR0aD0iMTAiIHgxPSIwIiB4Mj0iNDAwIiB5MT0iNDAwIiB5Mj0iMCIgLz48cmVjdCBmaWxsPSIjZDNkM2QzIiBoZWlnaHQ9IjUwIiB3aWR0aD0iMjE4LjAiIHg9IjkxLjAiIHk9IjE3NS4wIiAvPjx0ZXh0IGZpbGw9IndoaXRlIiBmb250LXNpemU9IjMwIiBmb250LXdlaWdodD0iYm9sZCIgdGV4dC1hbmNob3I9Im1pZGRsZSIgeD0iMjAwLjAiIHk9IjIwNy41Ij5QTEFDRUhPTERFUjwvdGV4dD48L3N2Zz4=' : props.attributes.$key,
3794 value: props.attributes.{$key}_xy.x !== undefined && props.attributes.{$key}_xy.x >= 0 ? props.attributes.{$key}_xy : {x: 0.5,y: 0.5,},
3795 // value: props.attributes.{$key}_xy,
3796 onChange: function(focalPoint){
3797 console.log(props.attributes);
3798 return props.setAttributes({
3799 {$key}_xy: focalPoint
3800 });
3801 },
3802 // @todo for some reason this does not work as expected.
3803 // onDrag: function(focalPointTemp){
3804 // return props.setAttributes({
3805 // {$key}_xy: focalPointTemp
3806 // });
3807 // }
3808
3809
3810 }), ";
3811
3812
3813 $value = '""';
3814 $type = 'MediaUpload';
3815 $extra .= "onSelect: function(media){
3816 return props.setAttributes({
3817 $key: media.url,
3818 {$key}_id: media.id
3819 });
3820 },";
3821 $extra .= "type: 'image',";
3822 $extra .= "render: function (obj) {
3823 return el( 'div',{},
3824 ( !props.attributes.$key && !props.attributes.{$key}_use_featured ) && el( wp.components.Button, {
3825 className: 'components-button components-circular-option-picker__clear is-primary is-smallx',
3826 onClick: obj.open
3827 },
3828 'Upload Image'
3829 ),
3830 $img_preview
3831 props.attributes.$key && el( wp.components.Button, {
3832 className: 'components-button components-circular-option-picker__clear is-secondary is-small',
3833 style: {margin:'8px 0',display: 'block'},
3834 onClick: function(){
3835 return props.setAttributes({
3836 $key: '',
3837 {$key}_id: ''
3838 });
3839 }
3840 },
3841 props.attributes.$key? 'Clear' : ''
3842 )
3843 )
3844
3845
3846
3847 }";
3848 $onchange = "";
3849
3850 //$inside_elements = ",el('div',{},'file upload')";
3851 } else if ( $args['type'] == 'images' ) {
3852 $img_preview = "props.attributes.$key && (function() {
3853 let uploads = JSON.parse('['+props.attributes.$key+']');
3854 let images = [];
3855 uploads.map((upload, index) => (
3856 images.push( el('div',{ className: 'col p-2', draggable: 'true', 'data-index': index },
3857 el('img', {
3858 src: (upload.sizes && upload.sizes.thumbnail ? upload.sizes.thumbnail.url : upload.url),
3859 style: { maxWidth:'100%', background: '#ccc', pointerEvents:'none' }
3860 }),
3861 el('i',{
3862 className: 'fas fa-times-circle text-danger position-absolute ml-n2 mt-n1 bg-white rounded-circle c-pointer',
3863 onClick: function() {
3864 aui_confirm('".esc_attr__('Are you sure?')."', '".esc_attr__('Delete')."', '".esc_attr__('Cancel')."', true).then(function(confirmed) {
3865 if (confirmed) {
3866 let new_uploads = JSON.parse('['+props.attributes.$key+']');
3867 new_uploads.splice(index, 1);
3868 return props.setAttributes({ {$key}: JSON.stringify( new_uploads ).replace('[','').replace(']','') });
3869 }
3870 });
3871 }},
3872 '')
3873 ))
3874 ));
3875 return images;
3876 })(),";
3877
3878
3879 $value = '""';
3880 $type = 'MediaUpload';
3881 $extra .= "onSelect: function(media){
3882 let slim_images = props.attributes.$key ? JSON.parse('['+props.attributes.$key+']') : [];
3883 if(media.length){
3884 for (var i=0; i < media.length; i++) {
3885 slim_images.push({id: media[i].id, caption: media[i].caption, description: media[i].description,title: media[i].title,alt: media[i].alt,sizes: media[i].sizes, url: media[i].url});
3886 }
3887 }
3888 var slimImagesV = JSON.stringify(slim_images);
3889 if (slimImagesV) {
3890 slimImagesV = slimImagesV.replace('[','').replace(']','').replace(/'/g, '&#39;');
3891 }
3892 return props.setAttributes({ $key: slimImagesV});
3893 },";
3894 $extra .= "type: 'image',";
3895 $extra .= "multiple: true,";
3896 $extra .= "render: function (obj) {
3897 /* Init the sort */
3898 enableDragSort('sd-sortable');
3899 return el( 'div',{},
3900 el( wp.components.Button, {
3901 className: 'components-button components-circular-option-picker__clear is-primary is-smallx',
3902 onClick: obj.open
3903 },
3904 'Upload Images'
3905 ),
3906 el('div',{
3907 className: 'row row-cols-3 px-2 sd-sortable',
3908 'data-field':'$key'
3909 },
3910 $img_preview
3911 ),
3912 props.attributes.$key && el( wp.components.Button, {
3913 className: 'components-button components-circular-option-picker__clear is-secondary is-small',
3914 style: {margin:'8px 0'},
3915 onClick: function(){
3916 return props.setAttributes({ $key: '' });
3917 }
3918 },
3919 props.attributes.$key ? 'Clear All' : ''
3920 )
3921 )
3922 }";
3923 $onchange = "";
3924
3925 //$inside_elements = ",el('div',{},'file upload')";
3926 }
3927 elseif ( $args['type'] == 'checkbox' ) {
3928 $type = 'CheckboxControl';
3929 $extra .= "checked: props.attributes.$key,";
3930 $onchange = "props.setAttributes({ $key: ! props.attributes.$key } )";
3931 } elseif ( $args['type'] == 'textarea' ) {
3932 $type = 'TextareaControl';
3933
3934 } elseif ( $args['type'] == 'select' || $args['type'] == 'multiselect' ) {
3935 $type = 'SelectControl';
3936
3937 if($args['name'] == 'category' && !empty($args['post_type_linked'])){
3938 $options .= "options: taxonomies_".str_replace("-","_", $this->id).",";
3939 }elseif($args['name'] == 'sort_by' && !empty($args['post_type_linked'])){
3940 $options .= "options: sort_by_".str_replace("-","_", $this->id).",";
3941 }else {
3942
3943 if ( ! empty( $args['options'] ) ) {
3944 $options .= "options: [";
3945 foreach ( $args['options'] as $option_val => $option_label ) {
3946 $options .= "{ value: '" . esc_attr( $option_val ) . "', label: '" . esc_js( addslashes( $option_label ) ) . "' },";
3947 }
3948 $options .= "],";
3949 }
3950 }
3951 if ( isset( $args['multiple'] ) && $args['multiple'] ) { //@todo multiselect does not work at the moment: https://github.com/WordPress/gutenberg/issues/5550
3952 $extra .= ' multiple:true,style:{height:"auto",paddingRight:"8px","overflow-y":"auto"}, ';
3953 }
3954
3955 if($args['type'] == 'multiselect' || ( isset( $args['multiple'] ) && $args['multiple'] ) ){
3956 $after_elements .= "props.attributes.$key && el( wp.components.Button, {
3957 className: 'components-button components-circular-option-picker__clear is-secondary is-small',
3958 style: {margin:'-8px 0 8px 0',display: 'block'},
3959 onClick: function(){
3960 return props.setAttributes({
3961 $key: '',
3962 });
3963 }
3964 },
3965 'Clear'
3966 ),";
3967 }
3968 } elseif ( $args['type'] == 'tagselect' ) {
3969 // $type = 'FormTokenField';
3970 //
3971 // if ( ! empty( $args['options'] ) ) {
3972 // $options .= "suggestions: [";
3973 // foreach ( $args['options'] as $option_val => $option_label ) {
3974 // $options .= "{ value: '" . esc_attr( $option_val ) . "', title: '" . addslashes( $option_label ) . "' },";
3975 //// $options .= "'" . esc_attr( $option_val ) . "':'" . addslashes( $option_label ) . "',";
3976 // }
3977 // $options .= "],";
3978 // }
3979 //
3980 // $onchangex = "{ ( selectedItems ) => {
3981 // // Build array of selected posts.
3982 // let selectedPostsArray = [];
3983 // selectedPosts.map(
3984 // ( postName ) => {
3985 // const matchingPost = posts.find( ( post ) => {
3986 // return post.title.raw === postName;
3987 //
3988 // } );
3989 // if ( matchingPost !== undefined ) {
3990 // selectedPostsArray.push( matchingPost.id );
3991 // }
3992 // }
3993 // )
3994 //
3995 // setAttributes( { selectedPosts: selectedPostsArray } );
3996 // } } ";
3997 // $onchange = '';// "props.setAttributes({ $key: [ props.attributes.$key ] } )";
3998 //
3999 //// $options = "";
4000 // $value = "[]";
4001 // $extra .= ' __experimentalExpandOnFocus: true,';
4002
4003 } else if ( $args['type'] == 'alignment' ) {
4004 $type = 'AlignmentToolbar'; // @todo this does not seem to work but cant find a example
4005 } else if ( $args['type'] == 'margins' ) {
4006
4007 } else if ( $args['type'] == 'visibility_conditions' && $this->supports_block_visibility() ) {
4008 $type = 'TextControl';
4009 $value = "(props.attributes.$key ? props.attributes.$key : '')";
4010 $args['type'] = 'text';
4011 $options .= 'disabled:true,';
4012 $bsvc_title = esc_attr( addslashes( $args['title'] ) );
4013 $bsvc_body = $this->block_visibility_fields( $args );
4014 // @TODO reset button
4015 $bsvc_footer = '<button type="button" class="btn btn-danger d-none">' . __( 'Reset', 'ayecode-connect' ) . '</button>' . ( $aui_bs5 ? '<button type="button" class="btn btn-secondary bs-vc-close text-white" data-bs-dismiss="modal">' . __( 'Close', 'ayecode-connect' ) . '</button>' : '<button type="button" class="close btn btn-secondary bs-vc-close text-white" data-dismiss="modal" aria-label="' . esc_attr__( 'Close', 'ayecode-connect' ) . '"><span aria-hidden="true">&times;</span></button>' ) . '<button type="button" class="btn btn-primary bs-vc-save">' . __( 'Save Rules', 'ayecode-connect' ) . '</button>';
4016 $after_elements .= "el('div', {className: 'components-base-control bs-vc-button-wrap'}, el(wp.components.Button, {
4017 className: 'components-button components-circular-option-picker__clear is-primary is-smallx',
4018 onClick: function() {
4019 var sValue = props.attributes." . $key . ";
4020 var oValue;
4021 try {oValue = JSON.parse(sValue);} catch(err) {}
4022 jQuery(document).off('show.bs.modal', '.bs-vc-modal').on('show.bs.modal', '.bs-vc-modal', function (e) {
4023 if (e.target && jQuery(e.target).hasClass('bs-vc-modal')) {
4024 sd_block_visibility_render_fields(oValue);
4025 if (!jQuery('.bs-vc-modal-form .bs-vc-rule-sets .bs-vc-rule').length) {
4026 jQuery('.bs-vc-modal-form .bs-vc-add-rule').trigger('click');
4027 }
4028 if(typeof aui_init_select2 == 'function') {
4029 aui_init_select2();
4030 }
4031 jQuery('.bs-vc-modal-form').trigger('change');
4032 }
4033 });
4034 aui_modal('" . $bsvc_title . "', '" . addslashes( $bsvc_body ) . "', '" . $bsvc_footer . "', true, 'bs-vc-modal', 'modal-lg', '');
4035 jQuery(document).off('change', '#bsvc_raw_value').on('change', '#bsvc_raw_value', function(e) {
4036 props.setAttributes({" . $key . ": e.target.value});
4037 });
4038 }
4039 },
4040 '" . addslashes( ! empty( $args['button_title'] ) ? $args['button_title'] : $args['title'] ) . "'
4041 ) ),";
4042 } else {
4043 return;// if we have not implemented the control then don't break the JS.
4044 }
4045
4046 // color input does not show the labels so we add them
4047 if($args['type']=='color'){
4048 // add show only if advanced
4049 echo $require_advanced;
4050 // add setting require if defined
4051 echo $element_require;
4052 echo "el('div', {style: {'marginBottom': '8px'}}, '".addslashes( $args['title'] )."'),";
4053 }
4054
4055 // add show only if advanced
4056 echo $require_advanced;
4057 // add setting require if defined
4058 echo $element_require;
4059 echo $device_type_require;
4060
4061 // icon
4062 echo $icon;
4063 ?>
4064 el( <?php echo $args['type'] == 'image' || $args['type'] == 'images' ? $type : "wp.components.".$type; ?>, {
4065 label: <?php if ( empty( $args['title'] ) ) { echo "''"; } else if ( empty( $args['row'] ) && ! empty( $args['device_type'] ) ) { ?>el('label',{className:'components-base-control__label',style:{width:"100%"}},el('span',{dangerouslySetInnerHTML: {__html: '<?php echo addslashes( $args['title'] ) ?>'}}),<?php if ( $device_type_icon ) { ?>deviceType == '<?php echo $device_type;?>' && el('span',{dangerouslySetInnerHTML: {__html: '<?php echo $device_type_icon; ?>'},title: deviceType + ": Set preview mode to change",style: {right:"0",position:"absolute",color:"var(--wp-admin-theme-color)"}})<?php } ?>)<?php
4066 } else { ?>'<?php echo addslashes( trim( esc_html( $args['title'] ) ) ); ?>'<?php } ?>,
4067 help: <?php echo ( isset( $args['desc'] ) ? "el('span', {dangerouslySetInnerHTML: {__html: '" . trim( wp_kses_post( addslashes( $args['desc'] ) ) ) . "'}})" : "''" ); ?>,
4068 value: <?php echo $value; ?>,
4069 <?php if ( $type == 'TextControl' && $args['type'] != 'text' ) {
4070 echo "type: '" . addslashes( $args['type'] ) . "',";
4071 } ?>
4072 <?php if ( ! empty( $args['placeholder'] ) ) {
4073 echo "placeholder: '" . esc_js( addslashes( trim( esc_html( $args['placeholder'] ) ) ) ) . "',";
4074 } ?>
4075 <?php echo $options; ?>
4076 <?php echo $extra; ?>
4077 <?php echo $custom_attributes; ?>
4078 <?php echo $onchangecomplete; ?>
4079 <?php if ( $onchange ) { ?>
4080 onChange: function ( <?php echo $key; ?> ) {
4081 <?php echo $onchange; ?>
4082 }
4083 <?php } ?>
4084 } <?php echo $inside_elements; ?> ),
4085 <?php
4086 echo $after_elements;
4087 }
4088
4089 /**
4090 * Convert an array of attributes to block string.
4091 *
4092 * @param $custom_attributes
4093 *
4094 * @return string
4095 *@todo there is prob a faster way to do this, also we could add some validation here.
4096 *
4097 */
4098 public function array_to_attributes( $custom_attributes, $html = false ) {
4099 $attributes = '';
4100 if ( ! empty( $custom_attributes ) ) {
4101
4102 foreach ( $custom_attributes as $key => $val ) {
4103 if(is_array($val)){
4104 $attributes .= $key.': {'.$this->array_to_attributes( $val, $html ).'},';
4105 }else{
4106 $attributes .= $html ? " $key='$val' " : "'$key': '$val',";
4107 }
4108 }
4109
4110 }
4111
4112 return $attributes;
4113 }
4114
4115
4116
4117 /**
4118 * A self looping function to create the output for JS block elements.
4119 *
4120 * This is what is output in the WP Editor visual view.
4121 *
4122 * @param $args
4123 */
4124 public function block_element( $args, $save = false ) {
4125
4126 // print_r($args);echo '###';exit;
4127
4128 if ( ! empty( $args ) ) {
4129 foreach ( $args as $element => $new_args ) {
4130
4131 if ( is_array( $new_args ) ) { // its an element
4132
4133
4134 if ( isset( $new_args['element'] ) ) {
4135
4136 if ( isset( $new_args['element_require'] ) ) {
4137 echo str_replace( array(
4138 "'+",
4139 "+'"
4140 ), '', $this->block_props_replace( $new_args['element_require'] ) ) . " && ";
4141 unset( $new_args['element_require'] );
4142 }
4143
4144 if($new_args['element']=='InnerBlocks'){
4145 echo "\n el( InnerBlocks, {";
4146 }elseif($new_args['element']=='innerBlocksProps'){
4147 $element = isset($new_args['inner_element']) ? esc_attr($new_args['inner_element']) : 'div';
4148 // echo "\n el( 'section', wp.blockEditor.useInnerBlocksProps( blockProps, {";
4149 // echo $save ? "\n el( '$element', wp.blockEditor.useInnerBlocksProps.save( " : "\n el( '$element', wp.blockEditor.useInnerBlocksProps( ";
4150 echo $save ? "\n el( '$element', wp.blockEditor.useInnerBlocksProps.save( " : "\n el( '$element', wp.blockEditor.useInnerBlocksProps( ";
4151 echo $save ? "wp.blockEditor.useBlockProps.save( {" : "wp.blockEditor.useBlockProps( {";
4152 echo !empty($new_args['blockProps']) ? $this->block_element( $new_args['blockProps'],$save ) : '';
4153
4154 echo "} ), {";
4155 echo !empty($new_args['innerBlocksProps']) && !$save ? $this->block_element( $new_args['innerBlocksProps'],$save ) : '';
4156 // echo '###';
4157
4158 // echo '###';
4159 }elseif($new_args['element']=='BlocksProps'){
4160
4161 if ( isset($new_args['if_inner_element']) ) {
4162 $element = $new_args['if_inner_element'];
4163 }else {
4164 $element = isset($new_args['inner_element']) ? "'".esc_attr($new_args['inner_element'])."'" : "'div'";
4165 }
4166
4167 unset($new_args['inner_element']);
4168 echo $save ? "\n el( $element, wp.blockEditor.useBlockProps.save( {" : "\n el( $element, wp.blockEditor.useBlockProps( {";
4169 echo !empty($new_args['blockProps']) ? $this->block_element( $new_args['blockProps'],$save ) : '';
4170
4171
4172 // echo "} ),";
4173
4174 }else{
4175 echo "\n el( '" . $new_args['element'] . "', {";
4176 }
4177
4178
4179 // get the attributes
4180 foreach ( $new_args as $new_key => $new_value ) {
4181
4182
4183 if ( $new_key == 'element' || $new_key == 'content'|| $new_key == 'if_content' || $new_key == 'element_require' || $new_key == 'element_repeat' || is_array( $new_value ) ) {
4184 // do nothing
4185 } else {
4186 echo $this->block_element( array( $new_key => $new_value ),$save );
4187 }
4188 }
4189
4190 echo $new_args['element']=='BlocksProps' ? '} ),' : "},";// end attributes
4191
4192 // get the content
4193 $first_item = 0;
4194 foreach ( $new_args as $new_key => $new_value ) {
4195 if ( $new_key === 'content' || $new_key === 'if_content' || is_array( $new_value ) ) {
4196
4197 if ( $new_key === 'content' ) {
4198 echo "'" . $this->block_props_replace( wp_slash( $new_value ) ) . "'";
4199 }else if ( $new_key === 'if_content' ) {
4200 echo $this->block_props_replace( $new_value );
4201 }
4202
4203 if ( is_array( $new_value ) ) {
4204
4205 if ( isset( $new_value['element_require'] ) ) {
4206 echo str_replace( array(
4207 "'+",
4208 "+'"
4209 ), '', $this->block_props_replace( $new_value['element_require'] ) ) . " && ";
4210 unset( $new_value['element_require'] );
4211 }
4212
4213 if ( isset( $new_value['element_repeat'] ) ) {
4214 $x = 1;
4215 while ( $x <= absint( $new_value['element_repeat'] ) ) {
4216 $this->block_element( array( '' => $new_value ),$save );
4217 $x ++;
4218 }
4219 } else {
4220 $this->block_element( array( '' => $new_value ),$save );
4221 }
4222 }
4223 $first_item ++;
4224 }
4225 }
4226
4227 if($new_args['element']=='innerBlocksProps' || $new_args['element']=='xBlocksProps'){
4228 echo "))";// end content
4229 }else{
4230 echo ")";// end content
4231 }
4232
4233
4234 echo ", \n";
4235
4236 }
4237 } else {
4238
4239 if ( substr( $element, 0, 3 ) === "if_" ) {
4240 $extra = '';
4241 if( strpos($new_args, '[%WrapClass%]') !== false ){
4242 $new_args = str_replace('[%WrapClass%]"','" + sd_build_aui_class(props.attributes)',$new_args);
4243 $new_args = str_replace('[%WrapClass%]','+ sd_build_aui_class(props.attributes)',$new_args);
4244 }
4245 echo str_replace( "if_", "", $element ) . ": " . $this->block_props_replace( $new_args, true ) . ",";
4246 } elseif ( $element == 'style' && strpos($new_args, '[%WrapStyle%]') !== false ) {
4247 $new_args = str_replace('[%WrapStyle%]','',$new_args);
4248 echo $element . ": {..." . $this->block_props_replace( $new_args ) . " , ...sd_build_aui_styles(props.attributes) },";
4249 // echo $element . ": " . $this->block_props_replace( $new_args ) . ",";
4250 } elseif ( $element == 'style' ) {
4251 echo $element . ": " . $this->block_props_replace( $new_args ) . ",";
4252 } elseif ( ( $element == 'class' || $element == 'className' ) && strpos($new_args, '[%WrapClass%]') !== false ) {
4253 $new_args = str_replace('[%WrapClass%]','',$new_args);
4254 echo $element . ": '" . $this->block_props_replace( $new_args ) . "' + sd_build_aui_class(props.attributes),";
4255 } elseif ( $element == 'template' && $new_args ) {
4256 echo $element . ": $new_args,";
4257 } else {
4258 echo $element . ": '" . $this->block_props_replace( $new_args ) . "',";
4259 }
4260
4261 }
4262 }
4263 }
4264 }
4265
4266 /**
4267 * Replace block attributes placeholders with the proper naming.
4268 *
4269 * @param $string
4270 *
4271 * @return mixed
4272 */
4273 public function block_props_replace( $string, $no_wrap = false ) {
4274 if ( $no_wrap ) {
4275 $string = str_replace( array( "[%", "%]", "%:checked]" ), array( "props.attributes.", "", "" ), $string );
4276 } else {
4277 $string = str_replace( array( "![%", "[%", "%]", "%:checked]" ), array( "'+!props.attributes.", "'+props.attributes.", "+'", "+'" ), $string );
4278 }
4279
4280 return $string;
4281 }
4282
4283 /**
4284 * Outputs the content of the widget
4285 *
4286 * @param array $args
4287 * @param array $instance
4288 */
4289 public function widget( $args, $instance ) {
4290 if ( ! is_array( $args ) ) {
4291 $args = array();
4292 }
4293
4294 // Get the filtered values
4295 $argument_values = $this->argument_values( $instance );
4296 $argument_values = $this->string_to_bool( $argument_values );
4297 $output = $this->output( $argument_values, $args );
4298
4299 $no_wrap = false;
4300 if ( isset( $argument_values['no_wrap'] ) && $argument_values['no_wrap'] ) {
4301 $no_wrap = true;
4302 }
4303
4304 ob_start();
4305 if ( $output && ! $no_wrap ) {
4306
4307 $class_original = $this->options['widget_ops']['classname'];
4308 $class = $this->options['widget_ops']['classname']." sdel-".$this->get_instance_hash();
4309
4310 // Before widget
4311 $before_widget = ! empty( $args['before_widget'] ) ? $args['before_widget'] : '';
4312 $before_widget = $before_widget ? str_replace( $class_original, $class, $before_widget ) : $before_widget;
4313 $before_widget = apply_filters( 'wp_super_duper_before_widget', $before_widget, $args, $instance, $this );
4314 $before_widget = apply_filters( 'wp_super_duper_before_widget_' . $this->base_id, $before_widget, $args, $instance, $this );
4315
4316 // After widget
4317 $after_widget = ! empty( $args['after_widget'] ) ? $args['after_widget'] : '';
4318 $after_widget = apply_filters( 'wp_super_duper_after_widget', $after_widget, $args, $instance, $this );
4319 $after_widget = apply_filters( 'wp_super_duper_after_widget_' . $this->base_id, $after_widget, $args, $instance, $this );
4320
4321 echo $before_widget;
4322 // elementor strips the widget wrapping div so we check for and add it back if needed
4323 if ( $this->is_elementor_widget_output() ) {
4324 // Filter class & attrs for elementor widget output.
4325 $class = apply_filters( 'wp_super_duper_div_classname', $class, $args, $this );
4326 $class = apply_filters( 'wp_super_duper_div_classname_' . $this->base_id, $class, $args, $this );
4327
4328 $attrs = apply_filters( 'wp_super_duper_div_attrs', '', $args, $this );
4329 $attrs = apply_filters( 'wp_super_duper_div_attrs_' . $this->base_id, '', $args, $this );
4330
4331 echo "<span class='" . esc_attr( $class ) . "' " . $attrs . ">";
4332 }
4333 echo $this->output_title( $args, $instance );
4334 echo $output;
4335 if ( $this->is_elementor_widget_output() ) {
4336 echo "</span>";
4337 }
4338 echo $after_widget;
4339 } elseif ( $this->is_preview() && $output == '' ) {// if preview show a placeholder if empty
4340 $output = $this->preview_placeholder_text( "{{" . $this->base_id . "}}" );
4341 echo $output;
4342 } elseif ( $output && $no_wrap ) {
4343 echo $output;
4344 }
4345 $output = ob_get_clean();
4346
4347 $output = apply_filters( 'wp_super_duper_widget_output', $output, $instance, $args, $this );
4348
4349 echo $output;
4350 }
4351
4352 /**
4353 * Tests if the current output is inside a elementor container.
4354 *
4355 * @return bool
4356 *@since 1.0.4
4357 */
4358 public function is_elementor_widget_output() {
4359 $result = false;
4360 if ( defined( 'ELEMENTOR_VERSION' ) && isset( $this->number ) && $this->number == 'REPLACE_TO_ID' ) {
4361 $result = true;
4362 }
4363
4364 return $result;
4365 }
4366
4367 /**
4368 * Tests if the current output is inside a elementor preview.
4369 *
4370 * @return bool
4371 *@since 1.0.4
4372 */
4373 public function is_elementor_preview() {
4374 $result = false;
4375 if ( isset( $_REQUEST['elementor-preview'] ) || ( is_admin() && isset( $_REQUEST['action'] ) && $_REQUEST['action'] == 'elementor' ) || ( isset( $_REQUEST['action'] ) && $_REQUEST['action'] == 'elementor_ajax' ) ) {
4376 $result = true;
4377 }
4378
4379 return $result;
4380 }
4381
4382 /**
4383 * Tests if the current output is inside a Divi preview.
4384 *
4385 * @return bool
4386 *@since 1.0.6
4387 */
4388 public function is_divi_preview() {
4389 $result = false;
4390 if ( isset( $_REQUEST['et_fb'] ) || isset( $_REQUEST['et_pb_preview'] ) || ( is_admin() && isset( $_REQUEST['action'] ) && $_REQUEST['action'] == 'elementor' ) ) {
4391 $result = true;
4392 }
4393
4394 return $result;
4395 }
4396
4397 /**
4398 * Tests if the current output is inside a Beaver builder preview.
4399 *
4400 * @return bool
4401 *@since 1.0.6
4402 */
4403 public function is_beaver_preview() {
4404 $result = false;
4405 if ( isset( $_REQUEST['fl_builder'] ) ) {
4406 $result = true;
4407 }
4408
4409 return $result;
4410 }
4411
4412 /**
4413 * Tests if the current output is inside a siteorigin builder preview.
4414 *
4415 * @return bool
4416 *@since 1.0.6
4417 */
4418 public function is_siteorigin_preview() {
4419 $result = false;
4420 if ( ! empty( $_REQUEST['siteorigin_panels_live_editor'] ) ) {
4421 $result = true;
4422 }
4423
4424 return $result;
4425 }
4426
4427 /**
4428 * Tests if the current output is inside a cornerstone builder preview.
4429 *
4430 * @return bool
4431 *@since 1.0.8
4432 */
4433 public function is_cornerstone_preview() {
4434 $result = false;
4435 if ( ! empty( $_REQUEST['cornerstone_preview'] ) || basename( $_SERVER['REQUEST_URI'] ) == 'cornerstone-endpoint' ) {
4436 $result = true;
4437 }
4438
4439 return $result;
4440 }
4441
4442 /**
4443 * Tests if the current output is inside a fusion builder preview.
4444 *
4445 * @return bool
4446 *@since 1.1.0
4447 */
4448 public function is_fusion_preview() {
4449 $result = false;
4450 if ( ! empty( $_REQUEST['fb-edit'] ) || ! empty( $_REQUEST['fusion_load_nonce'] ) ) {
4451 $result = true;
4452 }
4453
4454 return $result;
4455 }
4456
4457 /**
4458 * Tests if the current output is inside a Oxygen builder preview.
4459 *
4460 * @return bool
4461 *@since 1.0.18
4462 */
4463 public function is_oxygen_preview() {
4464 $result = false;
4465 if ( ! empty( $_REQUEST['ct_builder'] ) || ( ! empty( $_REQUEST['action'] ) && ( substr( $_REQUEST['action'], 0, 11 ) === "oxy_render_" || substr( $_REQUEST['action'], 0, 10 ) === "ct_render_" ) ) ) {
4466 $result = true;
4467 }
4468
4469 return $result;
4470 }
4471
4472 /**
4473 * Check for Kallyas theme Zion builder preview.
4474 *
4475 * @since 1.1.22
4476 *
4477 * @return bool True when preview page otherwise false.
4478 */
4479 public function is_kallyas_zion_preview() {
4480 $result = false;
4481
4482 if ( function_exists( 'znhg_kallyas_theme_config' ) && ! empty( $_REQUEST['zn_pb_edit'] ) ) {
4483 $result = true;
4484 }
4485
4486 return $result;
4487 }
4488
4489 /**
4490 * Check for Bricks theme builder preview.
4491 *
4492 * @since 1.1.31
4493 *
4494 * @return bool True when preview page otherwise false.
4495 */
4496 public function is_bricks_preview() {
4497 $result = false;
4498
4499 if ( function_exists( 'bricks_is_builder' ) && ( bricks_is_builder() || bricks_is_builder_call() ) ) {
4500 $result = true;
4501 }
4502
4503 return $result;
4504 }
4505
4506 /**
4507 * Check for Breakdance builder preview.
4508 *
4509 * @since 1.2.28
4510 *
4511 * @return bool True when preview page otherwise false.
4512 */
4513 public function is_breakdance_preview() {
4514 return ( \function_exists( 'Breakdance\\isRequestFromBuilderIframe' ) && ( \Breakdance\isRequestFromBuilderIframe() || \Breakdance\isRequestFromBuilderSsr() ) );
4515 }
4516
4517 /**
4518 * General function to check if we are in a preview situation.
4519 *
4520 * @return bool
4521 *@since 1.0.6
4522 */
4523 public function is_preview() {
4524 $preview = false;
4525 if ( $this->is_divi_preview() ) {
4526 $preview = true;
4527 } elseif ( $this->is_elementor_preview() ) {
4528 $preview = true;
4529 } elseif ( $this->is_beaver_preview() ) {
4530 $preview = true;
4531 } elseif ( $this->is_siteorigin_preview() ) {
4532 $preview = true;
4533 } elseif ( $this->is_cornerstone_preview() ) {
4534 $preview = true;
4535 } elseif ( $this->is_fusion_preview() ) {
4536 $preview = true;
4537 } elseif ( $this->is_oxygen_preview() ) {
4538 $preview = true;
4539 } elseif( $this->is_kallyas_zion_preview() ) {
4540 $preview = true;
4541 } elseif( $this->is_block_content_call() ) {
4542 $preview = true;
4543 } elseif( $this->is_bricks_preview() ) {
4544 $preview = true;
4545 } elseif( $this->is_breakdance_preview() ) {
4546 $preview = true;
4547 }
4548
4549 return $preview;
4550 }
4551
4552 /**
4553 * Output the super title.
4554 *
4555 * @param $args
4556 * @param array $instance
4557 *
4558 * @return string
4559 */
4560 public function output_title( $args, $instance = array() ) {
4561 $output = '';
4562 if ( ! empty( $instance['title'] ) ) {
4563 /** This filter is documented in wp-includes/widgets/class-wp-widget-pages.php */
4564 $title = apply_filters( 'widget_title', $instance['title'], $instance, $this->id_base );
4565
4566 if ( empty( $instance['widget_title_tag'] ) ) {
4567 if ( ! isset( $args['before_title'] ) ) {
4568 $args['before_title'] = '';
4569 }
4570
4571 if ( ! isset( $args['after_title'] ) ) {
4572 $args['after_title'] = '';
4573 }
4574
4575 $output = $args['before_title'] . $title . $args['after_title'];
4576 } else {
4577 $tag = esc_attr( $instance['widget_title_tag'] );
4578 $allowed_tags = array( 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'span', 'div', 'p' );
4579 $title_tag = in_array( $tag, $allowed_tags, true ) ? esc_attr( $tag ) : 'h2';
4580
4581 // classes
4582 $title_classes = array();
4583 $title_classes[] = !empty( $instance['widget_title_size_class'] ) ? sanitize_html_class( $instance['widget_title_size_class'] ) : '';
4584 $title_classes[] = !empty( $instance['widget_title_align_class'] ) ? sanitize_html_class( $instance['widget_title_align_class'] ) : '';
4585 $title_classes[] = !empty( $instance['widget_title_color_class'] ) ? "text-".sanitize_html_class( $instance['widget_title_color_class'] ) : '';
4586 $title_classes[] = !empty( $instance['widget_title_border_class'] ) ? sanitize_html_class( $instance['widget_title_border_class'] ) : '';
4587 $title_classes[] = !empty( $instance['widget_title_border_color_class'] ) ? "border-".sanitize_html_class( $instance['widget_title_border_color_class'] ) : '';
4588 $title_classes[] = !empty( $instance['widget_title_mt_class'] ) ? "mt-".absint( $instance['widget_title_mt_class'] ) : '';
4589 $title_classes[] = !empty( $instance['widget_title_mr_class'] ) ? "mr-".absint( $instance['widget_title_mr_class'] ) : '';
4590 $title_classes[] = !empty( $instance['widget_title_mb_class'] ) ? "mb-".absint( $instance['widget_title_mb_class'] ) : '';
4591 $title_classes[] = !empty( $instance['widget_title_ml_class'] ) ? "ml-".absint( $instance['widget_title_ml_class'] ) : '';
4592 $title_classes[] = !empty( $instance['widget_title_pt_class'] ) ? "pt-".absint( $instance['widget_title_pt_class'] ) : '';
4593 $title_classes[] = !empty( $instance['widget_title_pr_class'] ) ? "pr-".absint( $instance['widget_title_pr_class'] ) : '';
4594 $title_classes[] = !empty( $instance['widget_title_pb_class'] ) ? "pb-".absint( $instance['widget_title_pb_class'] ) : '';
4595 $title_classes[] = !empty( $instance['widget_title_pl_class'] ) ? "pl-".absint( $instance['widget_title_pl_class'] ) : '';
4596
4597 $class = !empty( $title_classes ) ? implode(" ",$title_classes) : '';
4598 $output = "<$title_tag class='$class' >$title</$title_tag>";
4599 }
4600
4601 }
4602
4603 return $output;
4604 }
4605
4606 /**
4607 * Outputs the options form inputs for the widget.
4608 *
4609 * @param array $instance The widget options.
4610 */
4611 public function form( $instance ) {
4612
4613 // set widget instance
4614 $this->instance = $instance;
4615
4616 // set it as a SD widget
4617 echo $this->widget_advanced_toggle();
4618
4619 echo "<p>" . esc_attr( $this->options['widget_ops']['description'] ) . "</p>";
4620 $arguments_raw = $this->get_arguments();
4621
4622 if ( is_array( $arguments_raw ) ) {
4623
4624 $arguments = $this->group_arguments( $arguments_raw );
4625
4626 // Do we have sections?
4627 $has_sections = $arguments == $arguments_raw ? false : true;
4628
4629
4630 if ( $has_sections ) {
4631 $panel_count = 0;
4632 foreach ( $arguments as $key => $args ) {
4633
4634 ?>
4635 <script>
4636 // jQuery(this).find("i").toggleClass("fas fa-chevron-up fas fa-chevron-down");jQuery(this).next().toggle();
4637 </script>
4638 <?php
4639
4640 $hide = $panel_count ? ' style="display:none;" ' : '';
4641 $icon_class = $panel_count ? 'fas fa-chevron-up' : 'fas fa-chevron-down';
4642 echo "<button onclick='jQuery(this).find(\"i\").toggleClass(\"fas fa-chevron-up fas fa-chevron-down\");jQuery(this).next().slideToggle();' type='button' class='sd-toggle-group-button sd-input-group-toggle" . sanitize_title_with_dashes( $key ) . "'>" . esc_attr( $key ) . " <i style='float:right;' class='" . $icon_class . "'></i></button>";
4643 echo "<div class='sd-toggle-group sd-input-group-" . sanitize_title_with_dashes( $key ) . "' $hide>";
4644
4645 foreach ( $args as $k => $a ) {
4646
4647 $this->widget_inputs_row_start($k, $a);
4648 $this->widget_inputs( $a, $instance );
4649 $this->widget_inputs_row_end($k, $a);
4650
4651 }
4652
4653 echo "</div>";
4654
4655 $panel_count ++;
4656
4657 }
4658 } else {
4659 foreach ( $arguments as $key => $args ) {
4660 $this->widget_inputs_row_start($key, $args);
4661 $this->widget_inputs( $args, $instance );
4662 $this->widget_inputs_row_end($key, $args);
4663 }
4664 }
4665
4666 }
4667 }
4668
4669 public function widget_inputs_row_start( $key, $args ) {
4670 if ( ! empty( $args['row'] ) ) {
4671 // Maybe open
4672 if ( ! empty( $args['row']['open'] ) ) {
4673 ?>
4674 <div class='bsui sd-argument' data-argument='<?php echo esc_attr( $args['row']['key'] ); ?>' data-element_require='<?php echo ( ! empty( $args['row']['element_require'] ) ? $this->convert_element_require( $args['row']['element_require'] ) : '' ); ?>'>
4675 <?php if ( ! empty( $args['row']['title'] ) ) { ?>
4676 <?php
4677 if ( isset( $args['row']['icon'] ) ) {
4678 $args['row']['icon'] = '';
4679 }
4680
4681 if ( ! isset( $args['row']['device_type'] ) && isset( $args['device_type'] ) ) {
4682 $args['row']['device_type'] = $args['device_type'];
4683 }
4684 ?>
4685 <label class="mb-0"><?php echo $this->widget_field_title( $args['row'] ); ?><?php echo $this->widget_field_desc( $args['row'] ); ?></label>
4686 <?php } ?>
4687 <div class='row<?php echo ( ! empty( $args['row']['class'] ) ? ' ' . esc_attr( $args['row']['class'] ) : '' ); ?>'>
4688 <div class='col pr-2'>
4689 <?php
4690 } else if ( ! empty( $args['row']['close'] ) ) {
4691 echo "<div class='col pl-0 ps-0'>";
4692 } else {
4693 echo "<div class='col pl-0 ps-0 pr-2 pe-2'>";
4694 }
4695 }
4696 }
4697
4698 public function widget_inputs_row_end( $key, $args ) {
4699 if ( ! empty( $args['row'] ) ) {
4700 // Maybe close
4701 if ( ! empty( $args['row']['close'] ) ) {
4702 echo "</div></div>";
4703 }
4704 echo "</div>";
4705 }
4706 }
4707
4708 /**
4709 * Get the hidden input that when added makes the advanced button show on widget settings.
4710 *
4711 * @return string
4712 */
4713 public function widget_advanced_toggle() {
4714
4715 $output = '';
4716 if ( $this->block_show_advanced() ) {
4717 $val = 1;
4718 } else {
4719 $val = 0;
4720 }
4721
4722 $output .= "<input type='hidden' class='sd-show-advanced' value='$val' />";
4723
4724 return $output;
4725 }
4726
4727 /**
4728 * Convert require element.
4729 *
4730 * @param string $input Input element.
4731 *
4732 * @return string $output
4733 *@since 1.0.0
4734 *
4735 */
4736 public function convert_element_require( $input ) {
4737 $input = str_replace( "'", '"', $input );// we only want double quotes
4738
4739 $output = esc_attr( str_replace( array( "[%", "%]", "%:checked]" ), array(
4740 "jQuery(form).find('[data-argument=\"",
4741 "\"]').find('input,select,textarea').val()",
4742 "\"]').find('input:checked').val()"
4743 ), $input ) );
4744
4745 return $output;
4746 }
4747
4748 /**
4749 * Builds the inputs for the widget options.
4750 *
4751 * @param $args
4752 * @param $instance
4753 */
4754 public function widget_inputs( $args, $instance ) {
4755
4756 $class = "";
4757 $element_require = "";
4758 $custom_attributes = "";
4759
4760 // get value
4761 if ( isset( $instance[ $args['name'] ] ) ) {
4762 $value = $instance[ $args['name'] ];
4763 } elseif ( ! isset( $instance[ $args['name'] ] ) && ! empty( $args['default'] ) ) {
4764 $value = is_array( $args['default'] ) ? array_map( "esc_html", $args['default'] ) : esc_html( $args['default'] );
4765 } else {
4766 $value = '';
4767 }
4768
4769 // get placeholder
4770 if ( ! empty( $args['placeholder'] ) ) {
4771 $placeholder = "placeholder='" . esc_html( $args['placeholder'] ) . "'";
4772 } else {
4773 $placeholder = '';
4774 }
4775
4776 // get if advanced
4777 if ( isset( $args['advanced'] ) && $args['advanced'] ) {
4778 $class .= " sd-advanced-setting ";
4779 }
4780
4781 // element_require
4782 if ( isset( $args['element_require'] ) && $args['element_require'] ) {
4783 $element_require = $args['element_require'];
4784 }
4785
4786 // custom_attributes
4787 if ( isset( $args['custom_attributes'] ) && $args['custom_attributes'] ) {
4788 $custom_attributes = $this->array_to_attributes( $args['custom_attributes'], true );
4789 }
4790
4791 // before wrapper
4792 ?>
4793 <p class="sd-argument <?php echo esc_attr( $class ); ?>" data-argument='<?php echo esc_attr( $args['name'] ); ?>' data-element_require='<?php if ( $element_require ) { echo $this->convert_element_require( $element_require );} ?>'>
4794 <?php
4795 switch ( $args['type'] ) {
4796 //array('text','password','number','email','tel','url','color')
4797 case "text":
4798 case "password":
4799 case "number":
4800 case "email":
4801 case "tel":
4802 case "url":
4803 case "color":
4804 ?>
4805 <label for="<?php echo esc_attr( $this->get_field_id( $args['name'] ) ); ?>"><?php echo $this->widget_field_title( $args );?><?php echo $this->widget_field_desc( $args ); ?></label>
4806 <input <?php echo $placeholder; ?> class="widefat" <?php echo $custom_attributes; ?> id="<?php echo esc_attr( $this->get_field_id( $args['name'] ) ); ?>" name="<?php echo esc_attr( $this->get_field_name( $args['name'] ) ); ?>" type="<?php echo esc_attr( $args['type'] ); ?>" value="<?php echo esc_attr( $value ); ?>">
4807 <?php
4808
4809 break;
4810 case "select":
4811 $multiple = isset( $args['multiple'] ) && $args['multiple'] ? true : false;
4812 if ( $multiple ) {
4813 if ( empty( $value ) ) {
4814 $value = array();
4815 }
4816 }
4817 ?>
4818 <label for="<?php echo esc_attr( $this->get_field_id( $args['name'] ) ); ?>"><?php echo $this->widget_field_title( $args ); ?><?php echo $this->widget_field_desc( $args ); ?></label>
4819 <select <?php echo $placeholder; ?> class="widefat" <?php echo $custom_attributes; ?> id="<?php echo esc_attr( $this->get_field_id( $args['name'] ) ); ?>" name="<?php echo esc_attr( $this->get_field_name( $args['name'] ) ); if ( $multiple ) { echo "[]"; } ?>"
4820 <?php if ( $multiple ) {
4821 echo "multiple";
4822 } //@todo not implemented yet due to gutenberg not supporting it
4823 ?>>
4824 <?php
4825
4826 if ( ! empty( $args['options'] ) ) {
4827 foreach ( $args['options'] as $val => $label ) {
4828 if ( $multiple ) {
4829 $selected = in_array( $val, $value ) ? 'selected="selected"' : '';
4830 } else {
4831 $selected = selected( $value, $val, false );
4832 }
4833 echo "<option value='$val' " . $selected . ">$label</option>";
4834 }
4835 }
4836 ?>
4837 </select>
4838 <?php
4839 break;
4840 case "checkbox":
4841 ?>
4842 <input <?php echo $placeholder; ?> <?php checked( 1, $value, true ) ?> <?php echo $custom_attributes; ?> class="widefat" id="<?php echo esc_attr( $this->get_field_id( $args['name'] ) ); ?>" name="<?php echo esc_attr( $this->get_field_name( $args['name'] ) ); ?>" type="checkbox" value="1">
4843 <label for="<?php echo esc_attr( $this->get_field_id( $args['name'] ) ); ?>"><?php echo $this->widget_field_title( $args );?><?php echo $this->widget_field_desc( $args ); ?></label>
4844 <?php
4845 break;
4846 case "textarea":
4847 ?>
4848 <label for="<?php echo esc_attr( $this->get_field_id( $args['name'] ) ); ?>"><?php echo $this->widget_field_title( $args ); ?><?php echo $this->widget_field_desc( $args ); ?></label>
4849 <textarea <?php echo $placeholder; ?> class="widefat" <?php echo $custom_attributes; ?> id="<?php echo esc_attr( $this->get_field_id( $args['name'] ) ); ?>" name="<?php echo esc_attr( $this->get_field_name( $args['name'] ) ); ?>"><?php echo esc_attr( $value ); ?></textarea>
4850 <?php
4851
4852 break;
4853 case "hidden":
4854 ?>
4855 <input id="<?php echo esc_attr( $this->get_field_id( $args['name'] ) ); ?>" name="<?php echo esc_attr( $this->get_field_name( $args['name'] ) ); ?>" type="hidden" value="<?php echo esc_attr( $value ); ?>">
4856 <?php
4857 break;
4858 default:
4859 echo "No input type found!"; // @todo we need to add more input types.
4860 }
4861 // after wrapper
4862 ?></p><?php
4863 }
4864
4865 public function get_widget_icon($icon = 'box-top', $title = ''){
4866 if($icon=='box-top'){
4867 return '<svg title="'.esc_attr($title).'" width="20px" height="20px" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg" fill-rule="evenodd" clip-rule="evenodd" stroke-linejoin="round" stroke-miterlimit="1.414" role="img" aria-hidden="true" focusable="false"><rect x="2.714" y="5.492" width="1.048" height="9.017" fill="#555D66"></rect><rect x="16.265" y="5.498" width="1.023" height="9.003" fill="#555D66"></rect><rect x="5.518" y="2.186" width="8.964" height="2.482" fill="#272B2F"></rect><rect x="5.487" y="16.261" width="9.026" height="1.037" fill="#555D66"></rect></svg>';
4868 }elseif($icon=='box-right'){
4869 return '<svg title="'.esc_attr($title).'" width="20px" height="20px" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg" fill-rule="evenodd" clip-rule="evenodd" stroke-linejoin="round" stroke-miterlimit="1.414" role="img" aria-hidden="true" focusable="false"><rect x="2.714" y="5.492" width="1.046" height="9.017" fill="#555D66"></rect><rect x="15.244" y="5.498" width="2.518" height="9.003" fill="#272B2F"></rect><rect x="5.518" y="2.719" width="8.964" height="0.954" fill="#555D66"></rect><rect x="5.487" y="16.308" width="9.026" height="0.99" fill="#555D66"></rect></svg>';
4870 }elseif($icon=='box-bottom'){
4871 return '<svg title="'.esc_attr($title).'" width="20px" height="20px" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg" fill-rule="evenodd" clip-rule="evenodd" stroke-linejoin="round" stroke-miterlimit="1.414" role="img" aria-hidden="true" focusable="false"><rect x="2.714" y="5.492" width="1" height="9.017" fill="#555D66"></rect><rect x="16.261" y="5.498" width="1.027" height="9.003" fill="#555D66"></rect><rect x="5.518" y="2.719" width="8.964" height="0.968" fill="#555D66"></rect><rect x="5.487" y="15.28" width="9.026" height="2.499" fill="#272B2F"></rect></svg>';
4872 }elseif($icon=='box-left'){
4873 return '<svg title="'.esc_attr($title).'" width="20px" height="20px" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg" fill-rule="evenodd" clip-rule="evenodd" stroke-linejoin="round" stroke-miterlimit="1.414" role="img" aria-hidden="true" focusable="false"><rect x="2.202" y="5.492" width="2.503" height="9.017" fill="#272B2F"></rect><rect x="16.276" y="5.498" width="1.012" height="9.003" fill="#555D66"></rect><rect x="5.518" y="2.719" width="8.964" height="0.966" fill="#555D66"></rect><rect x="5.487" y="16.303" width="9.026" height="0.995" fill="#555D66"></rect></svg>';
4874 }
4875 }
4876
4877 /**
4878 * Get the widget input description html.
4879 *
4880 * @param $args
4881 *
4882 * @return string
4883 * @todo, need to make its own tooltip script
4884 */
4885 public function widget_field_desc( $args ) {
4886
4887 $description = '';
4888 if ( isset( $args['desc'] ) && $args['desc'] ) {
4889 if ( isset( $args['desc_tip'] ) && $args['desc_tip'] ) {
4890 $description = $this->desc_tip( $args['desc'] );
4891 } else {
4892 $description = '<span class="description">' . wp_kses_post( $args['desc'] ) . '</span>';
4893 }
4894 }
4895
4896 return $description;
4897 }
4898
4899 /**
4900 * Get the widget input title html.
4901 *
4902 * @param $args
4903 *
4904 * @return string
4905 */
4906 public function widget_field_title( $args ) {
4907 $title = '';
4908
4909 if ( isset( $args['title'] ) && $args['title'] ) {
4910 if ( ! empty( $args['device_type'] ) ) {
4911 $args['title'] .= ' (' . $args['device_type'] . ')'; // Append device type to title.
4912 }
4913
4914 if ( isset( $args['icon'] ) && $args['icon'] ) {
4915 $title = self::get_widget_icon( $args['icon'], $args['title'] );
4916 } else {
4917 $title = esc_attr( $args['title'] );
4918 }
4919 }
4920
4921 return $title;
4922 }
4923
4924 /**
4925 * Get the tool tip html.
4926 *
4927 * @param $tip
4928 * @param bool $allow_html
4929 *
4930 * @return string
4931 */
4932 function desc_tip( $tip, $allow_html = false ) {
4933 if ( $allow_html ) {
4934 $tip = $this->sanitize_tooltip( $tip );
4935 } else {
4936 $tip = esc_attr( $tip );
4937 }
4938
4939 return '<span class="gd-help-tip dashicons dashicons-editor-help" title="' . $tip . '"></span>';
4940 }
4941
4942 /**
4943 * Sanitize a string destined to be a tooltip.
4944 *
4945 * @param string $var
4946 *
4947 * @return string
4948 */
4949 public function sanitize_tooltip( $var ) {
4950 return htmlspecialchars( wp_kses( html_entity_decode( $var ), array(
4951 'br' => array(),
4952 'em' => array(),
4953 'strong' => array(),
4954 'small' => array(),
4955 'span' => array(),
4956 'ul' => array(),
4957 'li' => array(),
4958 'ol' => array(),
4959 'p' => array(),
4960 ) ) );
4961 }
4962
4963 /**
4964 * Processing widget options on save
4965 *
4966 * @param array $new_instance The new options
4967 * @param array $old_instance The previous options
4968 *
4969 * @return array
4970 * @todo we should add some sanitation here.
4971 */
4972 public function update( $new_instance, $old_instance ) {
4973
4974 //save the widget
4975 $instance = array_merge( (array) $old_instance, (array) $new_instance );
4976
4977 // set widget instance
4978 $this->instance = $instance;
4979
4980 if ( empty( $this->arguments ) ) {
4981 $this->get_arguments();
4982 }
4983
4984 // check for checkboxes
4985 if ( ! empty( $this->arguments ) ) {
4986 foreach ( $this->arguments as $argument ) {
4987 if ( isset( $argument['type'] ) && $argument['type'] == 'checkbox' && ! isset( $new_instance[ $argument['name'] ] ) ) {
4988 $instance[ $argument['name'] ] = '0';
4989 }
4990 }
4991 }
4992
4993 // maybe sanitize widget title
4994 if(!empty($instance['title'])) {
4995 $instance['title'] = wp_kses_post( $instance['title'] );
4996 }
4997
4998 return $instance;
4999 }
5000
5001 /**
5002 * Checks if the current call is a ajax call to get the block content.
5003 *
5004 * This can be used in your widget to return different content as the block content.
5005 *
5006 * @return bool
5007 *@since 1.0.3
5008 */
5009 public function is_block_content_call() {
5010 $result = false;
5011 if ( wp_doing_ajax() && isset( $_REQUEST['action'] ) && $_REQUEST['action'] == 'super_duper_output_shortcode' ) {
5012 $result = true;
5013 }
5014
5015 return $result;
5016 }
5017
5018 /**
5019 * Get an instance hash that will be unique to the type and settings.
5020 *
5021 * @return string
5022 *@since 1.0.20
5023 */
5024 public function get_instance_hash(){
5025 $instance_string = $this->base_id.serialize($this->instance);
5026 return hash('crc32b',$instance_string);
5027 }
5028
5029 /**
5030 * Generate and return inline styles from CSS rules that will match the unique class of the instance.
5031 *
5032 * @param array $rules
5033 *
5034 * @return string
5035 *@since 1.0.20
5036 */
5037 public function get_instance_style($rules = array()){
5038 $css = '';
5039
5040 if(!empty($rules)){
5041 $rules = array_unique($rules);
5042 $instance_hash = $this->get_instance_hash();
5043 $css .= "<style>";
5044 foreach($rules as $rule){
5045 $css .= ".sdel-$instance_hash $rule";
5046 }
5047 $css .= "</style>";
5048 }
5049
5050 return $css;
5051 }
5052
5053 /**
5054 * Encode shortcodes tags.
5055 *
5056 * @param string $content Content to search for shortcode tags.
5057 *
5058 *@return string Content with shortcode tags removed.
5059 *@since 1.0.28
5060 *
5061 */
5062 public function encode_shortcodes( $content ) {
5063 // Avoids existing encoded tags.
5064 $trans = array(
5065 '&#91;' => '&#091;',
5066 '&#93;' => '&#093;',
5067 '&amp;#91;' => '&#091;',
5068 '&amp;#93;' => '&#093;',
5069 '&lt;' => '&0lt;',
5070 '&gt;' => '&0gt;',
5071 '&amp;lt;' => '&0lt;',
5072 '&amp;gt;' => '&0gt;',
5073 );
5074
5075 $content = strtr( $content, $trans );
5076
5077 $trans = array(
5078 '[' => '&#91;',
5079 ']' => '&#93;',
5080 '<' => '&lt;',
5081 '>' => '&gt;',
5082 '"' => '&quot;',
5083 "'" => '&#39;',
5084 );
5085
5086 $content = strtr( $content, $trans );
5087
5088 return $content;
5089 }
5090
5091 /**
5092 * Remove encoded shortcod tags.
5093 *
5094 * @param string $content Content to search for shortcode tags.
5095 *
5096 *@return string Content with decoded shortcode tags.
5097 *@since 1.0.28
5098 *
5099 */
5100 public function decode_shortcodes( $content ) {
5101 $trans = array(
5102 '&#91;' => '[',
5103 '&#93;' => ']',
5104 '&amp;#91;' => '[',
5105 '&amp;#93;' => ']',
5106 '&lt;' => '<',
5107 '&gt;' => '>',
5108 '&amp;lt;' => '<',
5109 '&amp;gt;' => '>',
5110 '&quot;' => '"',
5111 '&apos;' => "'",
5112 );
5113
5114 $content = strtr( $content, $trans );
5115
5116 $trans = array(
5117 '&#091;' => '&#91;',
5118 '&#093;' => '&#93;',
5119 '&amp;#091;' => '&#91;',
5120 '&amp;#093;' => '&#93;',
5121 '&0lt;' => '&lt;',
5122 '&0gt;' => '&gt;',
5123 '&amp;0lt;' => '&lt;',
5124 '&amp;0gt;' => '&gt;',
5125 );
5126
5127 $content = strtr( $content, $trans );
5128
5129 return $content;
5130 }
5131
5132 public function block_visibility_fields( $args ) {
5133 global $aui_bs5;
5134
5135 $value = ! empty( $args['value'] ) ? esc_attr( $args['value'] ) : '';
5136 $content = '<div class="bs-vc-rule-template d-none">';
5137 $content .= '<div class="px-3 pt-3 pb-0 mb-3 border border-1 rounded-1 position-relative bs-vc-rule" data-bs-index="BSVCINDEX" >';
5138 $content .= '<div class="row">';
5139 $content .= '<div class="col-sm-12">';
5140 $content .= '<div class="bs-rule-action position-absolute top-0 end-0 right-0 p-2 zindex-5"' . ( $aui_bs5 ? '' : ' style="top:0!important;right:0!important;z-index:5!important;"' ) . '><span class="text-danger c-pointer bs-vc-remove-rule" title="' . esc_attr__( 'Remove Rule', 'ayecode-connect' ) . '"><i class="fas fa-circle-minus fs-6"></i></span></div>';
5141 $content .= aui()->select(
5142 array(
5143 'id' => 'bsvc_rule_BSVCINDEX',
5144 'name' => 'bsvc_rule_BSVCINDEX',
5145 'label' => __( 'Rule', 'ayecode-connect' ),
5146 'placeholder' => __( 'Select Rule...', 'ayecode-connect' ),
5147 'class' => 'bsvc_rule ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5148 'options' => sd_visibility_rules_options(),
5149 'default' => '',
5150 'value' => '',
5151 'label_type' => '',
5152 'select2' => false,
5153 'input_group_left' => __( 'Rule:', 'ayecode-connect' ),
5154 'extra_attributes' => array(
5155 'data-minimum-results-for-search' => '-1'
5156 )
5157 )
5158 );
5159
5160 $content .= '</div>';
5161
5162 if ( ! $aui_bs5 ) {
5163 $content = str_replace( 'input-group"', 'input-group input-group-sm"', $content );
5164 }
5165
5166 if ( class_exists( 'GeoDirectory' ) ) {
5167 $content .= '<div class="col-md-7 col-sm-12">';
5168
5169 $content .= aui()->select(
5170 array(
5171 'id' => 'bsvc_gd_field_BSVCINDEX',
5172 'name' => 'bsvc_gd_field_BSVCINDEX',
5173 'label' => __( 'FIELD', 'ayecode-connect' ),
5174 'placeholder' => __( 'FIELD', 'ayecode-connect' ),
5175 'class' => 'bsvc_gd_field ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5176 'options' => sd_visibility_gd_field_options(),
5177 'default' => '',
5178 'value' => '',
5179 'label_type' => '',
5180 'select2' => false,
5181 'element_require' => '[%bsvc_rule_BSVCINDEX%]=="gd_field"',
5182 'extra_attributes' => array(
5183 'data-minimum-results-for-search' => '-1'
5184 )
5185 )
5186 );
5187
5188 $content .= '</div>';
5189 $content .= '<div class="col-md-5 col-sm-12">';
5190
5191 $content .= aui()->select(
5192 array(
5193 'id' => 'bsvc_gd_field_condition_BSVCINDEX',
5194 'name' => 'bsvc_gd_field_condition_BSVCINDEX',
5195 'label' => __( 'CONDITION', 'ayecode-connect' ),
5196 'placeholder' => __( 'CONDITION', 'ayecode-connect' ),
5197 'class' => 'bsvc_gd_field_condition ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5198 'options' => sd_visibility_field_condition_options(),
5199 'default' => '',
5200 'value' => '',
5201 'label_type' => '',
5202 'select2' => false,
5203 'element_require' => '[%bsvc_rule_BSVCINDEX%]=="gd_field"',
5204 'extra_attributes' => array(
5205 'data-minimum-results-for-search' => '-1'
5206 )
5207 )
5208 );
5209
5210 $content .= '</div>';
5211 $content .= '<div class="col-sm-12">';
5212
5213 $content .= aui()->input(
5214 array(
5215 'type' => 'text',
5216 'id' => 'bsvc_gd_field_search_BSVCINDEX',
5217 'name' => 'bsvc_gd_field_search_BSVCINDEX',
5218 'label' => __( 'VALUE TO MATCH', 'ayecode-connect' ),
5219 'class' => 'bsvc_gd_field_search form-control-sm',
5220 'placeholder' => __( 'VALUE TO MATCH', 'ayecode-connect' ),
5221 'label_type' => '',
5222 'value' => '',
5223 'element_require' => '([%bsvc_rule_BSVCINDEX%]=="gd_field" && [%bsvc_gd_field_condition_BSVCINDEX%] && [%bsvc_gd_field_condition_BSVCINDEX%]!="is_empty" && [%bsvc_gd_field_condition_BSVCINDEX%]!="is_not_empty")'
5224 )
5225 );
5226
5227 $content .= '</div>';
5228 }
5229
5230 $content .= apply_filters( 'sd_block_visibility_fields', '', $args );
5231
5232 $content .= '</div>';
5233
5234 $content .= '<div class="row aui-conditional-field" data-element-require="jQuery(form).find(\'[name=bsvc_rule_BSVCINDEX]\').val()==\'user_roles\'" data-argument="bsvc_user_roles_BSVCINDEX_1"><label for="bsvc_user_roles_BSVCINDEX_1" class="form-label mb-3' . ( $aui_bs5 ? '' : ' ml-3 w-100' ) . '">' . __( 'Select User Roles:', 'ayecode-connect' ) . '</label>';
5235 $role_options = sd_user_roles_options();
5236
5237 $role_option_i = 0;
5238 foreach ( $role_options as $role_option_key => $role_option_name ) {
5239 $role_option_i++;
5240
5241 $content .= '<div class="col-sm-6' . ( $aui_bs5 ? '' : ' mb-2' ) . '">';
5242 $content .= aui()->input(
5243 array(
5244 'id' => 'bsvc_user_roles_BSVCINDEX_' . $role_option_i,
5245 'name' => 'bsvc_user_roles_BSVCINDEX[]',
5246 'type' => 'checkbox',
5247 'label' => $role_option_name,
5248 'label_type' => 'hidden',
5249 'class' => 'bsvc_user_roles',
5250 'value' => $role_option_key,
5251 'switch' => 'md',
5252 'no_wrap' => true
5253 )
5254 );
5255 $content .= '</div>';
5256 }
5257 $content .= '</div>';
5258 $content .= '<div class="bs-vc-sep-wrap text-center position-absolute top-0 mt-n3"' . ( $aui_bs5 ? '' : ' style="top:0!important;"' ) . '><div class="bs-vc-sep-cond d-inline-block badge text-dark bg-gray mt-1">' . esc_html__( 'AND', 'ayecode-connect' ) . '</div></div>';
5259 $content .= '</div>';
5260 $content .= '</div>';
5261 $content .= '<form id="bs-vc-modal-form" class="bs-vc-modal-form">';
5262 $content .= '<div class="bs-vc-rule-sets"></div>';
5263 $content .= '<div class="row"><div class="col-sm-12 text-center pt-1 pb-4"><button type="button" class="btn btn-sm btn-primary d-block w-100 bs-vc-add-rule"><i class="fas fa-plus"></i> ' . __( 'Add Rule', 'ayecode-connect' ) . '</button></div></div>';
5264 $content .= '<div class="row"><div class="col-md-6 col-sm-12">';
5265 $content .= aui()->select(
5266 array(
5267 'id' => 'bsvc_output',
5268 'name' => 'bsvc_output',
5269 'label' => __( 'What should happen if rules met.', 'ayecode-connect' ),
5270 'placeholder' => __( 'Show Block', 'ayecode-connect' ),
5271 'class' => 'bsvc_output ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5272 'options' => sd_visibility_output_options(),
5273 'default' => '',
5274 'value' => '',
5275 'label_type' => 'top',
5276 'select2' => false,
5277 'extra_attributes' => array(
5278 'data-minimum-results-for-search' => '-1'
5279 )
5280 )
5281 );
5282
5283 $content .= '</div><div class="col-md-6 col-sm-12">';
5284
5285 $content .= aui()->select(
5286 array(
5287 'id' => 'bsvc_page',
5288 'name' => 'bsvc_page',
5289 'label' => __( 'Page Content', 'ayecode-connect' ),
5290 'placeholder' => __( 'Select Page ID...', 'ayecode-connect' ),
5291 'class' => 'bsvc_page ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5292 'options' => sd_template_page_options(),
5293 'default' => '',
5294 'value' => '',
5295 'label_type' => 'top',
5296 'select2' => false,
5297 'element_require' => '[%bsvc_output%]=="page"'
5298 )
5299 );
5300
5301 $content .= aui()->select(
5302 array(
5303 'id' => 'bsvc_tmpl_part',
5304 'name' => 'bsvc_tmpl_part',
5305 'label' => __( 'Template Part', 'ayecode-connect' ),
5306 'placeholder' => __( 'Select Template Part...', 'ayecode-connect' ),
5307 'class' => 'bsvc_tmpl_part ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5308 'options' => sd_template_part_options(),
5309 'default' => '',
5310 'value' => '',
5311 'label_type' => 'top',
5312 'select2' => false,
5313 'element_require' => '[%bsvc_output%]=="template_part"',
5314 'extra_attributes' => array(
5315 'data-minimum-results-for-search' => '-1'
5316 )
5317 )
5318 );
5319
5320 $content .= aui()->select(
5321 array(
5322 'id' => 'bsvc_message_type',
5323 'name' => 'bsvc_message_type',
5324 'label' => __( 'Custom Message Type', 'ayecode-connect' ),
5325 'placeholder' => __( 'Default (none)', 'ayecode-connect' ),
5326 'class' => 'bsvc_message_type ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5327 'options' => sd_aui_colors(),
5328 'default' => '',
5329 'value' => '',
5330 'label_type' => 'top',
5331 'select2' => false,
5332 'element_require' => '[%bsvc_output%]=="message"',
5333 'extra_attributes' => array(
5334 'data-minimum-results-for-search' => '-1'
5335 )
5336 )
5337 );
5338
5339 $content .= '</div><div class="col-sm-12">';
5340
5341 $content .= aui()->input(
5342 array(
5343 'type' => 'text',
5344 'id' => 'bsvc_message',
5345 'name' => 'bsvc_message',
5346 'label' => '',
5347 'class' => 'bsvc_message form-control-sm mb-3',
5348 'placeholder' => __( 'CUSTOM MESSAGE TO SHOW', 'ayecode-connect' ),
5349 'label_type' => '',
5350 'value' => '',
5351 'form_group_class' => ' ',
5352 'element_require' => '[%bsvc_output%]=="message"',
5353 )
5354 );
5355
5356 $content .= '</div></div><div class="row"><div class="col col-12"><div class="pt-3 mt-1 border-top"></div></div><div class="col-md-6 col-sm-12">';
5357 $content .= aui()->select(
5358 array(
5359 'id' => 'bsvc_output_n',
5360 'name' => 'bsvc_output_n',
5361 'label' => __( 'What should happen if rules NOT met.', 'ayecode-connect' ),
5362 'placeholder' => __( 'Show Block', 'ayecode-connect' ),
5363 'class' => 'bsvc_output_n ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5364 'options' => sd_visibility_output_options(),
5365 'default' => '',
5366 'value' => '',
5367 'label_type' => 'top',
5368 'select2' => false,
5369 'extra_attributes' => array(
5370 'data-minimum-results-for-search' => '-1'
5371 )
5372 )
5373 );
5374
5375 $content .= '</div><div class="col-md-6 col-sm-12">';
5376
5377 $content .= aui()->select(
5378 array(
5379 'id' => 'bsvc_page_n',
5380 'name' => 'bsvc_page_n',
5381 'label' => __( 'Page Content', 'ayecode-connect' ),
5382 'placeholder' => __( 'Select Page ID...', 'ayecode-connect' ),
5383 'class' => 'bsvc_page_n ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5384 'options' => sd_template_page_options(),
5385 'default' => '',
5386 'value' => '',
5387 'label_type' => 'top',
5388 'select2' => false,
5389 'element_require' => '[%bsvc_output_n%]=="page"'
5390 )
5391 );
5392
5393 $content .= aui()->select(
5394 array(
5395 'id' => 'bsvc_tmpl_part_n',
5396 'name' => 'bsvc_tmpl_part_n',
5397 'label' => __( 'Template Part', 'ayecode-connect' ),
5398 'placeholder' => __( 'Select Template Part...', 'ayecode-connect' ),
5399 'class' => 'bsvc_tmpl_part_n ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5400 'options' => sd_template_part_options(),
5401 'default' => '',
5402 'value' => '',
5403 'label_type' => 'top',
5404 'select2' => false,
5405 'element_require' => '[%bsvc_output_n%]=="template_part"',
5406 'extra_attributes' => array(
5407 'data-minimum-results-for-search' => '-1'
5408 )
5409 )
5410 );
5411
5412 $content .= aui()->select(
5413 array(
5414 'id' => 'bsvc_message_type_n',
5415 'name' => 'bsvc_message_type_n',
5416 'label' => __( 'Custom Message Type', 'ayecode-connect' ),
5417 'placeholder' => __( 'Default (none)', 'ayecode-connect' ),
5418 'class' => 'bsvc_message_type_n ' . ( $aui_bs5 ? 'form-select-sm' : 'custom-select-sm' ) . ' no-select2 mw-100',
5419 'options' => sd_aui_colors(),
5420 'default' => '',
5421 'value' => '',
5422 'label_type' => 'top',
5423 'select2' => false,
5424 'element_require' => '[%bsvc_output_n%]=="message"',
5425 'extra_attributes' => array(
5426 'data-minimum-results-for-search' => '-1'
5427 )
5428 )
5429 );
5430
5431 $content .= '</div><div class="col-sm-12">';
5432
5433 $content .= aui()->input(
5434 array(
5435 'type' => 'text',
5436 'id' => 'bsvc_message_n',
5437 'name' => 'bsvc_message_n',
5438 'label' => '',
5439 'class' => 'bsvc_message_n form-control-sm',
5440 'placeholder' => __( 'CUSTOM MESSAGE TO SHOW', 'ayecode-connect' ),
5441 'label_type' => '',
5442 'value' => '',
5443 'form_group_class' => ' ',
5444 'element_require' => '[%bsvc_output_n%]=="message"',
5445 )
5446 );
5447
5448 $content .= '</div></div></form><input type="hidden" id="bsvc_raw_value" name="bsvc_raw_value" value="' . $value . '">';
5449
5450 return $content;
5451 }
5452
5453 /**
5454 * Handle media_buttons hook.
5455 *
5456 * @since 1.2.7
5457 */
5458 public function wp_media_buttons() {
5459 global $shortcode_insert_button_once;
5460
5461 // Fix conflicts with UpSolution Core in header template edit element.
5462 if ( defined( 'US_CORE_DIR' ) && ! empty( $_REQUEST['action'] ) && $_REQUEST['action'] == 'us_ajax_hb_get_ebuilder_html' ) {
5463 $shortcode_insert_button_once = true;
5464 }
5465 }
5466
5467 /**
5468 * Check if supports block visibility.
5469 *
5470 * @since 1.2.28
5471 * @return bool True if site supports block visibility else False.
5472 */
5473 public function supports_block_visibility() {
5474 // FSE Theme.
5475 if ( function_exists( 'wp_is_block_theme' ) && wp_is_block_theme() ) {
5476 return true;
5477 }
5478
5479 // BlockStrap Block Builder.
5480 if ( defined( 'BLOCKSTRAP_BLOCKS_VERSION' ) ) {
5481 return true;
5482 }
5483
5484 return $this->is_gutenberg();
5485 }
5486
5487 /**
5488 * Check if Gutenberg is in use.
5489 *
5490 * @since 1.2.28
5491 * @return bool True if site uses Gutenberg else False.
5492 */
5493 public function is_gutenberg() {
5494 global $wp_version;
5495
5496 $is_gutenberg = true;
5497
5498 // If less than v5.
5499 if ( version_compare( $wp_version, '5.0.0', '<' ) ) {
5500 $is_gutenberg = false;
5501 }
5502
5503 if ( class_exists( 'Classic_Editor' ) ) {
5504 $is_gutenberg = false; // Classic Editor plugin is active.
5505 } else if ( $this->is_classicpress() ) {
5506 $is_gutenberg = false; // Site is using ClassicPress.
5507 }
5508
5509 return $is_gutenberg;
5510 }
5511
5512 /**
5513 * Check if ClassicPress is in use.
5514 *
5515 * @since 1.2.29
5516 * @return bool True if site uses ClassicPress else False.
5517 */
5518 public function is_classicpress() {
5519 if ( function_exists( 'classicpress_version' ) ) {
5520 $is_classicpress = true;
5521 } else {
5522 $is_classicpress = false;
5523 }
5524
5525 return $is_classicpress;
5526 }
5527 }
5528 }
5529