PluginProbe
weForms – Easy Drag & Drop Contact Form Builder For WordPress / 1.6.9
weForms – Easy Drag & Drop Contact Form Builder For WordPress v1.6.9
1.6.7 1.6.8 1.6.9 1.6.12 1.6.13 1.6.14 1.6.15 1.6.16 1.6.17 1.6.18 1.6.19 1.6.2 1.6.20 1.6.21 1.6.22 1.6.23 1.6.24 1.6.25 1.6.26 1.6.27 1.6.28 1.6.3 1.6.4 1.6.5 1.6.6 All 74 releases
weforms / includes / class-form.php

class-form.php in weForms – Easy Drag & Drop Contact Form Builder For WordPress 1.6.9, at includes/class-form.php

635 lines 20.5 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 /**
4 * The Form Class
5 *
6 * @since 1.1.0
7 */
8 class WeForms_Form {
9
10 /**
11 * The form id
12 *
13 * @var int
14 */
15 public $id = 0;
16
17 /**
18 * The form title
19 *
20 * @var string
21 */
22 public $name = '';
23
24 /**
25 * Holds the post data object
26 *
27 * @var WP_post|null
28 */
29 public $data = null;
30
31 /**
32 * Form fields
33 *
34 * @var array
35 */
36 public $form_fields = [];
37
38 /**
39 * The Constructor
40 *
41 * @param int|WP_Post $form
42 */
43 public function __construct( $form = null ) {
44 if ( is_numeric( $form ) ) {
45 $the_post = get_post( $form );
46
47 if ( $the_post ) {
48 $this->id = $the_post->ID;
49 $this->name = $the_post->post_title;
50 $this->data = $the_post;
51 }
52 } elseif ( is_a( $form, 'WP_Post' ) ) {
53 $this->id = $form->ID;
54 $this->name = $form->post_title;
55 $this->data = $form;
56 }
57 }
58
59 /**
60 * Get the form ID
61 *
62 * @return int
63 */
64 public function get_id() {
65 return $this->id;
66 }
67
68 /**
69 * Get the form name
70 *
71 * @return string
72 */
73 public function get_name() {
74 return $this->name;
75 }
76
77 /**
78 * Get all form fields of this form
79 *
80 * @return array
81 */
82 public function get_fields() {
83
84 // return if already fetched
85 if ( $this->form_fields ) {
86 return $this->form_fields;
87 }
88
89 $fields = get_children( [
90 'post_parent' => $this->id,
91 'post_status' => 'publish',
92 'post_type' => 'wpuf_input',
93 'numberposts' => '-1',
94 'orderby' => 'menu_order',
95 'order' => 'ASC',
96 ] );
97
98 $form_fields = [];
99
100 foreach ( $fields as $key => $content ) {
101 $field = maybe_unserialize( $content->post_content );
102
103 if ( empty( $field['template'] ) ) {
104 continue;
105 }
106
107 $field['id'] = $content->ID;
108
109 // Add inline property for radio and checkbox fields
110 $inline_supported_fields = apply_filters( 'inline_supported_fields_list', [ 'radio_field', 'checkbox_field' ] );
111
112 if ( in_array( $field['template'], $inline_supported_fields ) ) {
113 if ( !isset( $field['inline'] ) ) {
114 $field['inline'] = 'no';
115 }
116 }
117
118 // Add 'selected' property
119 $option_based_fields = apply_filters( 'option_based_fields_list', [ 'dropdown_field', 'multiple_select', 'radio_field', 'checkbox_field' ] );
120
121 if ( in_array( $field['template'], $option_based_fields ) ) {
122 if ( !isset( $field['selected'] ) ) {
123 if ( 'dropdown_field' === $field['template'] || 'radio_field' === $field['template'] ) {
124 $field['selected'] = '';
125 } else {
126 $field['selected'] = [];
127 }
128 }
129 }
130
131 // Add 'multiple' key for template:repeat
132 if ( 'repeat_field' === $field['template'] && !isset( $field['multiple'] ) ) {
133 $field['multiple'] = '';
134 }
135
136 if ( 'recaptcha' === $field['template'] ) {
137 $field['name'] = 'recaptcha';
138 $field['enable_no_captcha'] = isset( $field['enable_no_captcha'] ) ? $field['enable_no_captcha'] : '';
139 $field['recaptcha_theme'] = isset( $field['recaptcha_theme'] ) ? $field['recaptcha_theme'] : 'light';
140 }
141
142 // Check if meta_key has changed when saving form compared current entries
143 $field['original_name'] = $field['name'];
144
145 $form_fields[] = apply_filters( 'weforms-get-form-field', $field, $this->id );
146 }
147
148 $this->form_fields = apply_filters( 'weforms-get-form-fields', $form_fields, $this->id );
149
150 return $this->form_fields;
151 }
152
153 /**
154 * Check if any perticular field template is used in a form
155 *
156 * @return array
157 */
158 public function has_field( $field_template ) {
159 foreach ( $this->get_fields() as $key => $field ) {
160 if ( isset( $field['template'] ) && $field['template'] == $field_template ) {
161 return true;
162 }
163 }
164 }
165
166 /**
167 * Get all fields by a template
168 *
169 * @return array
170 */
171 public function search_fields( $field_template ) {
172 $fields = [];
173
174 foreach ( $this->get_fields() as $key => $field ) {
175 if ( isset( $field['template'] ) && $field['template'] == $field_template ) {
176 $fields[] = $field;
177 }
178 }
179
180 return $fields;
181 }
182
183 /**
184 * Search fileds and get the first one
185 *
186 * @return array
187 */
188 public function search_field( $field_template ) {
189 $fields = $this->search_fields( $field_template );
190
191 return isset( $fields[0] ) ? $fields[0] : [];
192 }
193
194 /**
195 * Get formatted field name/values
196 *
197 * @return array
198 */
199 public function get_field_values() {
200 $values = [];
201 $fields = $this->get_fields();
202
203 if ( !$fields ) {
204 return $values;
205 }
206
207 $ignore_fields = apply_filters( 'ignore_fields_list', [ 'recaptcha', 'section_break' ] );
208 $options_fields = apply_filters( 'option_fields_list', [ 'dropdown_field', 'radio_field', 'multiple_select', 'checkbox_field' ] );
209
210 foreach ( $fields as $field ) {
211 if ( in_array( $field['template'], $ignore_fields ) ) {
212 continue;
213 }
214
215 // Prepare column field data
216 if ( $field['template'] == 'column_field' ) {
217 $inner_columns = $field['inner_fields'];
218
219 if ( !empty( $inner_columns ) ) {
220 foreach ( $inner_columns as $column => $column_fields ) {
221 if ( !empty( $column_fields ) ) {
222 foreach ( $column_fields as $field_obj ) {
223 if ( in_array( $field_obj['template'], $ignore_fields ) ) {
224 continue;
225 }
226
227 if ( !isset( $field_obj['name'] ) ) {
228 continue;
229 }
230
231 $field_value = [
232 'label' => isset( $field_obj['label'] ) ? $field_obj['label'] : '',
233 'type' => $field_obj['template'],
234 ];
235
236 // put options if this is an option field
237 if ( in_array( $field_obj['template'], $options_fields ) ) {
238 $field_value['options'] = $field_obj['options'];
239 }
240
241 $values[ $field_obj['name'] ] = array_merge( $field_obj, $field_value );
242 }
243 }
244 }
245 }
246 }
247
248 if ( !isset( $field['name'] ) ) {
249 continue;
250 }
251
252 $value = [
253 'label' => isset( $field['label'] ) ? $field['label'] : '',
254 'type' => $field['template'],
255 ];
256
257 // put options if this is an option field
258 if ( in_array( $field['template'], $options_fields ) ) {
259 $value['options'] = $field['options'];
260 }
261
262 $values[ $field['name'] ] = array_merge( $field, $value );
263 }
264
265 return apply_filters( 'weforms_get_field_values', $values );
266 }
267
268 /**
269 * Get form settings
270 *
271 * @return array
272 */
273 public function get_settings() {
274 $settings = get_post_meta( $this->id, 'wpuf_form_settings', true );
275 $default = weforms_get_default_form_settings();
276
277 return apply_filters( 'weforms-get-form-settings', array_merge( $default, $settings ), $this->id );
278 }
279
280 /**
281 * Check if the form submission is open
282 *
283 * @return bool|WP_Error
284 */
285 public function is_submission_open() {
286 $settings = $this->get_settings();
287
288 $needs_login = ( isset( $settings['require_login'] ) && $settings['require_login'] == 'true' ) ? true : false;
289 $has_limit = ( isset( $settings['limit_entries'] ) && $settings['limit_entries'] == 'true' ) ? true : false;
290 $is_scheduled = ( isset( $settings['schedule_form'] ) && $settings['schedule_form'] == 'true' ) ? true : false;
291
292 if ( $this->data->post_status != 'publish' ) {
293 return new WP_Error( 'needs-publish', __( 'The form is not published yet.', 'weforms' ) );
294 }
295
296 if ( $needs_login && !is_user_logged_in() ) {
297 return new WP_Error( 'needs-login', $settings['req_login_message'] );
298 }
299
300 if ( $has_limit ) {
301 $limit = (int) $settings['limit_number'];
302 $form_entries = $this->num_form_entries();
303
304 if ( $limit <= $form_entries ) {
305 return new WP_Error( 'entry-limit', $settings['limit_message'] );
306 }
307 }
308
309 if ( $is_scheduled ) {
310 $start_time = strtotime( $settings['schedule_start'] );
311 $end_time = strtotime( $settings['schedule_end'] );
312 $current_time = current_time( 'timestamp' );
313
314 // too early?
315 if ( $current_time < $start_time ) {
316 return new WP_Error( 'form-pending', $settings['sc_pending_message'] );
317 } elseif ( $current_time > $end_time ) {
318 return new WP_Error( 'form-expired', $settings['sc_expired_message'] );
319 }
320 }
321
322 return apply_filters( 'weforms_is_submission_open', true, $settings, $this );
323 }
324
325 /**
326 * Get form notifications
327 *
328 * @return array
329 */
330 public function get_notifications() {
331 $notifications = get_post_meta( $this->id, 'notifications', true );
332 $defualt = weforms_get_default_form_notification();
333
334 if ( !$notifications ) {
335 $notifications = [];
336 }
337
338 $notifications = array_map( function ( $notification ) use ( $defualt ) {
339 if ( empty( $notification ) ) {
340 $notification = [];
341 }
342
343 return array_merge( $defualt, $notification );
344 }, $notifications );
345
346 return $notifications;
347 }
348
349 /**
350 * Get all the integrations
351 *
352 * @return array
353 */
354 public function get_integrations() {
355 $integrations = get_post_meta( $this->id, 'integrations', true );
356
357 if ( !$integrations ) {
358 return [];
359 }
360
361 return $integrations;
362 }
363
364 /**
365 * Get entries of this form
366 *
367 * @return \WeForms_Form_Entry_Manager
368 */
369 public function entries() {
370 return new WeForms_Form_Entry_Manager( $this->id, $this );
371 }
372
373 /**
374 * When a user is editing their form they may change a fields name.
375 * This method will loop through existing entries to match the new field names.
376 *
377 * @since 1.6.9
378 *
379 * @param int $form_id
380 * @param array $form_fields
381 */
382 public function maybe_update_entries( $form_fields ) {
383 $changed_fields = $this->get_changed_fields( $form_fields );
384 // Loop through changed fields and update entries
385 foreach ( $changed_fields as $old => $new) {
386 $updated_fields = $this->rename_field( $old, $new );
387 }
388 }
389
390 /**
391 * When a user is editing their form they may change a fields name.
392 * This method will loop through all fields that have changed.
393 *
394 * @since 1.6.9
395 *
396 * @param int $form_id
397 * @param array $form_fields
398 *
399 * @return array
400 */
401 public function get_changed_fields( $form_fields ) {
402 $changed_fields = array();
403 foreach ( $form_fields as $field ) {
404 $org_field = $field['original_name'];
405 error_log("Org Field" . " = " . print_r($org_field,1));
406 // All form fields should have an original name.
407 if ( empty( $field['original_name'] ) ) {
408 continue;
409 }
410 if ( $field['name'] !== $field['original_name'] ) {
411 $changed_fields[$field['original_name']] = $field['name'];
412 } else {
413 continue;
414 }
415 }
416 return $changed_fields;
417
418 }
419
420 /**
421 * When a user changes the field names of a form, the existing entries will need updated.
422 * This method will loop through the existing entries and update them will the new names.
423 *
424 * @since 1.6.9
425 *
426 * @param int $form_id
427 * @param array $form_fields
428 *
429 * @return array
430 */
431 public function rename_field ( $old, $new ) {
432 global $wpdb;
433
434 $entries = weforms_get_form_entries( $this->id );
435
436 foreach ( $entries as $entry ) {
437 $entry_id = $entry->id;
438 $values = weforms_get_entry_meta( $entry_id );
439 $update_keys = $wpdb->update( $wpdb->weforms_entrymeta, array( 'meta_key' => $new ), array( 'meta_key' => $old, 'weforms_entry_id' => $entry_id ) );
440 }
441 }
442
443 /**
444 * Get number of form entries
445 *
446 * @return int
447 */
448 public function num_form_entries() {
449 return weforms_count_form_entries( $this->id );
450 }
451
452 /**
453 * Get number of form payments
454 *
455 * @return int
456 */
457 public function num_form_payments() {
458 return weforms_count_form_payments( $this->id );
459 }
460
461 /**
462 * Get form author details
463 *
464 * @return array
465 */
466 public function get_form_author_details() {
467 return weforms_get_form_author_details( $this->id );
468 }
469
470 /**
471 * Get the number of form views
472 *
473 * @return int
474 */
475 public function num_form_views() {
476 return weforms_get_form_views( $this->id );
477 }
478
479 /**
480 * prepare_entries
481 *
482 * @return array
483 */
484 public function prepare_entries( $args = [] ) {
485 $fields = weforms()->fields->get_fields();
486 $form_fields = $this->get_fields();
487
488 $entry_fields = [];
489
490 $ignore_list = apply_filters( 'wefroms_entry_ignore_list', [
491 'recaptcha', 'section_break', 'step_start',
492 ] );
493
494 foreach ( $form_fields as $field ) {
495 if ( in_array( $field['template'], $ignore_list ) ) {
496 continue;
497 }
498
499 if ( !array_key_exists( $field['template'], $fields ) ) {
500 continue;
501 }
502
503 // Prepare column field data
504 if ( $field['template'] == 'column_field' ) {
505 $inner_columns = $field['inner_fields'];
506
507 if ( !empty( $inner_columns ) ) {
508 foreach ( $inner_columns as $column => $column_fields ) {
509 if ( !empty( $column_fields ) ) {
510 foreach ( $column_fields as $field_obj ) {
511 if ( in_array( $field_obj['template'], $ignore_list ) ) {
512 continue;
513 }
514
515 $fieldClass = $fields[ $field_obj['template'] ];
516 $entry_fields[ $field_obj['name'] ] = $fieldClass->prepare_entry( $field_obj );
517 }
518 }
519 }
520 }
521 }
522
523 $field_class = $fields[ $field['template'] ];
524
525 $entry_fields[ $field['name'] ] = $field_class->prepare_entry( $field, $args );
526 }
527
528 return apply_filters( 'weforms_prepare_entries', $entry_fields );
529 }
530
531 /**
532 * Check if the form submission is open On API
533 *
534 * @return bool|WP_Error
535 */
536 public function is_api_form_submission_open() {
537 $response = [];
538 $settings = $this->get_settings();
539 $form_entries = $this->num_form_entries();
540 $needs_login = isset( $settings['require_login'] ) ? $settings['require_login'] : 'false';
541 $limit_entries = isset( $settings['limit_entries'] ) ? $settings['limit_entries'] : 'false';
542 $schedule_form = isset( $settings['schedule_form'] ) ? $settings['schedule_form'] : 'false';
543 $limit_number = isset( $settings['limit_number'] ) ? $settings['limit_number'] : '';
544 $schedule_start = isset( $settings['schedule_start'] ) ? $settings['schedule_start'] : '';
545 $schedule_end = isset( $settings['schedule_end'] ) ? $settings['schedule_end'] : '';
546 $schedule_start_date = date_i18n( 'M d, Y', strtotime( $schedule_start ) );
547 $schedule_end_date = date_i18n( 'M d, Y', strtotime( $schedule_end ) );
548
549 if ( $this->data->post_status != 'publish' ) {
550 $response['type'] = __( 'Closed', 'weforms' );
551 }
552
553 if ( $this->isFormStatusClosed( $settings, $form_entries ) ) {
554 $response['type'] = __( 'Closed', 'weforms' );
555 } else {
556 $response['type'] = __( 'Open', 'weforms' );
557 }
558
559 if ( $limit_entries === 'true' ) {
560 if ( $schedule_form === 'true' && $this->isExpiredForm( $schedule_end ) ) {
561 $response['message'] = __( "Expired at {$schedule_end_date}", 'weforms' );
562 } elseif ( $schedule_form === 'true' && $this->isPendingForm( $schedule_start ) ) {
563 $response['message'] = __( "Starts at {$schedule_start_date}", 'weforms' );
564 } elseif ( $form_entries >= $limit_number ) {
565 $response['message'] = __( 'Reached maximum entry limit', 'weforms' );
566 } else {
567 $remaining_entries = $limit_number - $form_entries;
568 $response['message'] = __( "{$remaining_entries} entries remaining ", 'weforms' );
569 }
570 } elseif ( $schedule_form === 'true' ) {
571 if ( $this->isPendingForm( $schedule_start ) ) {
572 $response['message'] = __( "Starts at {$schedule_start_date}", 'weforms' );
573 } elseif ( $this->isExpiredForm( $schedule_end ) ) {
574 $response['message'] = __( "Expired at {$schedule_end_date}", 'weforms' );
575 } elseif ( $this->isOpenForm( $schedule_start, $schedule_end ) ) {
576 $response['message'] = __( "Expires at {$schedule_end_date}", 'weforms' );
577 }
578 } elseif ( $needs_login === 'true' ) {
579 $response['message'] =__( 'Requires login', 'weforms' );
580 }
581
582 return apply_filters( 'weforms_is_submission_open', $response, $settings, $this );
583 }
584
585 public function isPendingForm( $scheduleStart ) {
586 $currentTime = current_time( 'timestamp' );
587 $startTime = strtotime( $scheduleStart );
588
589 if ( $currentTime < $startTime ) {
590 return true;
591 }
592
593 return false;
594 }
595
596 public function isExpiredForm( $scheduleEnd ) {
597 $currentTime = current_time( 'timestamp' );
598 $endTime = strtotime( $scheduleEnd );
599
600 if ( $currentTime > $endTime ) {
601 return true;
602 }
603
604 return false;
605 }
606
607 public function isOpenForm( $scheduleStart, $scheduleEnd ) {
608 $currentTime = current_time( 'timestamp' );
609 $startTime = strtotime( $scheduleStart );
610 $endTime = strtotime( $scheduleEnd );
611
612 if ( $currentTime > $startTime && $currentTime < $endTime ) {
613 return true;
614 }
615
616 return false;
617 }
618
619 public function isFormStatusClosed( $formSettings, $entries ) {
620 if ( $formSettings['schedule_form'] === 'true' && $this->isPendingForm( $formSettings['schedule_start'] ) ) {
621 return true;
622 }
623
624 if ( $formSettings['schedule_form'] === 'true' && $this->isExpiredForm( $formSettings['schedule_end'] ) ) {
625 return true;
626 }
627
628 if ( $formSettings['limit_entries'] === 'true' && $entries >= $formSettings['limit_number'] ) {
629 return true;
630 }
631
632 return false;
633 }
634 }
635