PluginProbe
Booking Calendar / 11.4
Booking Calendar v11.4
11.8.1 11.8 11.7 11.6.1 11.6 11.5 11.4.3 11.4.2 11.4.1 11.4 11.3 11.2.1 11.2 11.1 11.0 10.15.7 10.15.6 10.1.3 10.10 10.10.1 10.10.2 10.11 10.11.2 10.11.3 10.11.4 All 201 releases
booking / includes / ui_settings / class-page-structure.php

class-page-structure.php in Booking Calendar 11.4, at includes/ui_settings/class-page-structure.php

843 lines 30.8 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Page Structure in Admin Panel
4 *
5 * @version 1.2
6 * @package Any
7 * @category Page Structure in Admin Panel
8 * @author wpdevelop
9 *
10 * @web-site https://wpbookingcalendar.com/
11 * @email info@wpbookingcalendar.com
12 *
13 * @modified 2024-12-23, 2015-11-02
14 */
15
16 if ( ! defined( 'ABSPATH' ) ) {
17 exit; // Exit, if accessed directly.
18 }
19
20 /**
21 * == All Page Parameters ==
22 *
23 * TODO Refactorig: Continue work with description of the: List of all parameters, that possible to use in public function tabs() { ... }
24
25 'is_default_full_screen' => false, // true | false. Default: false.
26 'is_force_full_screen' => false, // true | false. Default: false.
27 'right_vertical_sidebar__is_show' => false, // true | false. Default: false.
28 'right_vertical_sidebar__default_view_mode' => 'max', // '' | 'min' | 'compact' | 'max' | 'none'. Default: ''.
29 'left_navigation__default_view_mode' => 'max', // '' | 'min' | 'compact' | 'max' | 'none'. Default: ''.
30 'left_navigation__force_view_mode' => '', // '' | 'min' | 'compact' | 'max' | 'none'. Default: ''.
31 'right_vertical_sidebar_compact__is_show' => false, // true | false. Default: false.
32
33 // TODO: recheck functionality and ability to use:
34
35 'is_show_top_path' => true, // true | false. By default value is: true.
36 'is_show_top_navigation' => false, // true | false. By default value is: false.
37 'title' => __( 'Booking Form Builder', 'booking' ), // Title of TAB //FixIn: 9.8.15.2.2.
38 'hint' => __( 'Define available days', 'booking' ), // Hint.
39 'page_title' => __( 'Booking Form Builder', 'booking' ), // Title of Page.
40 'link' => '', // Can be skiped, then generated link based on Page and Tab tags. Or can be extenral link.
41 'position' => '', // 'left' / 'right' / ''.
42 'css_classes' => '', // CSS c l a s s(es).
43 'icon' => '', // Icon - link to the real PNG img.
44 'font_icon' => 'wpbc_icn_flip_x0 wpbc-bi-input-cursor-text', // 'wpbc_icn_free_cancellation' // CSS definition of forn Icon.
45 'font_icon_right' => 'wpbc-bi-asterisk',
46 'default' => false, // Is this tab activated by default or not: true || false.
47 'disabled' => false, // Is this tab disbaled: true || false.
48 'hided' => false, // Is this tab hided: true || false.
49 'subtabs' => array(),
50 'folder_style' => 'order:11;',
51
52 */
53
54
55 /**
56 * Define Settings Page Structure
57 */
58 abstract class WPBC_Page_Structure extends WPBC_Menu_Structure {
59
60 // FixIn: 11.0.0.1.
61
62 /**
63 * Constructor
64 */
65 public function __construct() {
66
67 parent::__construct();
68
69 // This Hook fire in the class WPBC_Admin_Menus for showing page content of specific menu.
70 add_action( 'wpbc_page_structure_show', array( $this, 'content_structure' ) );
71
72 add_filter( 'admin_body_class', array( $this, 'wpbc_add_admin_body_class' ) );
73 }
74
75
76 /**
77 * Set the wpbc_admin class to body.
78 *
79 * @param bool $classes Body classes.
80 *
81 * @return array
82 */
83 public function wpbc_add_admin_body_class( $classes ) {
84
85
86 if ( $this->is_page_activated() ) {
87 $classes .= ' wpbc_admin';
88 }
89
90 return $classes;
91 }
92
93
94 // -----------------------------------------------------------------------------------------------------------------
95 // Abstract Methods
96 // -----------------------------------------------------------------------------------------------------------------
97 // FixIn: 10.11.4.4. Removed abstarct classes that exists in the parent class.
98
99 /**
100 * Child classes ovveride it for auto update / save options in main form
101 *
102 * @return void
103 */
104 public function maybe_update() {}
105
106
107 /**
108 * Child classes ovveride -- show vertical "Right Sidebar Content".
109 * // FixIn: 10.14.1.3.
110 *
111 * @return void
112 */
113 public function right_sidebar_content(){}
114
115
116
117 /**
118 * Child classes ovveride -- show vertical "Right Sidebar Content - Compact".
119 * // FixIn: 10.14.1.3.
120 *
121 * @return void
122 */
123 public function right_sidebar_compact_content(){}
124
125
126 // -----------------------------------------------------------------------------------------------------------------
127 // C O N T E N T
128 // -----------------------------------------------------------------------------------------------------------------
129
130 /**
131 * General Page Structure
132 *
133 * @param string $page_tag - its the same that return $this->in_page ().
134 */
135 public function content_structure( $page_tag ) {
136
137 // -------------------------------------------------------------------------------------------------------------
138 // Checking if this page - A C T I V E
139 // -------------------------------------------------------------------------------------------------------------
140 if ( ! $this->is_page_activated() ) {
141 return false;
142 }
143
144 $active_page_tab = $this->get_active__tab__tag();
145 $active_page_subtab = $this->get_active__subtab__tag();
146
147 // Fires Before showing settings Content page. Used in MultiUser version for blocking access to some pages.
148 $is_show_this_page = apply_filters( 'wpbc_before_showing_settings_page_is_show_page', true, $page_tag, $active_page_tab, $active_page_subtab );
149 if ( false === $is_show_this_page ) {
150 return false;
151 }
152
153 $this->update_nav_tabs_structure( $page_tag, $active_page_tab, $active_page_subtab );
154
155 // -------------------------------------------------------------------------------------------------------------
156 // -- U p d a t e --
157 // -------------------------------------------------------------------------------------------------------------
158 $this->maybe_update();
159
160 // -------------------------------------------------------------------------------------------------------------
161 // -- T e m p l a t e --
162 // -------------------------------------------------------------------------------------------------------------
163
164 // Hook: Fires Before showing settings Content page.
165 do_action( 'wpbc_before_settings_content', $page_tag, $active_page_tab, $active_page_subtab );
166
167
168 $template_params_arr = array(
169 'active_page' => $page_tag,
170 'active_tab' => $active_page_tab,
171 'active_subtab' => $active_page_subtab,
172 'page_structure_obj' => $this,
173 );
174 $settings_templates = new WPBC_Settings_Page_Parts( $template_params_arr );
175
176 // ---------------------------------------------------------------------------------------------------------
177 // Template Header
178 // ---------------------------------------------------------------------------------------------------------
179 $settings_templates->template_header();
180
181 wp_nonce_field( 'wpbc_ajax_admin_nonce', 'wpbc_admin_panel_nonce', true, true ); // Nonce.
182
183 // ---------------------------------------------------------------------------------------------------------
184 // Content.
185 // ---------------------------------------------------------------------------------------------------------
186 if ( ( isset( $this->current_page_params['subtab'] ) ) && ( isset( $this->current_page_params['subtab']['content'] ) ) ) {
187 call_user_func( array( $this, $this->current_page_params['subtab']['content'] ) );
188 } elseif ( ( isset( $this->current_page_params['tab'] ) ) && ( isset( $this->current_page_params['tab']['content'] ) ) ) {
189 call_user_func( array( $this, $this->current_page_params['tab']['content'] ) );
190 } else {
191 $this->content();
192 }
193
194 do_action( 'wpbc_show_settings_content', $page_tag, $active_page_tab, $active_page_subtab ); // Hook.
195
196 // ---------------------------------------------------------------------------------------------------------
197 // Template Footer
198 // ---------------------------------------------------------------------------------------------------------
199 $settings_templates->template_footer();
200
201 do_action( 'wpbc_after_settings_content', $page_tag, $active_page_tab, $active_page_subtab ); // Hook: Fires After showing settings Content page.
202 }
203
204
205 // -----------------------------------------------------------------------------------------------------------------
206 // == Support ==
207 // -----------------------------------------------------------------------------------------------------------------
208
209 /**
210 * Update structure of self::$nav_tabs with 'is_active' and 'url' parameters.
211 * We can do this here, because this function executed at step of showing content, and we know about all the structure of the menus, already.
212 *
213 * Based on URL: /admin.php?page=wpbc-settings&tab=email&subtab=new-visitor
214 *
215 * @param string $page_tag - 'wpbc-settings'.
216 * @param string $active_page_tab - 'email'.
217 * @param string $active_page_subtab - 'new-visitor'.
218 *
219 * @return bool
220 */
221 private function update_nav_tabs_structure( $page_tag, $active_page_tab, $active_page_subtab ) {
222
223 if ( empty( self::$nav_tabs ) ) {
224 return false;
225 }
226
227 // Menu Pages [Bookings, Resources, Prices, Settings ].
228 foreach ( self::$nav_tabs as $nav_page_tag => $nav_page_arr ) {
229
230 // Tabs [ General, Emails, ... ].
231 foreach ( self::$nav_tabs[ $nav_page_tag ] as $nav_tab_tag => $nav_tab_arr ) {
232
233 self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['is_active'] = false;
234 self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['url'] = ( ! empty( self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['link'] ) )
235 ? self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['link']
236 : $this->get_tab_url( $nav_page_tag, $nav_tab_tag );
237 // Inside of this page 'wpbc-settings' ?
238 if ( $nav_page_tag === $page_tag ) {
239
240 // Tab not selected -> clicked on Left menu only, but this is 'DEFAULT' TAB, so true.
241 if ( ( empty( $active_page_tab ) ) && ( ! empty( self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['default'] ) ) ) {
242 self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['is_active'] = true;
243 }
244
245 // Page and Tab clicked !
246 if ( ( $nav_page_tag === $page_tag ) && ( $active_page_tab === $nav_tab_tag ) ) {
247 self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['is_active'] = true;
248 }
249 }
250
251 if ( ! empty( self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['subtabs'] ) ) {
252 // SubTabs e.g.: [ "New booking", "Approved", ... ].
253 foreach ( self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['subtabs'] as $nav_subtab_tag => $nav_subtab_arr ) {
254
255 self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['subtabs'][ $nav_subtab_tag ]['is_active'] = false;
256
257 self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['subtabs'][ $nav_subtab_tag ]['url'] = ( ! empty( self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['subtabs'][ $nav_subtab_tag ]['link'] ) )
258 ? self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['subtabs'][ $nav_subtab_tag ]['link']
259 : $this->get_tab_url( $nav_page_tag, $nav_tab_tag, $nav_subtab_tag );
260 // We know that this TAB is active.
261 if ( ! empty( self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['is_active'] ) ) {
262
263 // SubTab not selected -> clicked on Left menu and Tab only, but not clicked on submenu (e.g. Stripe or "approved email") and if we have this is 'DEFAULT' TAB, so true.
264 if ( ( empty( $active_page_subtab ) ) && ( ! empty( self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['subtabs'][ $nav_subtab_tag ]['default'] ) ) ) {
265 self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['subtabs'][ $nav_subtab_tag ]['is_active'] = true;
266 }
267
268 // Page and SubTab clicked !
269 if ( $active_page_subtab === $nav_subtab_tag ) {
270 self::$nav_tabs[ $nav_page_tag ][ $nav_tab_tag ]['subtabs'][ $nav_subtab_tag ]['is_active'] = true;
271 }
272 }
273 }
274 }
275 }
276 }
277 return true;
278 }
279
280 /**
281 * Get current active TAB 'Tag'
282 *
283 * @return mixed|string
284 */
285 protected function get_active__tab__tag() {
286
287 $active_page_tab = '';
288
289 if ( ( isset( $this->current_page_params['tab'] ) ) && ( ! empty( $this->current_page_params['tab']['tag'] ) ) ) {
290 $active_page_tab = $this->current_page_params['tab']['tag'];
291 }
292
293 return $active_page_tab;
294 }
295
296 /**
297 * Get current active SubTAB 'Tag'
298 *
299 * @return mixed|string
300 */
301 protected function get_active__subtab__tag() {
302
303 $active_page_subtab = '';
304
305 if ( ( isset( $this->current_page_params['subtab'] ) ) && ( ! empty( $this->current_page_params['subtab']['tag'] ) ) ) {
306 $active_page_subtab = $this->current_page_params['subtab']['tag'];
307 }
308
309 return $active_page_subtab;
310 }
311
312 /**
313 * Get Option. Check if this defined in Tabs or Subtabs array Otherwise return false.
314 *
315 * @param string $option_name - name of the option, like 'is_use_new_settings_skin'.
316 *
317 * @return false|mixed
318 *
319 * Example: $is_use_new_settings_skin = $this->is_use_option__in_subtabs( 'is_use_new_settings_skin' );
320 */
321 public function is_use_option__in_subtabs_or_tabs( $option_name ) {
322
323 // Check if this otion defined in tabs or 'subtabs' ?
324 $is_use_option = $this->is_use_option__in_subtabs( $option_name );
325
326 // If this option not defined in 'subtabs', then we check it in 'tab'.
327 if ( false === $is_use_option ) {
328 $is_use_option = ( $this->is_use_option__in_tabs( $option_name ) );
329 }
330
331 return $is_use_option;
332 }
333
334 /**
335 * Get Option. Check if this defined in subtabs array Otherwise return false.
336 *
337 * @param string $option_name - name of the option, like 'is_use_new_settings_skin'.
338 *
339 * @return false|mixed
340 *
341 * Example: $is_use_new_settings_skin = $this->is_use_option__in_subtabs( 'is_use_new_settings_skin' );
342 */
343 public function is_use_option__in_subtabs( $option_name ) {
344
345 // Check if this otion defined in subtabs ?
346 $is_use_option = ( ( isset( $this->current_page_params['subtab'] ) ) && ( ! empty( $this->current_page_params['subtab'][ $option_name ] ) ) )
347 ? $this->current_page_params['subtab'][ $option_name ]
348 : false;
349
350 return $is_use_option;
351 }
352
353 /**
354 * Get Option. Check if this defined in btabs array Otherwise return false.
355 *
356 * @param string $option_name - name of the option, like 'is_use_new_settings_skin'.
357 *
358 * @return false|mixed
359 *
360 * Example: $is_use_new_settings_skin = $this->is_use_option__in_subtabs( 'is_use_new_settings_skin' );
361 */
362 public function is_use_option__in_tabs( $option_name ) {
363
364 // Check if this otion defined in subtabs ?
365 $is_use_option = ( ( isset( $this->current_page_params['tab'] ) ) && ( ! empty( $this->current_page_params['tab'][ $option_name ] ) ) )
366 ? $this->current_page_params['tab'][ $option_name ]
367 : false;
368
369 return $is_use_option;
370 }
371
372 /**
373 * Get allowed left sidebar mode.
374 *
375 * @param string $mode Sidebar mode.
376 *
377 * @return string
378 */
379 private function get_valid_left_navigation_mode( $mode ) {
380
381 $mode = strval( $mode );
382 $allowed_modes = array( '', 'min', 'compact', 'max', 'none' );
383
384 return in_array( $mode, $allowed_modes, true ) ? $mode : '';
385 }
386
387 /**
388 * Get page-defined left sidebar mode before user preferences.
389 *
390 * @return string
391 */
392 private function get_page_left_navigation_default_mode() {
393
394 return $this->get_valid_left_navigation_mode( $this->is_use_option__in_subtabs_or_tabs( 'left_navigation__default_view_mode' ) );
395 }
396
397 /**
398 * Get forced left sidebar mode, if the current page must not use the user preference.
399 *
400 * @return string
401 */
402 private function get_forced_left_navigation_mode() {
403
404 return $this->get_valid_left_navigation_mode( $this->is_use_option__in_subtabs_or_tabs( 'left_navigation__force_view_mode' ) );
405 }
406
407 /**
408 * Check whether the current page should save and restore the user left sidebar preference.
409 *
410 * @return bool
411 */
412 public function is_left_navigation_user_mode_enabled() {
413
414 $forced_mode = $this->get_forced_left_navigation_mode();
415
416 if ( ! empty( $forced_mode ) ) {
417 return false;
418 }
419
420 if ( 'none' === $this->get_page_left_navigation_default_mode() ) {
421 return false;
422 }
423
424 return true;
425 }
426
427 /**
428 * Resolve the initial left sidebar mode.
429 *
430 * Forced page mode wins, then the saved user preference, then the page default.
431 *
432 * @return string
433 */
434 public function get_left_navigation_default_view_mode() {
435
436 $forced_mode = $this->get_forced_left_navigation_mode();
437
438 if ( ! empty( $forced_mode ) ) {
439 return $forced_mode;
440 }
441
442 $page_default_mode = $this->get_page_left_navigation_default_mode();
443
444 if ( 'none' === $page_default_mode ) {
445 return 'none';
446 }
447
448 $saved_user_mode = '';
449 if ( class_exists( 'WPBC_User_Custom_Data_Saver' ) ) {
450 $saved_user_mode = WPBC_User_Custom_Data_Saver::get_user_data_value( wpbc_get_current_user_id(), 'left_sidebar_view_mode' );
451 $saved_user_mode = $this->get_valid_left_navigation_mode( $saved_user_mode );
452 }
453
454 if ( ! empty( $saved_user_mode ) && ( 'none' !== $saved_user_mode ) ) {
455 return $saved_user_mode;
456 }
457
458 return $page_default_mode;
459 }
460
461 /**
462 * Check whether the current page should open in fullscreen.
463 *
464 * Forced page mode wins, then the saved user preference, then the page default.
465 *
466 * @return bool
467 */
468 public function is_full_screen_mode_enabled() {
469
470 if ( $this->is_use_option__in_subtabs_or_tabs( 'is_force_full_screen' ) ) {
471 return true;
472 }
473
474 if ( class_exists( 'WPBC_User_Custom_Data_Saver' ) ) {
475 $saved_full_screen = WPBC_User_Custom_Data_Saver::get_user_data_value( wpbc_get_current_user_id(), 'is_full_screen' );
476 $saved_full_screen = function_exists( 'wpbc_ui__get_full_screen_mode_from_cookie' )
477 ? wpbc_ui__get_full_screen_mode_from_cookie( $saved_full_screen )
478 : $saved_full_screen;
479
480 if ( 'On' === $saved_full_screen ) {
481 return true;
482 }
483
484 if ( 'Off' === $saved_full_screen ) {
485 return false;
486 }
487 }
488
489 return (bool) $this->is_use_option__in_subtabs_or_tabs( 'is_default_full_screen' );
490 }
491
492 /**
493 * Check whether the current page should save and restore the user fullscreen preference.
494 *
495 * @return bool
496 */
497 public function is_full_screen_user_mode_enabled() {
498
499 if ( $this->is_use_option__in_subtabs_or_tabs( 'is_force_full_screen' ) ) {
500 return false;
501 }
502
503 return true;
504 }
505
506 /**
507 * Get breadcrumb/status-line items for the top path.
508 *
509 * Pages usually only need 'is_show_top_path' => true. Optional 'top_path'
510 * settings in tabs/subtabs can override root title, root URL, version
511 * visibility, or provide custom items.
512 *
513 * @return array
514 */
515 public function get_top_path_items() {
516
517 $page_tag = $this->get_top_path_page_tag();
518 $top_path_config = $this->is_use_option__in_subtabs_or_tabs( 'top_path' );
519 $top_path_config = is_array( $top_path_config ) ? $top_path_config : array();
520
521 if ( ! empty( $top_path_config['items'] ) && is_array( $top_path_config['items'] ) ) {
522 $items = $this->normalize_top_path_items( $top_path_config['items'] );
523 return apply_filters( 'wpbc_ui_settings_top_path_items', $items, $this, $top_path_config );
524 }
525
526 $items = array();
527
528 if ( ! isset( $top_path_config['product_title'] ) || false !== $top_path_config['product_title'] ) {
529 $items[] = array(
530 'title' => isset( $top_path_config['product_title'] ) ? $top_path_config['product_title'] : __( 'WP Booking Calendar', 'booking' ),
531 'url' => isset( $top_path_config['product_url'] ) ? $top_path_config['product_url'] : $this->get_top_path_product_url(),
532 'active' => false,
533 );
534 }
535
536 if ( ! isset( $top_path_config['root_title'] ) || false !== $top_path_config['root_title'] ) {
537 $items[] = array(
538 'title' => isset( $top_path_config['root_title'] ) ? $top_path_config['root_title'] : $this->get_top_path_default_root_title( $page_tag ),
539 'url' => isset( $top_path_config['root_url'] ) ? $top_path_config['root_url'] : $this->get_top_path_default_root_url( $page_tag ),
540 'active' => false,
541 );
542 }
543
544 $tab_item = $this->get_top_path_tab_item( $page_tag );
545 if ( ! empty( $tab_item ) ) {
546 $items = $this->append_top_path_item( $items, $tab_item );
547 }
548
549 $subtab_item = $this->get_top_path_subtab_item( $page_tag );
550 if ( ! empty( $subtab_item ) ) {
551 $items = $this->append_top_path_item( $items, $subtab_item );
552 }
553
554 if ( ! empty( $items ) ) {
555 $last_item_index = count( $items ) - 1;
556 foreach ( $items as $item_index => $item ) {
557 $items[ $item_index ]['active'] = ( $item_index === $last_item_index );
558 }
559 }
560
561 $items = $this->normalize_top_path_items( $items );
562
563 return apply_filters( 'wpbc_ui_settings_top_path_items', $items, $this, $top_path_config );
564 }
565
566 /**
567 * Check whether the top path should be visible.
568 *
569 * The status line is visible by default. Pages can disable it explicitly
570 * with 'is_show_top_path' => false in tab or subtab definition.
571 *
572 * @return bool
573 */
574 public function is_top_path_enabled() {
575
576 if ( isset( $this->current_page_params['subtab'] ) && array_key_exists( 'is_show_top_path', $this->current_page_params['subtab'] ) ) {
577 return ( false !== $this->current_page_params['subtab']['is_show_top_path'] );
578 }
579
580 if ( isset( $this->current_page_params['tab'] ) && array_key_exists( 'is_show_top_path', $this->current_page_params['tab'] ) ) {
581 return ( false !== $this->current_page_params['tab']['is_show_top_path'] );
582 }
583
584 return true;
585 }
586
587 /**
588 * Check whether the top path should include the version/status block.
589 *
590 * @return bool
591 */
592 public function is_top_path_show_version() {
593
594 $top_path_config = $this->is_use_option__in_subtabs_or_tabs( 'top_path' );
595
596 if ( is_array( $top_path_config ) && array_key_exists( 'show_version', $top_path_config ) ) {
597 return (bool) $top_path_config['show_version'];
598 }
599
600 return true;
601 }
602
603 /**
604 * Get active page tag for top path generation.
605 *
606 * @return string
607 */
608 private function get_top_path_page_tag() {
609
610 $this_page = $this->in_page();
611 $this_page_arr = is_array( $this_page ) ? $this_page : array( $this_page );
612 $request_page = isset( $_REQUEST['page'] ) ? sanitize_text_field( wp_unslash( $_REQUEST['page'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Recommended, WordPress.Security.NonceVerification.Missing
613
614 if ( in_array( $request_page, $this_page_arr, true ) ) {
615 return $request_page;
616 }
617
618 return (string) reset( $this_page_arr );
619 }
620
621 /**
622 * Get default root title.
623 *
624 * @param string $page_tag Page tag.
625 *
626 * @return string
627 */
628 private function get_top_path_default_root_title( $page_tag ) {
629
630 $root_titles = array(
631 'wpbc' => __( 'Bookings', 'booking' ),
632 'wpbc-availability' => __( 'Availability', 'booking' ),
633 'wpbc-prices' => __( 'Prices', 'booking' ),
634 'wpbc-resources' => __( 'Resources', 'booking' ),
635 'wpbc-settings' => __( 'Settings', 'booking' ),
636 'wpbc-setup' => __( 'Setup', 'booking' ),
637 );
638
639 return isset( $root_titles[ $page_tag ] ) ? $root_titles[ $page_tag ] : __( 'Booking Calendar', 'booking' );
640 }
641
642 /**
643 * Get product root URL.
644 *
645 * @return string
646 */
647 private function get_top_path_product_url() {
648
649 if ( function_exists( 'wpbc_get_bookings_url' ) ) {
650 return wpbc_get_bookings_url();
651 }
652
653 return admin_url( 'admin.php?page=wpbc' );
654 }
655
656 /**
657 * Get default root URL.
658 *
659 * @param string $page_tag Page tag.
660 *
661 * @return string
662 */
663 private function get_top_path_default_root_url( $page_tag ) {
664
665 if ( 'wpbc' === $page_tag && function_exists( 'wpbc_get_bookings_url' ) ) {
666 return wpbc_get_bookings_url();
667 }
668
669 if ( 'wpbc-availability' === $page_tag && function_exists( 'wpbc_get_availability_url' ) ) {
670 return wpbc_get_availability_url();
671 }
672
673 if ( 'wpbc-prices' === $page_tag && function_exists( 'wpbc_get_price_url' ) ) {
674 return wpbc_get_price_url();
675 }
676
677 if ( 'wpbc-settings' === $page_tag && function_exists( 'wpbc_get_settings_url' ) ) {
678 return wpbc_get_settings_url();
679 }
680
681 if ( 'wpbc-resources' === $page_tag && function_exists( 'wpbc_get_resources_url' ) ) {
682 return wpbc_get_resources_url();
683 }
684
685 if ( 'wpbc-setup' === $page_tag && function_exists( 'wpbc_get_setup_wizard_page_url' ) ) {
686 return wpbc_get_setup_wizard_page_url();
687 }
688
689 return admin_url( add_query_arg( array( 'page' => $page_tag ), 'admin.php' ) );
690 }
691
692 /**
693 * Get top path item for the active tab.
694 *
695 * @param string $page_tag Page tag.
696 *
697 * @return array
698 */
699 private function get_top_path_tab_item( $page_tag ) {
700
701 $active_tab_tag = $this->get_active__tab__tag();
702 $nav_tabs = $this->get_nav_tabs();
703 $tab_arr = isset( $nav_tabs[ $page_tag ][ $active_tab_tag ] ) ? $nav_tabs[ $page_tag ][ $active_tab_tag ] : array();
704
705 if ( empty( $tab_arr ) && ! empty( $this->current_page_params['tab'] ) ) {
706 $tab_arr = $this->current_page_params['tab'];
707 }
708
709 if ( empty( $active_tab_tag ) || empty( $tab_arr ) ) {
710 return array();
711 }
712
713 return array(
714 'title' => isset( $tab_arr['top_path_title'] ) ? $tab_arr['top_path_title'] : ( isset( $tab_arr['title'] ) ? $tab_arr['title'] : '' ),
715 'url' => ! empty( $tab_arr['url'] ) ? $tab_arr['url'] : $this->get_tab_url( $page_tag, $active_tab_tag ),
716 'onclick' => ! empty( $tab_arr['onclick'] ) ? $tab_arr['onclick'] : '',
717 'active' => true,
718 );
719 }
720
721 /**
722 * Get top path item for the active subtab.
723 *
724 * @param string $page_tag Page tag.
725 *
726 * @return array
727 */
728 private function get_top_path_subtab_item( $page_tag ) {
729
730 $active_tab_tag = $this->get_active__tab__tag();
731 $active_subtab_tag = $this->get_active__subtab__tag();
732 $nav_tabs = $this->get_nav_tabs();
733 $subtab_arr = isset( $nav_tabs[ $page_tag ][ $active_tab_tag ]['subtabs'][ $active_subtab_tag ] ) ? $nav_tabs[ $page_tag ][ $active_tab_tag ]['subtabs'][ $active_subtab_tag ] : array();
734
735 if ( empty( $subtab_arr ) && ! empty( $this->current_page_params['subtab'] ) ) {
736 $subtab_arr = $this->current_page_params['subtab'];
737 }
738
739 if ( empty( $active_tab_tag ) || empty( $active_subtab_tag ) || empty( $subtab_arr ) || empty( $subtab_arr['type'] ) || 'subtab' !== $subtab_arr['type'] ) {
740 return array();
741 }
742
743 return array(
744 'title' => isset( $subtab_arr['top_path_title'] ) ? $subtab_arr['top_path_title'] : ( isset( $subtab_arr['title'] ) ? $subtab_arr['title'] : '' ),
745 'url' => ! empty( $subtab_arr['url'] ) ? $subtab_arr['url'] : $this->get_tab_url( $page_tag, $active_tab_tag, $active_subtab_tag ),
746 'onclick' => ! empty( $subtab_arr['onclick'] ) ? $subtab_arr['onclick'] : '',
747 'active' => true,
748 );
749 }
750
751 /**
752 * Normalize top path item values.
753 *
754 * @param array $items Top path items.
755 *
756 * @return array
757 */
758 private function normalize_top_path_items( $items ) {
759
760 $normalized_items = array();
761
762 foreach ( $items as $item ) {
763 if ( empty( $item['title'] ) ) {
764 continue;
765 }
766
767 $normalized_items[] = array(
768 'title' => wp_strip_all_tags( $item['title'] ),
769 'url' => isset( $item['url'] ) ? $item['url'] : '',
770 'onclick' => isset( $item['onclick'] ) ? $item['onclick'] : '',
771 'active' => ! empty( $item['active'] ),
772 );
773 }
774
775 return $normalized_items;
776 }
777
778 /**
779 * Append top path item, avoiding consecutive duplicate labels.
780 *
781 * @param array $items Top path items.
782 * @param array $item New top path item.
783 *
784 * @return array
785 */
786 private function append_top_path_item( $items, $item ) {
787
788 if ( empty( $items ) || empty( $item['title'] ) ) {
789 $items[] = $item;
790 return $items;
791 }
792
793 $last_item_index = count( $items ) - 1;
794 $last_title = isset( $items[ $last_item_index ]['title'] ) ? wp_strip_all_tags( $items[ $last_item_index ]['title'] ) : '';
795 $item_title = wp_strip_all_tags( $item['title'] );
796
797 if ( $last_title === $item_title ) {
798 if ( ! empty( $item['url'] ) ) {
799 $items[ $last_item_index ]['url'] = $item['url'];
800 }
801 if ( ! empty( $item['onclick'] ) ) {
802 $items[ $last_item_index ]['onclick'] = $item['onclick'];
803 }
804 return $items;
805 }
806
807 $items[] = $item;
808
809 return $items;
810 }
811
812 /**
813 * Get Navigation path for header, if applicable.
814 * Used in Setup Wizard page.
815 *
816 * @return false|array
817 */
818 protected function is_use_navigation_path_arr() {
819
820 // Use Top line as Path in Setup Wizard page // FixIn: 10.4.0.2.
821 $is_use_navigation_path_arr = $this->is_use_option__in_subtabs( 'is_use_navigation_path' );
822
823 return $is_use_navigation_path_arr;
824 }
825
826 /**
827 * Get URL of settings page, based on Page Slug and Tab Slug e.g. page=wpbc-settings&tab=email&subtab=approved
828 *
829 * @param string $page_tag - e.g. 'wpbc-settings'.
830 * @param string $tab_name - e.g. 'email'.
831 * @param string $subtab_name ( Optional ) - e.g. 'approved'.
832 *
833 * @return string - Escaped URL to plugin page.
834 */
835 private function get_tab_url( $page_tag, $tab_name, $subtab_name = false ) {
836 if ( false === $subtab_name ) {
837 return esc_url( admin_url( add_query_arg( array( 'page' => $page_tag, $this->tags['tab'] => $tab_name ), 'admin.php' ) ) );
838 } else {
839 return esc_url( admin_url( add_query_arg( array( 'page' => $page_tag, $this->tags['tab'] => $tab_name, $this->tags['subtab'] => $subtab_name ), 'admin.php' ) ) );
840 }
841 }
842 }
843