PluginProbe
Kit (formerly ConvertKit) – Email Newsletter, Email Marketing, Membership, Subscribers and Landing Pages / 3.4.0
Kit (formerly ConvertKit) – Email Newsletter, Email Marketing, Membership, Subscribers and Landing Pages v3.4.0
3.4.1 3.4.0 3.3.9 3.3.8 3.3.7 3.3.6 3.3.5 3.3.4 3.3.3 3.3.2 3.3.1 2.2.0 2.2.1 2.2.2 2.2.3 2.2.4 2.2.5 2.2.6 2.2.7 2.2.8 2.2.9 2.3.0 2.3.1 2.3.2 2.3.3 All 194 releases
convertkit / admin / section / class-convertkit-admin-section-base.php

class-convertkit-admin-section-base.php in Kit (formerly ConvertKit) – Email Newsletter, Email Marketing, Membership, Subscribers and Landing Pages 3.4.0, at admin/section/class-convertkit-admin-section-base.php

955 lines 23.5 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * ConvertKit Settings Base class.
4 *
5 * @package ConvertKit
6 * @author ConvertKit
7 */
8
9 /**
10 * ConvertKit Settings class
11 *
12 * @package ConvertKit
13 * @author ConvertKit
14 */
15 abstract class ConvertKit_Admin_Section_Base {
16
17 /**
18 * Section name
19 *
20 * @var string
21 */
22 public $name;
23
24 /**
25 * Section title
26 *
27 * @var string
28 */
29 public $title;
30
31 /**
32 * Section tab text
33 *
34 * @var string
35 */
36 public $tab_text;
37
38 /**
39 * Options table key
40 *
41 * @var string
42 */
43 public $settings_key;
44
45 /**
46 * Holds the settings class for the section.
47 *
48 * @since 1.9.6
49 *
50 * @var false|ConvertKit_Settings|ConvertKit_ContactForm7_Settings|ConvertKit_Wishlist_Settings|ConvertKit_Settings_Restrict_Content|ConvertKit_Settings_Broadcasts|ConvertKit_Forminator_Settings|ConvertKit_Settings_MCP
51 */
52 public $settings;
53
54 /**
55 * Holds the settings sections for a settings screen.
56 *
57 * @since 2.7.1
58 *
59 * @var array
60 */
61 public $settings_sections = array();
62
63 /**
64 * Holds whether this settings section is for beta functionality.
65 *
66 * @since 2.1.0
67 *
68 * @var bool
69 */
70 public $is_beta = false;
71
72 /**
73 * Holds whether the save button should be disabled e.g. there are no
74 * settings on screen to save.
75 *
76 * @since 2.4.9
77 *
78 * @var bool
79 */
80 public $save_disabled = false;
81
82 /**
83 * Constructor
84 */
85 public function __construct() {
86
87 // If tab text is not defined, use the title for the tab's text.
88 if ( empty( $this->tab_text ) ) {
89 $this->tab_text = $this->title;
90 }
91
92 // Output the Intercom messenger if we're on the Plugin's settings screen.
93 if ( $this->on_settings_screen( $this->name ) ) {
94 add_action( 'admin_footer', array( $this, 'output_intercom' ) );
95 }
96
97 // Register the settings section.
98 $this->register_section();
99
100 }
101
102 /**
103 * Helper method to determine if we're viewing the current settings screen.
104 *
105 * @since 2.5.0
106 *
107 * @param string $tab Current settings tab (general|tools|restrict-content|broadcasts).
108 * @return bool
109 */
110 public function on_settings_screen( $tab ) {
111
112 // Bail if this is an AJAX or Cron request.
113 if ( wp_doing_ajax() || wp_doing_cron() ) {
114 return false;
115 }
116
117 // Bail if we're not on the settings screen.
118 if ( ! filter_has_var( INPUT_GET, 'page' ) ) {
119 return false;
120 }
121 if ( filter_input( INPUT_GET, 'page', FILTER_SANITIZE_FULL_SPECIAL_CHARS ) !== '_wp_convertkit_settings' ) {
122 return false;
123 }
124
125 // Define current settings tab.
126 // General screen won't always be loaded with a `tab` parameter.
127 if ( filter_has_var( INPUT_GET, 'tab' ) ) {
128 $current_tab = filter_input( INPUT_GET, 'tab', FILTER_SANITIZE_FULL_SPECIAL_CHARS );
129 } else {
130 $current_tab = 'general';
131 }
132
133 // Return whether the request is for the current settings tab.
134 return ( $current_tab === $tab );
135
136 }
137
138 /**
139 * Register settings section.
140 */
141 public function register_section() {
142
143 // Don't register a settings section if no settings key is defined.
144 if ( empty( $this->settings_key ) ) {
145 return;
146 }
147
148 // Register settings sections.
149 foreach ( $this->settings_sections as $name => $settings_section ) {
150 // Determine if this settings section needs to be wrapped in its own container.
151 $wrap = array();
152 if ( $settings_section['wrap'] ) {
153 $wrap = array(
154 'before_section' => $this->get_render_container_start(),
155 'after_section' => $this->get_render_container_end(),
156 );
157 }
158
159 add_settings_section(
160 ( $name === 'general' ? $this->name : $this->name . '-' . $name ),
161 $settings_section['title'],
162 $settings_section['callback'],
163 $this->settings_key,
164 $wrap
165 );
166 }
167
168 // Register settings fields.
169 $this->register_fields();
170
171 // Register setting to store data in options table.
172 register_setting(
173 $this->settings_key,
174 $this->settings_key,
175 array( $this, 'sanitize_settings' )
176 );
177
178 }
179
180 /**
181 * Register fields for this section
182 */
183 public function register_fields() {
184 }
185
186 /**
187 * Prints help info for this section
188 */
189 abstract public function print_section_info();
190
191 /**
192 * Returns the URL for the ConvertKit documentation for this setting section.
193 */
194 abstract public function documentation_url();
195
196 /**
197 * Outputs success and/or error notices if required.
198 *
199 * @since 2.0.0
200 */
201 public function maybe_output_notices() {
202
203 // Define notices that might be displayed as a notification.
204 $notices = array();
205
206 /**
207 * Register success and error notices for settings screens.
208 *
209 * @since 2.5.1
210 *
211 * @param array $notices Regsitered success and error notices.
212 * @return array
213 */
214 $notices = apply_filters( 'convertkit_settings_base_register_notices', $notices );
215
216 // Output the verbose error description if supplied (e.g. OAuth).
217 if ( filter_has_var( INPUT_GET, 'error_description' ) ) {
218 $this->output_error( filter_input( INPUT_GET, 'error_description', FILTER_SANITIZE_FULL_SPECIAL_CHARS ) );
219 }
220
221 // Output error notification if defined.
222 if ( filter_has_var( INPUT_GET, 'error' ) ) {
223 $error = filter_input( INPUT_GET, 'error', FILTER_SANITIZE_FULL_SPECIAL_CHARS );
224 if ( array_key_exists( $error, $notices ) ) {
225 $this->output_error( $notices[ $error ] );
226 }
227 }
228
229 // Output success notification if defined.
230 if ( filter_has_var( INPUT_GET, 'success' ) ) {
231 $success = filter_input( INPUT_GET, 'success', FILTER_SANITIZE_FULL_SPECIAL_CHARS );
232 if ( array_key_exists( $success, $notices ) ) {
233 $this->output_success( $notices[ $success ] );
234 }
235 }
236
237 }
238
239 /**
240 * Renders the section
241 */
242 public function render() {
243
244 /**
245 * Performs actions prior to rendering the settings form.
246 *
247 * @since 1.9.6
248 */
249 do_action( 'convertkit_settings_base_render_before' );
250
251 do_settings_sections( $this->settings_key );
252
253 settings_fields( $this->settings_key );
254
255 if ( ! $this->save_disabled ) {
256 submit_button();
257 }
258
259 /**
260 * Performs actions after rendering of the settings form.
261 *
262 * @since 1.9.6
263 */
264 do_action( 'convertkit_settings_base_render_after' );
265
266 }
267
268 /**
269 * Outputs opening .metabox-holder and .postbox container div elements,
270 * used before beginning a setting screen's output.
271 *
272 * @since 2.0.0
273 */
274 public function render_container_start() {
275
276 echo wp_kses(
277 $this->get_render_container_start(),
278 convertkit_kses_allowed_html()
279 );
280
281 }
282
283 /**
284 * Outputs closing .metabox-holder and .postbox container div elements,
285 * used after finishing a setting screen's output.
286 *
287 * @since 2.0.0
288 */
289 public function render_container_end() {
290
291 echo wp_kses(
292 $this->get_render_container_end(),
293 convertkit_kses_allowed_html()
294 );
295
296 }
297
298 /**
299 * Returns opening .metabox-holder and .postbox container div elements,
300 * used before beginning a section of a settings screen output.
301 *
302 * @since 2.7.1
303 */
304 public function get_render_container_start() {
305
306 return '<div class="metabox-holder"><div class="postbox ' . sanitize_html_class( $this->is_beta ? 'convertkit-beta' : '' ) . '">';
307
308 }
309
310 /**
311 * Returns closing .metabox-holder and .postbox container div elements,
312 * used after finishing a section of a settings screen output.
313 *
314 * @since 2.7.1
315 */
316 public function get_render_container_end() {
317
318 return '</div></div>';
319
320 }
321
322 /**
323 * Redirects to the settings screen.
324 *
325 * @since 2.2.9
326 */
327 public function redirect() {
328
329 wp_safe_redirect(
330 add_query_arg(
331 array(
332 'page' => '_wp_convertkit_settings',
333 'tab' => $this->name,
334 ),
335 'options-general.php'
336 )
337 );
338 exit();
339
340 }
341
342 /**
343 * Redirects to the settings screen with an error notice key.
344 *
345 * The function maybe_output_notices() will then output the translated error notice
346 * based on the supplied key.
347 *
348 * @since 2.5.1
349 *
350 * @param string $error The error notice key, registered using `convertkit_settings_base_register_notices`.
351 */
352 public function redirect_with_error_notice( $error ) {
353
354 wp_safe_redirect(
355 add_query_arg(
356 array(
357 'page' => '_wp_convertkit_settings',
358 'tab' => $this->name,
359 'error' => $error,
360 ),
361 'options-general.php'
362 )
363 );
364 exit();
365
366 }
367
368 /**
369 * Redirects to the settings screen with the verbose error description.
370 *
371 * @since 2.5.1
372 *
373 * @param string $error_description The error description.
374 */
375 public function redirect_with_error_description( $error_description ) {
376
377 wp_safe_redirect(
378 add_query_arg(
379 array(
380 'page' => '_wp_convertkit_settings',
381 'tab' => $this->name,
382 'error_description' => $error_description,
383 ),
384 'options-general.php'
385 )
386 );
387 exit();
388
389 }
390
391 /**
392 * Redirects to the settings screen with a success notice key.
393 *
394 * The function maybe_output_notices() will then output the translated success notice
395 * based on the supplied key.
396 *
397 * @since 2.5.1
398 *
399 * @param string $success The success notice key, registered using `convertkit_settings_base_register_notices`.
400 */
401 public function redirect_with_success_notice( $success ) {
402
403 wp_safe_redirect(
404 add_query_arg(
405 array(
406 'page' => '_wp_convertkit_settings',
407 'tab' => $this->name,
408 'success' => $success,
409 ),
410 'options-general.php'
411 )
412 );
413 exit();
414
415 }
416
417 /**
418 * Outputs the given success message in an inline notice.
419 *
420 * @since 2.0.0
421 *
422 * @param string $success_message Success Message.
423 */
424 public function output_success( $success_message ) {
425
426 ?>
427 <div class="notice notice-success is-dismissible">
428 <p>
429 <?php echo esc_attr( $success_message ); ?>
430 </p>
431 </div>
432 <?php
433
434 }
435
436 /**
437 * Outputs the given error message in an inline notice.
438 *
439 * @since 1.9.6
440 *
441 * @param string $error_message Error Message.
442 */
443 public function output_error( $error_message ) {
444
445 ?>
446 <div class="notice notice-error is-dismissible">
447 <p>
448 <?php echo esc_attr( $error_message ); ?>
449 </p>
450 </div>
451 <?php
452
453 }
454
455 /**
456 * Returns a masked value.
457 *
458 * @since 1.9.6
459 *
460 * @param string $value Value.
461 * @param bool|string $description Description.
462 * @return string Masked Value
463 */
464 public function get_masked_value( $value, $description = false ) {
465
466 $html = sprintf(
467 '<code>%s</code>',
468 str_repeat( '*', strlen( $value ) - 4 ) . substr( $value, - 4 )
469 );
470
471 if ( $description ) {
472 $html .= $this->get_description( $description );
473 }
474
475 return $html;
476
477 }
478
479 /**
480 * Outputs a masked value.
481 *
482 * @since 2.8.5
483 *
484 * @param string $value Value.
485 * @param bool|string $description Description.
486 */
487 public function output_masked_value( $value, $description = false ) {
488
489 $html = sprintf(
490 '<code>%s</code>',
491 str_repeat( '*', strlen( $value ) - 4 ) . substr( $value, - 4 )
492 );
493
494 if ( $description ) {
495 $html .= $this->get_description( $description );
496 }
497
498 echo wp_kses(
499 $html,
500 convertkit_kses_allowed_html()
501 );
502
503 }
504
505 /**
506 * Returns a text field.
507 *
508 * @since 1.9.6
509 *
510 * @param string $name Name.
511 * @param string $value Value.
512 * @param bool|string|array $description Description (false|string|array).
513 * @param bool|array $css_classes CSS Classes (false|array).
514 * @return string HTML Field
515 */
516 public function get_text_field( $name, $value = '', $description = false, $css_classes = false ) {
517
518 $html = sprintf(
519 '<input type="text" class="%s" id="%s" name="%s[%s]" value="%s" />',
520 ( is_array( $css_classes ) ? implode( ' ', $css_classes ) : 'regular-text' ),
521 $name,
522 $this->settings_key,
523 $name,
524 $value
525 );
526
527 return $html . $this->get_description( $description );
528
529 }
530
531 /**
532 * Outputs a text field.
533 *
534 * @since 2.8.5
535 *
536 * @param string $name Name.
537 * @param string $value Value.
538 * @param bool|string|array $description Description (false|string|array).
539 * @param bool|array $css_classes CSS Classes (false|array).
540 */
541 public function output_text_field( $name, $value = '', $description = false, $css_classes = false ) {
542
543 echo wp_kses(
544 $this->get_text_field( $name, $value, $description, $css_classes ),
545 convertkit_kses_allowed_html()
546 );
547
548 }
549
550 /**
551 * Returns a number field.
552 *
553 * @since 2.6.1
554 *
555 * @param string $name Name.
556 * @param string $value Value.
557 * @param int|float $min `min` attribute value.
558 * @param int|float $max `max` attribute value.
559 * @param int|float $step `step` attribute value.
560 * @param bool|string|array $description Description (false|string|array).
561 * @param bool|array $css_classes CSS Classes (false|array).
562 * @return string HTML Field
563 */
564 public function get_number_field( $name, $value = '', $min = 0, $max = 9999, $step = 1, $description = false, $css_classes = false ) {
565
566 $html = sprintf(
567 '<input type="number" class="%s" id="%s" name="%s[%s]" value="%s" min="%s" max="%s" step="%s" />',
568 ( is_array( $css_classes ) ? implode( ' ', $css_classes ) : 'small-text' ),
569 $name,
570 $this->settings_key,
571 $name,
572 $value,
573 $min,
574 $max,
575 $step
576 );
577
578 return $html . $this->get_description( $description );
579
580 }
581
582 /**
583 * Outputs a number field.
584 *
585 * @since 2.8.5
586 *
587 * @param string $name Name.
588 * @param string $value Value.
589 * @param int|float $min `min` attribute value.
590 * @param int|float $max `max` attribute value.
591 * @param int|float $step `step` attribute value.
592 * @param bool|string|array $description Description (false|string|array).
593 * @param bool|array $css_classes CSS Classes (false|array).
594 */
595 public function output_number_field( $name, $value = '', $min = 0, $max = 9999, $step = 1, $description = false, $css_classes = false ) {
596
597 echo wp_kses(
598 $this->get_number_field( $name, $value, $min, $max, $step, $description, $css_classes ),
599 convertkit_kses_allowed_html()
600 );
601
602 }
603
604 /**
605 * Returns a textarea field.
606 *
607 * @since 2.3.5
608 *
609 * @param string $name Name.
610 * @param string $value Value.
611 * @param bool|string|array $description Description (false|string|array).
612 * @param bool|array $css_classes CSS Classes (false|array).
613 * @return string HTML Field
614 */
615 public function get_textarea_field( $name, $value = '', $description = false, $css_classes = false ) {
616
617 $html = sprintf(
618 '<textarea class="%s" id="%s" name="%s[%s]">%s</textarea>',
619 ( is_array( $css_classes ) ? implode( ' ', $css_classes ) : 'regular-text' ),
620 $name,
621 $this->settings_key,
622 $name,
623 $value
624 );
625
626 return $html . $this->get_description( $description );
627
628 }
629
630 /**
631 * Outputs a textarea field.
632 *
633 * @since 2.8.5
634 *
635 * @param string $name Name.
636 * @param string $value Value.
637 * @param bool|string|array $description Description (false|string|array).
638 * @param bool|array $css_classes CSS Classes (false|array).
639 */
640 public function output_textarea_field( $name, $value = '', $description = false, $css_classes = false ) {
641
642 echo wp_kses(
643 $this->get_textarea_field( $name, $value, $description, $css_classes ),
644 convertkit_kses_allowed_html()
645 );
646
647 }
648
649 /**
650 * Returns a date field.
651 *
652 * @since 2.2.8
653 *
654 * @param string $name Name.
655 * @param string $value Value.
656 * @param bool|string|array $description Description (false|string|array).
657 * @param bool|array $css_classes CSS Classes (false|array).
658 * @return string HTML Field
659 */
660 public function get_date_field( $name, $value = '', $description = false, $css_classes = false ) {
661
662 $html = sprintf(
663 '<input type="date" class="%s" id="%s" name="%s[%s]" value="%s" />',
664 ( is_array( $css_classes ) ? implode( ' ', $css_classes ) : 'regular-text' ),
665 $name,
666 $this->settings_key,
667 $name,
668 $value
669 );
670
671 return $html . $this->get_description( $description );
672
673 }
674
675 /**
676 * Outputs a date field.
677 *
678 * @since 2.8.5
679 *
680 * @param string $name Name.
681 * @param string $value Value.
682 * @param bool|string|array $description Description (false|string|array).
683 * @param bool|array $css_classes CSS Classes (false|array).
684 */
685 public function output_date_field( $name, $value = '', $description = false, $css_classes = false ) {
686
687 echo wp_kses(
688 $this->get_date_field( $name, $value, $description, $css_classes ),
689 convertkit_kses_allowed_html()
690 );
691
692 }
693
694 /**
695 * Returns a select dropdown field.
696 *
697 * @since 1.9.6
698 *
699 * @param string $name Name.
700 * @param string $value Value.
701 * @param array $options Options / Choices.
702 * @param bool|string $description Description.
703 * @param bool|array $css_classes <select> CSS class(es).
704 * @param bool|array $attributes <select> attributes.
705 * @return string HTML Select Field
706 */
707 public function get_select_field( $name, $value = '', $options = array(), $description = false, $css_classes = false, $attributes = false ) {
708
709 // Build opening <select> tag.
710 $html = sprintf(
711 '<select id="%s" name="%s[%s]" class="%s" size="1" %s>',
712 $this->settings_key . '_' . $name,
713 $this->settings_key,
714 $name,
715 ( is_array( $css_classes ) ? implode( ' ', $css_classes ) : '' ),
716 ( is_array( $attributes ) ? $this->array_to_attributes( $attributes ) : '' )
717 );
718
719 // Build <option> tags.
720 foreach ( $options as $option => $label ) {
721 $html .= sprintf(
722 '<option value="%s"%s>%s</option>',
723 $option,
724 selected( $value, $option, false ),
725 $label
726 );
727 }
728
729 // Close <select>.
730 $html .= '</select>';
731
732 // If no description exists, just return the select field.
733 if ( empty( $description ) ) {
734 return $html;
735 }
736
737 // Return select field with description appended to it.
738 return $html . $this->get_description( $description );
739
740 }
741
742 /**
743 * Outputs a select dropdown field.
744 *
745 * @since 2.8.5
746 *
747 * @param string $name Name.
748 * @param string $value Value.
749 * @param array $options Options / Choices.
750 * @param bool|string $description Description.
751 * @param bool|array $css_classes <select> CSS class(es).
752 * @param bool|array $attributes <select> attributes.
753 */
754 public function output_select_field( $name, $value = '', $options = array(), $description = false, $css_classes = false, $attributes = false ) {
755
756 echo wp_kses(
757 $this->get_select_field( $name, $value, $options, $description, $css_classes, $attributes ),
758 convertkit_kses_allowed_html()
759 );
760
761 }
762
763 /**
764 * Returns a checkbox field.
765 *
766 * @since 1.9.6
767 *
768 * @param string $name Name.
769 * @param string $value Value.
770 * @param bool $checked Should checkbox be checked/ticked.
771 * @param bool|string $label Label.
772 * @param bool|string|array $description Description.
773 * @param bool|array $css_classes CSS class(es).
774 * @return string HTML Checkbox
775 */
776 public function get_checkbox_field( $name, $value, $checked = false, $label = '', $description = false, $css_classes = false ) {
777
778 $html = '';
779
780 if ( $label ) {
781 $html .= sprintf(
782 '<label for="%s">',
783 $name
784 );
785 }
786
787 $html .= sprintf(
788 '<input type="checkbox" id="%s" name="%s[%s]" class="%s" value="%s" %s />',
789 $name,
790 $this->settings_key,
791 $name,
792 ( is_array( $css_classes ) ? implode( ' ', $css_classes ) : '' ),
793 $value,
794 ( $checked ? ' checked' : '' )
795 );
796
797 if ( $label ) {
798 $html .= sprintf(
799 '%s</label>',
800 $label
801 );
802 }
803
804 // If no description exists, just return the field.
805 if ( empty( $description ) ) {
806 return $html;
807 }
808
809 // Return field with description appended to it.
810 return $html . $this->get_description( $description );
811
812 }
813
814 /**
815 * Outputs a checkbox field.
816 *
817 * @since 2.8.5
818 *
819 * @param string $name Name.
820 * @param string $value Value.
821 * @param bool $checked Should checkbox be checked/ticked.
822 * @param bool|string $label Label.
823 * @param bool|string|array $description Description.
824 * @param bool|array $css_classes CSS class(es).
825 */
826 public function output_checkbox_field( $name, $value, $checked = false, $label = '', $description = false, $css_classes = false ) {
827
828 echo wp_kses(
829 $this->get_checkbox_field( $name, $value, $checked, $label, $description, $css_classes ),
830 convertkit_kses_allowed_html()
831 );
832
833 }
834
835 /**
836 * Returns a link button.
837 *
838 * @since 2.8.5
839 *
840 * @param string $url URL.
841 * @param string $label Button Label.
842 * @param bool|array $css_classes CSS class(es).
843 * @return string HTML Link Button
844 */
845 public function get_link_button( $url, $label, $css_classes = false ) {
846
847 return sprintf(
848 '<a href="%s" class="button %s">%s</a>',
849 esc_url( $url ),
850 ( is_array( $css_classes ) ? implode( ' ', $css_classes ) : '' ),
851 esc_html( $label )
852 );
853
854 }
855
856 /**
857 * Outputs a link button.
858 *
859 * @since 2.8.5
860 *
861 * @param string $url URL.
862 * @param string $label Button Label.
863 * @param bool|array $css_classes CSS class(es).
864 */
865 public function output_link_button( $url, $label, $css_classes = false ) {
866
867 echo wp_kses(
868 $this->get_link_button( $url, $label, $css_classes ),
869 convertkit_kses_allowed_html()
870 );
871
872 }
873
874 /**
875 * Returns the given text wrapped in a paragraph with the description class.
876 *
877 * @since 1.9.6
878 *
879 * @param bool|string|array $description Description.
880 * @return string HTML Description
881 */
882 public function get_description( $description ) {
883
884 // Return blank string if no description specified.
885 if ( ! $description ) {
886 return '';
887 }
888
889 // Return description in paragraph if a string.
890 if ( ! is_array( $description ) ) {
891 return '<p class="description">' . $description . '</p>';
892 }
893
894 // Return description lines in a paragraph, using breaklines for each description entry in the array.
895 return '<p class="description">' . implode( '<br />', $description ) . '</p>';
896
897 }
898
899 /**
900 * Converts the given key/value array pairs into a HTML attribute="value" string.
901 *
902 * @since 1.9.8.5
903 *
904 * @param array $attributes_array Attributes.
905 * @return string HTML attributes string
906 */
907 private function array_to_attributes( $attributes_array ) {
908
909 $attributes = '';
910 foreach ( $attributes_array as $key => $value ) {
911 $attributes .= esc_attr( $key ) . '="' . esc_attr( $value ) . '" ';
912 }
913
914 return trim( $attributes );
915
916 }
917
918 /**
919 * Sanitizes the settings prior to being saved.
920 *
921 * @since 1.9.6
922 *
923 * @param array $settings Submitted Settings Fields.
924 * @return array Sanitized Settings with Defaults
925 */
926 public function sanitize_settings( $settings ) {
927
928 // Merge settings with defaults.
929 $updated_settings = wp_parse_args( $settings, $this->settings->get_defaults() );
930
931 /**
932 * Performs actions prior to settings being saved.
933 *
934 * @since 2.2.8
935 */
936 do_action( 'convertkit_settings_base_sanitize_settings', $this->name, $updated_settings );
937
938 // Return settings to be saved.
939 return $updated_settings;
940
941 }
942
943 /**
944 * Outputs the Intercom help widget in the footer of the Plugin's settings screens.
945 *
946 * @since 2.7.2
947 */
948 public function output_intercom() {
949
950 convertkit_output_intercom_messenger();
951
952 }
953
954 }
955