PluginProbe
Booking Calendar / 11.5
Booking Calendar v11.5
11.8.4 11.8.3 11.8.2 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 All 204 releases
booking / includes / _front_end / class-fe-render.php

class-fe-render.php in Booking Calendar 11.5, at includes/_front_end/class-fe-render.php

380 lines 16.6 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Front-End Render (Booking form, Calendar)
4 *
5 * File: /wp-content/plugins/booking/includes/_front_end/class-fe-render.php
6 */
7
8 if ( ! defined( 'ABSPATH' ) ) {
9 exit;
10 }
11
12 class WPBC_FE_Render {
13
14 /**
15 * Echo or return helper (to preserve legacy API behavior).
16 *
17 * @param string $html - already escaped/sanitizing HTML content.
18 * @param bool $is_echo - do we need to echo it?.
19 *
20 * @return string|void
21 */
22 private static function echo_or_return( $html, $is_echo ) {
23
24 if ( $is_echo ) {
25
26 echo $html; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
27
28 return;
29 }
30
31 return $html;
32 }
33
34 // -----------------------------------------------------------------------------------------------------------------
35
36 /**
37 * Render Booking Form (Calendar + Form).
38 *
39 * @param array $params_arr
40 *
41 * @return string|void
42 */
43 public static function render_booking_form( $params_arr = array() ) {
44
45 // Default parameters (keep identical to legacy).
46 $default_params = array(
47 'resource_id' => 1,
48 'cal_count' => 1,
49 'is_echo' => 1,
50 'custom_booking_form' => 'standard',
51 'selected_dates_without_calendar' => '',
52 'start_month_calendar' => false,
53 'shortcode_param__options' => '',
54 'calendar_dates_start' => '',
55 'calendar_dates_end' => '',
56 'booking_hash' => '',
57 'form_status' => 'published',
58 'calendar_request_overrides' => array(),
59 );
60 $params_arr = wp_parse_args( $params_arr, $default_params );
61 $is_echo = ( ! empty( $params_arr['is_echo'] ) );
62
63 // ---------------------------------------------------------------------
64 // Hash resolution, e.g. $_GET['booking_hash'] for Booking Form rendering.
65 // ---------------------------------------------------------------------
66 $hash_res = WPBC_FE_Attr_Postprocessor::resolve_booking_hash_and_maybe_get_parent_resource_id( $params_arr, 'form' );
67 if ( ! $hash_res['ok'] ) {
68 return self::echo_or_return( $hash_res['error_html'], $is_echo );
69 }
70 $params_arr = $hash_res['params_arr'];
71
72 // ---------------------------------------------------------------------
73 // Normalize aggregate resource IDs. - "5;3;9" -> [ 'resource_id' => 5, 'aggregate_resource_id_arr' => [5,3,9] ].
74 // ---------------------------------------------------------------------
75 $aggregate_resource_id_arr = array();
76 $split = WPBC_FE_Attr_Postprocessor::split_aggregate_resource_id( $params_arr['resource_id'] );
77 $params_arr['resource_id'] = $split['resource_id'];
78 $aggregate_resource_id_arr = $split['aggregate_resource_id_arr'];
79
80 // ---------------------------------------------------------------------
81 // Validate resource_id parameter and check if booking resource exists.
82 // ---------------------------------------------------------------------
83 $resource_validation = WPBC_FE_Attr_Postprocessor::validate_resource_id( $params_arr['resource_id'] );
84 if ( true !== $resource_validation ) {
85 return self::echo_or_return( $resource_validation, $is_echo );
86 }
87
88 // ---------------------------------------------------------------------
89 // == MU ==
90 // ---------------------------------------------------------------------
91 make_bk_action( 'check_multiuser_params_for_client_side', $params_arr['resource_id'] );
92
93 // Render a focused cancellation confirmation instead of loading the complete booking form and calendar.
94 if ( WPBC_GET_Request::has_get( 'booking_cancel' ) && function_exists( 'wpbc_customer_access_render_cancellation_confirmation' ) ) {
95 $booking_hash = sanitize_text_field( wp_unslash( (string) $params_arr['booking_hash'] ) );
96 if ( '' === $booking_hash ) {
97 $booking_hash = WPBC_GET_Request::get_sanitized( 'booking_hash' );
98 }
99
100 $cancellation_html = wpbc_customer_access_render_cancellation_confirmation( $booking_hash, $params_arr['resource_id'] );
101
102 /**
103 * Filters the complete visitor cancellation confirmation markup.
104 *
105 * @param string $cancellation_html Rendered confirmation markup.
106 * @param int $resource_id Resource ID used by the front-end form container.
107 * @param string $booking_hash Sanitized booking credential from the cancellation URL.
108 */
109 $cancellation_html = apply_filters(
110 'wpbc_customer_booking_cancellation_confirmation_html',
111 $cancellation_html,
112 absint( $params_arr['resource_id'] ),
113 $booking_hash
114 );
115
116 // phpcs:ignore WordPress.NamingConventions.PrefixAllGlobals.NonPrefixedHooknameFound
117 $my_result = apply_filters( 'wpdev_booking_form', ' ' . $cancellation_html . ' ', $params_arr['resource_id'] );
118
119 make_bk_action( 'finish_check_multiuser_params_for_client_side', $params_arr['resource_id'] );
120
121 return self::echo_or_return( $my_result, $is_echo );
122 }
123
124 // ---------------------------------------------------------------------
125 // Normalize calendar_dates_start/end.
126 // ---------------------------------------------------------------------
127 $calendar_dates_range = WPBC_FE_Attr_Postprocessor::normalize_calendar_dates_range( $params_arr['calendar_dates_start'], $params_arr['calendar_dates_end'] );
128
129 // ---------------------------------------------------------------------
130 // Calendar load params (keep identical keys).
131 // ---------------------------------------------------------------------
132 $calendar_load_params = array(
133 'resource_id' => $params_arr['resource_id'],
134 'aggregate_resource_id_arr' => $aggregate_resource_id_arr,
135 'selected_dates_without_calendar' => $params_arr['selected_dates_without_calendar'],
136 'calendar_number_of_months' => $params_arr['cal_count'],
137 'start_month_calendar' => $params_arr['start_month_calendar'],
138 'shortcode_options' => $params_arr['shortcode_param__options'],
139 'custom_form' => $params_arr['custom_booking_form'],
140 'calendar_dates_start' => $calendar_dates_range['start'],
141 'calendar_dates_end' => $calendar_dates_range['end'],
142 'calendar_request_overrides' => $params_arr['calendar_request_overrides'],
143 );
144
145 $start_script_code = wpbc__calendar__load( $calendar_load_params );
146
147 // Disable booked time slots when selected date is predefined (legacy behavior).
148 if ( '' !== $params_arr['selected_dates_without_calendar'] ) {
149 $assets_key = 'wpbc:disable_time_fields_in_booking_form:' . intval( $params_arr['resource_id'] );
150
151 // Fire on all booking dates loaded. // FixIn: 10.14.17.2.
152 $local_js_code = " jQuery( 'body' ).on( 'wpbc_calendar_ajx__loaded_data', function ( event, loaded_resource_id ){ ";
153 $local_js_code .= ' if ( loaded_resource_id == ' . intval( $params_arr['resource_id'] ) . ' ){ ';
154 $local_js_code .= ' wpbc_disable_time_fields_in_booking_form(' . intval( $params_arr['resource_id'] ) . ')';
155 $local_js_code .= ' }';
156 $local_js_code .= '} );';
157
158 $added = WPBC_FE_Assets::add_jq_ready_js_to_wp_script( 'wpbc_all', $local_js_code, $assets_key );
159 if ( ! $added ) {
160 $start_script_code .= WPBC_FE_Assets::add_inline_js( $local_js_code, $assets_key ); // Fallback to direct inline JS, if previosly not edded script.
161 }
162 }
163
164 // ---------------------------------------------------------------------
165 // For Phase #1 we still use legacy HTML builder for the form body. (Later phases will move it fully.)
166 // ---------------------------------------------------------------------
167 $legacy = wpbc_get_legacy_booking_instance();
168 if ( ! $legacy ) {
169 $err = '<div class="wpbc_after_booking_thank_you_section"><div class="wpbc_ty__container"><div class="wpbc_ty__header"><strong>' . esc_html__( 'Oops!', 'booking' ) . '</strong> ' . esc_html__( 'Booking Calendar front-end renderer is not available. Please contact support.', 'booking' ) . '</div></div></div>';
170 return self::echo_or_return( $err, $is_echo );
171 }
172
173 $form_html = WPBC_FE_Form_Body_Renderer::render(
174 array(
175 'resource_id' => $params_arr['resource_id'],
176 'custom_booking_form' => $params_arr['custom_booking_form'],
177 'form_status' => $params_arr['form_status'],
178 'selected_dates_without_calendar' => $params_arr['selected_dates_without_calendar'],
179 'cal_count' => $params_arr['cal_count'],
180 'shortcode_param__options' => $params_arr['shortcode_param__options'],
181 'booking_hash' => $params_arr['booking_hash'],
182 'legacy_instance' => $legacy,
183 )
184 );
185
186 $my_result = ' ' . $form_html . ' ' . $start_script_code;
187
188
189 // Add DIV structure, where to show payment form.
190 $my_result = apply_filters( 'wpdev_booking_form', $my_result, $params_arr['resource_id'] ); // phpcs:ignore WordPress.NamingConventions.PrefixAllGlobals.NonPrefixedHooknameFound
191
192 // == MU ==
193 make_bk_action( 'finish_check_multiuser_params_for_client_side', $params_arr['resource_id'] );
194
195 return self::echo_or_return( $my_result, $is_echo );
196 }
197
198
199 /**
200 * Render Availability Calendar Only.
201 *
202 * @param array $params_arr
203 *
204 * @return string|void
205 */
206 public static function render_calendar_only( $params_arr = array() ) {
207
208 $default_params = array(
209 'resource_id' => 1,
210 'cal_count' => 1,
211 'is_echo' => 1,
212 'start_month_calendar' => false,
213 'shortcode_param__options' => '',
214 'calendar_dates_start' => '',
215 'calendar_dates_end' => '',
216 'booking_hash' => '',
217 'calendar_request_overrides' => array(),
218 );
219 $params_arr = wp_parse_args( $params_arr, $default_params );
220 $is_echo = ( ! empty( $params_arr['is_echo'] ) );
221
222 // ---------------------------------------------------------------------
223 // Hash resolution, e.g. $_GET['booking_hash'] for Booking Form rendering.
224 // ---------------------------------------------------------------------
225 $hash_res = WPBC_FE_Attr_Postprocessor::resolve_booking_hash_and_maybe_get_parent_resource_id( $params_arr, 'calendar' );
226 if ( ! $hash_res['ok'] ) {
227 return self::echo_or_return( $hash_res['error_html'], $is_echo );
228 }
229 $params_arr = $hash_res['params_arr'];
230
231 // ---------------------------------------------------------------------
232 // Normalize aggregate resource IDs. - "5;3;9" -> [ 'resource_id' => 5, 'aggregate_resource_id_arr' => [5,3,9] ].
233 // ---------------------------------------------------------------------
234 $aggregate_resource_id_arr = array();
235 $split = WPBC_FE_Attr_Postprocessor::split_aggregate_resource_id( $params_arr['resource_id'] );
236 $params_arr['resource_id'] = $split['resource_id'];
237 $aggregate_resource_id_arr = $split['aggregate_resource_id_arr'];
238
239
240 // ---------------------------------------------------------------------
241 // Validate resource_id parameter and check if booking resource exists.
242 // ---------------------------------------------------------------------
243 $resource_validation = WPBC_FE_Attr_Postprocessor::validate_resource_id( $params_arr['resource_id'] );
244 if ( true !== $resource_validation ) {
245 return self::echo_or_return( $resource_validation, $is_echo );
246 }
247
248 // ---------------------------------------------------------------------
249 // == MU ==
250 // ---------------------------------------------------------------------
251 make_bk_action( 'check_multiuser_params_for_client_side', $params_arr['resource_id'] );
252
253 // ---------------------------------------------------------------------
254 // Normalize calendar_dates_start/end.
255 // ---------------------------------------------------------------------
256 $calendar_dates_range = WPBC_FE_Attr_Postprocessor::normalize_calendar_dates_range( $params_arr['calendar_dates_start'], $params_arr['calendar_dates_end'] );
257
258 $calendar_load_params = array(
259 'resource_id' => $params_arr['resource_id'],
260 'aggregate_resource_id_arr' => $aggregate_resource_id_arr,
261 'selected_dates_without_calendar' => '',
262 'calendar_number_of_months' => $params_arr['cal_count'],
263 'start_month_calendar' => $params_arr['start_month_calendar'],
264 'shortcode_options' => $params_arr['shortcode_param__options'],
265 'custom_form' => 'standard', // Because we show only 'AVAILABILITY CALENDAR' without the form, at all.
266 'calendar_dates_start' => $calendar_dates_range['start'],
267 'calendar_dates_end' => $calendar_dates_range['end'],
268 'calendar_request_overrides' => $params_arr['calendar_request_overrides'],
269 );
270 $start_script_code = wpbc__calendar__load( $calendar_load_params );
271
272
273 $my_result = '<div style="clear:both;height:10px;"></div>';
274 $my_result .= wpbc_pre_get_calendar_html( $params_arr['resource_id'], $params_arr['cal_count'], $params_arr['shortcode_param__options'] );
275 $my_result .= ' ' . $start_script_code;
276
277 // Keep legacy filter.
278 $my_result = apply_filters( 'wpdev_booking_calendar', $my_result, $params_arr['resource_id'] ); // phpcs:ignore WordPress.NamingConventions.PrefixAllGlobals.NonPrefixedHooknameFound
279
280 $booking_form_is_using_bs_css = get_bk_option( 'booking_form_is_using_bs_css' );
281 $my_result = '<span ' . ( ( 'On' === $booking_form_is_using_bs_css ) ? 'class="wpdevelop"' : '' ) . '>' . $my_result . '</span>';
282
283 // == MU ==
284 make_bk_action( 'finish_check_multiuser_params_for_client_side', $params_arr['resource_id'] );
285
286 return self::echo_or_return( $my_result, $is_echo );
287 }
288
289 }
290
291
292 /**
293 * Try to get legacy wpdev_booking instance (for Phase #1 fallback calls).
294 *
295 * @return wpdev_booking|null
296 */
297 function wpbc_get_legacy_booking_instance() {
298
299 if ( ! function_exists( 'WPBC' ) ) {
300 return null;
301 }
302
303 $wpbc_instance = WPBC();
304 if ( ! $wpbc_instance ) {
305 return null;
306 }
307
308 if ( empty( $wpbc_instance->booking_obj ) && class_exists( 'wpdev_booking' ) ) {
309 // Lazy boot as a last resort (avoid doing this if you don’t want any boot during true WPBC ajax).
310 $wpbc_instance->booking_obj = new wpdev_booking();
311 }
312
313 return ( $wpbc_instance->booking_obj instanceof wpdev_booking ) ? $wpbc_instance->booking_obj : null;
314 }
315
316
317
318 //TODO: replace evrywhere wpbc_get_rendered_booking_form_html() to some simpler call.
319
320 /**
321 * Get HTML of Rendered Booking From - Legacy type of calling render.
322 *
323 * @param $resource_id
324 * @param $cal_count
325 * @param $is_echo
326 * @param $my_booking_form
327 * @param $my_selected_dates_without_calendar
328 * @param $start_month_calendar
329 * @param $shortcode_param__options
330 *
331 * @return string|null
332 */
333 function wpbc_get_rendered_booking_form_html( $resource_id = 1, $cal_count = 1, $is_echo = 1, $my_booking_form = 'standard', $my_selected_dates_without_calendar = '', $start_month_calendar = false, $shortcode_param__options = array() ) {
334
335 return WPBC_FE_Render::render_booking_form(
336 array(
337 'resource_id' => $resource_id,
338 'cal_count' => $cal_count,
339 'is_echo' => $is_echo,
340 'custom_booking_form' => $my_booking_form,
341 'selected_dates_without_calendar' => $my_selected_dates_without_calendar,
342 'start_month_calendar' => $start_month_calendar,
343 'shortcode_param__options' => $shortcode_param__options,
344 )
345 );
346 }
347
348 /**
349 * Get booking form rendered HTML content without echo.
350 *
351 * @param $resource_id
352 * @param $cal_count
353 * @param $my_booking_form
354 * @param $my_selected_dates_without_calendar
355 * @param $start_month_calendar
356 * @param $shortcode_param__options
357 *
358 * @return string|null
359 */
360 function wpbc_get_rendered_booking_form_html__noecho( $resource_id = 1, $cal_count = 1, $my_booking_form = 'standard', $my_selected_dates_without_calendar = '', $start_month_calendar = false, $shortcode_param__options = array() ) {
361
362 $my_result = WPBC_FE_Render::render_booking_form(
363 array(
364 'resource_id' => $resource_id,
365 'cal_count' => $cal_count,
366 'is_echo' => 0,
367 'custom_booking_form' => $my_booking_form,
368 'selected_dates_without_calendar' => $my_selected_dates_without_calendar,
369 'start_month_calendar' => $start_month_calendar,
370 'shortcode_param__options' => $shortcode_param__options,
371 )
372 );
373 return $my_result;
374 }
375
376 /**
377 * This hook exists in personal.php file for the [bookingselect ..]
378 */
379 add_bk_filter( 'wpdevbk_get_booking_form', 'wpbc_get_rendered_booking_form_html__noecho' );
380