PluginProbe
Elementor Website Builder – more than just a page builder / 4.1.0-dev1
Elementor Website Builder – more than just a page builder v4.1.0-dev1
4.3.0-beta2 4.3.0-beta1 4.2.4 4.2.3 4.2.2 4.2.1 4.2.0 4.1.5 4.2.0-beta2 4.2.0-dev2 4.2.0-beta1 4.1.4 4.1.3 4.1.2 4.1.1 4.1.0 4.1.0-beta3 4.1.0-dev3 4.0.9 4.1.0-beta2 4.1.0-dev2 4.0.8 4.1.0-beta1 4.1.0-dev1 4.0.7 All 451 releases
elementor / includes / settings / settings-page.php

settings-page.php in Elementor Website Builder – more than just a page builder 4.1.0-dev1, at includes/settings/settings-page.php

464 lines 11.2 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 namespace Elementor;
3
4 use Elementor\Plugin;
5
6 if ( ! defined( 'ABSPATH' ) ) {
7 exit; // Exit if accessed directly.
8 }
9
10 /**
11 * Elementor settings page.
12 *
13 * An abstract class that provides the needed properties and methods to handle
14 * WordPress dashboard settings pages in inheriting classes.
15 *
16 * @since 1.0.0
17 * @abstract
18 */
19 abstract class Settings_Page {
20
21 /**
22 * Settings page ID.
23 */
24 const PAGE_ID = '';
25
26 /**
27 * Tabs.
28 *
29 * Holds the settings page tabs, sections and fields.
30 *
31 * @access private
32 *
33 * @var array
34 */
35 private $tabs;
36
37 /**
38 * Create tabs.
39 *
40 * Return the settings page tabs, sections and fields.
41 *
42 * @since 1.5.0
43 * @access protected
44 * @abstract
45 */
46 abstract protected function create_tabs();
47
48 /**
49 * Get settings page title.
50 *
51 * Retrieve the title for the settings page.
52 *
53 * @since 1.5.0
54 * @access protected
55 * @abstract
56 */
57 abstract protected function get_page_title();
58
59 /**
60 * Get settings page URL.
61 *
62 * Retrieve the URL of the settings page.
63 *
64 * @since 1.5.0
65 * @access public
66 * @static
67 *
68 * @return string Settings page URL.
69 */
70 final public static function get_url() {
71 return admin_url( 'admin.php?page=' . static::PAGE_ID );
72 }
73
74 /**
75 * Get settings tab URL.
76 *
77 * Retrieve the URL of a specific tab in the settings page.
78 *
79 * @since 3.23.0
80 * @access public
81 * @static
82 *
83 * @param string $tab_id The ID of the settings tab.
84 *
85 * @return string Settings tab URL.
86 */
87 final public static function get_settings_tab_url( $tab_id ): string {
88 return admin_url( "admin.php?page=elementor-settings#tab-$tab_id" );
89 }
90
91 /**
92 * Settings page constructor.
93 *
94 * Initializing Elementor settings page.
95 *
96 * @since 1.5.0
97 * @access public
98 */
99 public function __construct() {
100 // PHPCS - The user data is not used.
101 if ( ! empty( $_POST['option_page'] ) && static::PAGE_ID === $_POST['option_page'] ) { // phpcs:ignore WordPress.Security.NonceVerification.Missing
102 add_action( 'admin_init', [ $this, 'register_settings_fields' ] );
103 }
104 }
105
106 /**
107 * Get tabs.
108 *
109 * Retrieve the settings page tabs, sections and fields.
110 *
111 * @since 1.5.0
112 * @access public
113 *
114 * @return array Settings page tabs, sections and fields.
115 */
116 final public function get_tabs() {
117 $this->ensure_tabs();
118
119 return $this->tabs;
120 }
121
122 /**
123 * Add tab.
124 *
125 * Register a new tab to a settings page.
126 *
127 * @since 1.5.0
128 * @access public
129 *
130 * @param string $tab_id Tab ID.
131 * @param array $tab_args Optional. Tab arguments. Default is an empty array.
132 */
133 final public function add_tab( $tab_id, array $tab_args = [] ) {
134 $this->ensure_tabs();
135
136 if ( isset( $this->tabs[ $tab_id ] ) ) {
137 // Don't override an existing tab
138 return;
139 }
140
141 if ( ! isset( $tab_args['sections'] ) ) {
142 $tab_args['sections'] = [];
143 }
144
145 $this->tabs[ $tab_id ] = $tab_args;
146 }
147
148 /**
149 * Add section.
150 *
151 * Register a new section to a tab.
152 *
153 * @since 1.5.0
154 * @access public
155 *
156 * @param string $tab_id Tab ID.
157 * @param string $section_id Section ID.
158 * @param array $section_args Optional. Section arguments. Default is an
159 * empty array.
160 */
161 final public function add_section( $tab_id, $section_id, array $section_args = [] ) {
162 $this->ensure_tabs();
163
164 if ( ! isset( $this->tabs[ $tab_id ] ) ) {
165 // If the requested tab doesn't exists, use the first tab
166 $tab_id = key( $this->tabs );
167 }
168
169 if ( isset( $this->tabs[ $tab_id ]['sections'][ $section_id ] ) ) {
170 // Don't override an existing section
171 return;
172 }
173
174 if ( ! isset( $section_args['fields'] ) ) {
175 $section_args['fields'] = [];
176 }
177
178 $this->tabs[ $tab_id ]['sections'][ $section_id ] = $section_args;
179 }
180
181 /**
182 * Add field.
183 *
184 * Register a new field to a section.
185 *
186 * @since 1.5.0
187 * @access public
188 *
189 * @param string $tab_id Tab ID.
190 * @param string $section_id Section ID.
191 * @param string $field_id Field ID.
192 * @param array $field_args Field arguments.
193 */
194 final public function add_field( $tab_id, $section_id, $field_id, array $field_args ) {
195 $this->ensure_tabs();
196
197 if ( ! isset( $this->tabs[ $tab_id ] ) ) {
198 // If the requested tab doesn't exists, use the first tab
199 $tab_id = key( $this->tabs );
200 }
201
202 if ( ! isset( $this->tabs[ $tab_id ]['sections'][ $section_id ] ) ) {
203 // If the requested section doesn't exists, use the first section
204 $section_id = key( $this->tabs[ $tab_id ]['sections'] );
205 }
206
207 if ( isset( $this->tabs[ $tab_id ]['sections'][ $section_id ]['fields'][ $field_id ] ) ) {
208 // Don't override an existing field
209 return;
210 }
211
212 $this->tabs[ $tab_id ]['sections'][ $section_id ]['fields'][ $field_id ] = $field_args;
213 }
214
215 /**
216 * Add fields.
217 *
218 * Register multiple fields to a section.
219 *
220 * @since 1.5.0
221 * @access public
222 *
223 * @param string $tab_id Tab ID.
224 * @param string $section_id Section ID.
225 * @param array $fields {
226 * An array of fields.
227 *
228 * @type string $field_id Field ID.
229 * @type array $field_args Field arguments.
230 * }
231 */
232 final public function add_fields( $tab_id, $section_id, array $fields ) {
233 foreach ( $fields as $field_id => $field_args ) {
234 $this->add_field( $tab_id, $section_id, $field_id, $field_args );
235 }
236 }
237
238 /**
239 * Register settings fields.
240 *
241 * In each tab register his inner sections, and in each section register his
242 * inner fields.
243 *
244 * @since 1.5.0
245 * @access public
246 */
247 final public function register_settings_fields() {
248 $controls_class_name = __NAMESPACE__ . '\Settings_Controls';
249
250 $tabs = $this->get_tabs();
251
252 foreach ( $tabs as $tab_id => $tab ) {
253
254 foreach ( $tab['sections'] as $section_id => $section ) {
255 $full_section_id = 'elementor_' . $section_id . '_section';
256
257 $label = isset( $section['label'] ) ? $section['label'] : '';
258
259 $section_callback = isset( $section['callback'] ) ? $section['callback'] : '__return_empty_string';
260
261 add_settings_section( $full_section_id, $label, $section_callback, static::PAGE_ID );
262
263 foreach ( $section['fields'] as $field_id => $field ) {
264 $full_field_id = ! empty( $field['full_field_id'] ) ? $field['full_field_id'] : 'elementor_' . $field_id;
265
266 $field['field_args']['id'] = $full_field_id;
267
268 $field_classes = [ $full_field_id ];
269
270 if ( ! empty( $field['class'] ) ) {
271 $field_classes[] = $field['field_args']['class'];
272 }
273
274 $field['field_args']['class'] = implode( ' ', $field_classes );
275
276 if ( ! isset( $field['render'] ) ) {
277 $field['render'] = [ $controls_class_name, 'render' ];
278 }
279
280 add_settings_field(
281 $full_field_id,
282 isset( $field['label'] ) ? $field['label'] : '',
283 $field['render'],
284 static::PAGE_ID,
285 $full_section_id,
286 $field['field_args']
287 );
288
289 $setting_args = [];
290
291 if ( ! empty( $field['setting_args'] ) ) {
292 $setting_args = $field['setting_args'];
293 }
294
295 register_setting( static::PAGE_ID, $full_field_id, $setting_args );
296 }
297 }
298 }
299 }
300
301 /**
302 * Display settings page.
303 *
304 * Output the content for the settings page.
305 *
306 * @since 1.5.0
307 * @access public
308 */
309 public function display_settings_page() {
310 $this->register_settings_fields();
311
312 $tabs = $this->get_tabs();
313 ?>
314 <div class="wrap">
315 <h1 class="wp-heading-inline"><?php echo esc_html( $this->get_page_title() ); ?></h1>
316 <div id="elementor-settings-tabs-wrapper" class="nav-tab-wrapper">
317 <?php
318 foreach ( $tabs as $tab_id => $tab ) {
319 if ( ! $this->should_render_tab( $tab ) ) {
320 continue;
321 }
322
323 $active_class = '';
324
325 if ( 'general' === $tab_id ) {
326 $active_class = ' nav-tab-active';
327 }
328
329 $sanitized_tab_id = esc_attr( $tab_id );
330 $sanitized_tab_label = esc_html( $tab['label'] );
331
332 // PHPCS - Escaped the relevant strings above.
333 echo "<a id='elementor-settings-tab-{$sanitized_tab_id}' class='nav-tab{$active_class}' href='#tab-{$sanitized_tab_id}'>{$sanitized_tab_label}</a>"; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
334 }
335 ?>
336 </div>
337 <form id="elementor-settings-form" method="post" action="options.php">
338 <?php
339 settings_fields( static::PAGE_ID );
340
341 foreach ( $tabs as $tab_id => $tab ) {
342 if ( ! $this->should_render_tab( $tab ) ) {
343 continue;
344 }
345
346 $active_class = '';
347
348 if ( 'general' === $tab_id ) {
349 $active_class = ' elementor-active';
350 }
351
352 $sanitized_tab_id = esc_attr( $tab_id );
353
354 // PHPCS - $active_class is a non-dynamic string and $sanitized_tab_id is escaped above.
355 echo "<div id='tab-{$sanitized_tab_id}' class='elementor-settings-form-page{$active_class}'>"; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
356
357 foreach ( $tab['sections'] as $section_id => $section ) {
358 if ( ! $this->should_render_section( $section ) ) {
359 continue;
360 }
361
362 $full_section_id = 'elementor_' . $section_id . '_section';
363
364 if ( ! empty( $section['label'] ) ) {
365 echo '<h2>' . esc_html( $section['label'] ) . '</h2>';
366 }
367
368 if ( ! empty( $section['callback'] ) ) {
369 $section['callback']();
370 }
371
372 echo '<table class="form-table">';
373
374 do_settings_fields( static::PAGE_ID, $full_section_id );
375
376 echo '</table>';
377 }
378
379 echo '</div>';
380 }
381
382 submit_button( __( 'Save Changes', 'elementor' ), 'primary', 'submit', true, [ 'data-id' => 'elementor-settings-button-save-changes' ] );
383 ?>
384 </form>
385 </div><!-- /.wrap -->
386 <?php
387 }
388
389 public function get_usage_fields() {
390 return [
391 'allow_tracking' => [
392 'label' => esc_html__( 'Data Sharing', 'elementor' ),
393 'field_args' => [
394 'type' => 'checkbox',
395 'value' => 'yes',
396 'default' => '',
397 'sub_desc' => sprintf(
398 '%1$s <a href="https://go.elementor.com/usage-data-tracking/" target="_blank">%2$s</a>',
399 esc_html__( 'Become a super contributor by helping us understand how you use our service to enhance your experience and improve our product.', 'elementor' ),
400 esc_html__( 'Learn more', 'elementor' )
401 ),
402 ],
403 'setting_args' => [ __NAMESPACE__ . '\Tracker', 'check_for_settings_optin' ],
404 ],
405 ];
406 }
407
408 /**
409 * Ensure tabs.
410 *
411 * Make sure the settings page has tabs before inserting any new sections or
412 * fields.
413 *
414 * @since 1.5.0
415 * @access private
416 */
417 private function ensure_tabs() {
418 if ( null === $this->tabs ) {
419 $this->tabs = $this->create_tabs();
420
421 $page_id = static::PAGE_ID;
422
423 /**
424 * After create settings.
425 *
426 * Fires after the settings are created in Elementor admin page.
427 *
428 * The dynamic portion of the hook name, `$page_id`, refers to the current page ID.
429 *
430 * @since 1.0.0
431 *
432 * @param Settings_Page $this The settings page.
433 */
434 do_action( "elementor/admin/after_create_settings/{$page_id}", $this );
435 }
436 }
437
438 /**
439 * Should it render the settings tab
440 *
441 * @param array $tab
442 *
443 * @return bool
444 */
445 private function should_render_tab( $tab ) {
446 // BC - When 'show_if' prop is not exists, it actually should render the tab.
447 return ! empty( $tab['sections'] ) && ( ! isset( $tab['show_if'] ) || $tab['show_if'] );
448 }
449
450 /**
451 * Should it render the settings section
452 *
453 * @param array $section
454 *
455 * Since 3.19.0
456 *
457 * @return bool
458 */
459 private function should_render_section( $section ) {
460 // BC - When 'show_if' prop is not exists, it actually should render the section.
461 return ! isset( $section['show_if'] ) || $section['show_if'];
462 }
463 }
464