PluginProbe
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More / 6.8
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More v6.8
6.35 6.34 6.33.1 6.33 6.32.1 6.32 6.31 6.25 6.25.1 6.26 6.26.1 6.27 6.28 6.29 6.3 6.3.1 6.3.2 6.30 6.4 6.4.1 6.4.2 6.5 6.5.1 6.5.2 6.5.3 All 141 releases
← All changes | classes/helpers/FrmAppHelper.php +343 -111 6.3.16.8 View file →
@@ -3,13 +3,28 @@
3 3 die( 'You are not allowed to call this page directly.' );
4 4 }
5 5
6 6 class FrmAppHelper {
7 - public static $db_version = 98; // Version of the database we are moving to.
8 - public static $pro_db_version = 37; //deprecated
9 - public static $font_version = 7;
7 + /**
8 + * Version of the database we are moving to.
9 + *
10 + * @var int
11 + */
12 + public static $db_version = 101;
10 13
11 14 /**
15 + * Deprecated.
16 + *
17 + * @var int
18 + */
19 + public static $pro_db_version = 37;
20 +
21 + /**
22 + * @var float
23 + */
24 + public static $font_version = 7;
25 +
26 + /**
12 27 * @var bool $added_gmt_offset_filter
13 28 */
14 29 private static $added_gmt_offset_filter = false;
15 30
@@ -14,16 +29,21 @@
14 29 private static $added_gmt_offset_filter = false;
15 30
16 31 /**
17 32 * @since 2.0
33 + *
34 + * @var string
18 35 */
19 - public static $plug_version = '6.3.1';
36 + public static $plug_version = '6.8';
20 37
21 38 /**
39 + * @var bool
40 + */
41 + private static $included_svg = false;
42 +
43 + /**
22 44 * @since 1.07.02
23 45 *
24 - * @param none
25 - *
26 46 * @return string The version of this plugin
27 47 */
28 48 public static function plugin_version() {
29 49 return self::$plug_version;
@@ -148,12 +168,28 @@
148 168
149 169 public static function get_menu_name() {
150 170 $frm_settings = self::get_settings();
151 171
152 - return $frm_settings->menu;
172 + return FrmAddonsController::is_license_expired() ? 'Formidable' : $frm_settings->menu;
153 173 }
154 174
155 175 /**
176 + * Determine if the current branding is set to 'formidable'.
177 + *
178 + * Checks the menu title, retrieved through get_menu_name,
179 + * and verifies if it matches the 'formidable' branding.
180 + *
181 + * @since 6.4.2
182 + *
183 + * @return bool True if the menu title is 'formidable', false otherwise.
184 + */
185 + public static function is_formidable_branding() {
186 + $menu_title = self::get_menu_name();
187 +
188 + return 'formidable' === strtolower( trim( $menu_title ) );
189 + }
190 +
191 + /**
156 192 * @since 3.05
157 193 */
158 194 public static function svg_logo( $atts = array() ) {
159 195 $defaults = array(
@@ -243,9 +279,9 @@
243 279 * Check for certain page in Formidable settings
244 280 *
245 281 * @since 2.0
246 282 *
247 - * @param string $page The name of the page to check
283 + * @param string $page The name of the page to check.
248 284 *
249 285 * @return boolean
250 286 */
251 287 public static function is_admin_page( $page = 'formidable' ) {
@@ -290,10 +326,8 @@
290 326 * Check for the form preview page
291 327 *
292 328 * @since 2.0
293 329 *
294 - * @param None
295 - *
296 330 * @return boolean
297 331 */
298 332 public static function is_preview_page() {
299 333 global $pagenow;
@@ -306,10 +340,8 @@
306 340 * Check for ajax except the form preview page
307 341 *
308 342 * @since 2.0
309 343 *
310 - * @param None
311 - *
312 344 * @return boolean
313 345 */
314 346 public static function doing_ajax() {
315 347 return wp_doing_ajax() && ! self::is_preview_page();
@@ -349,10 +381,10 @@
349 381 * Check if value contains blank value or empty array
350 382 *
351 383 * @since 2.0
352 384 *
353 - * @param mixed $value - value to check
354 - * @param string
385 + * @param mixed $value Value to check.
386 + * @param string $empty
355 387 *
356 388 * @return boolean
357 389 */
358 390 public static function is_empty_value( $value, $empty = '' ) {
@@ -376,8 +408,28 @@
376 408 return isset( $_SERVER[ $value ] ) ? wp_strip_all_tags( wp_unslash( $_SERVER[ $value ] ) ) : '';
377 409 }
378 410
379 411 /**
412 + * Get the server OS
413 + *
414 + * @since 6.4.2
415 + *
416 + * @return string
417 + */
418 + public static function get_server_os() {
419 + if ( function_exists( 'php_uname' ) ) {
420 + return php_uname( 's' );
421 + }
422 +
423 + if ( ! defined( 'PHP_OS' ) ) {
424 + return '';
425 + }
426 +
427 + // match the same response for Windows server as php_uname('s')
428 + return in_array( PHP_OS, array( 'WIN32', 'WINNT', 'Windows_NT' ), true ) ? 'Windows NT' : PHP_OS;
429 + }
430 +
431 + /**
380 432 * Check for the IP address in several places (when custom headers are enabled).
381 433 * Used by [ip] shortcode.
382 434 *
383 435 * @return string The IP address of the current user
@@ -392,9 +444,10 @@
392 444 }
393 445
394 446 $key = self::get_server_value( $key );
395 447 foreach ( explode( ',', $key ) as $ip ) {
396 - $ip = trim( $ip ); // Just to be safe.
448 + // Just to be safe.
449 + $ip = trim( $ip );
397 450
398 451 if ( filter_var( $ip, FILTER_VALIDATE_IP, FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE ) !== false ) {
399 452 return sanitize_text_field( $ip );
400 453 }
@@ -537,14 +590,14 @@
537 590 );
538 591 $args = wp_parse_args( $args, $defaults );
539 592
540 593 $value = $args['default'];
541 - if ( $args['type'] == 'get' ) {
594 + if ( $args['type'] === 'get' ) {
542 595 if ( $_GET && isset( $_GET[ $args['param'] ] ) ) {
543 596 // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.InputNotSanitized, WordPress.Security.NonceVerification.Missing
544 597 $value = wp_unslash( $_GET[ $args['param'] ] );
545 598 }
546 - } elseif ( $args['type'] == 'post' ) {
599 + } elseif ( $args['type'] === 'post' ) {
547 600 if ( isset( $_POST[ $args['param'] ] ) ) { // phpcs:ignore WordPress.Security.NonceVerification.Missing
548 601 // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.InputNotSanitized, WordPress.Security.NonceVerification.Missing
549 602 $value = wp_unslash( $_POST[ $args['param'] ] );
550 603 if ( $args['serialized'] === true && is_serialized_string( $value ) && is_serialized( $value ) ) {
@@ -604,15 +657,52 @@
604 657 }
605 658
606 659 /**
607 660 * @since 4.0.04
661 + *
662 + * @param mixed $value
663 + * @return void
608 664 */
609 665 public static function sanitize_with_html( &$value ) {
610 - self::sanitize_value( 'wp_kses_post', $value );
666 + if ( current_user_can( 'frm_edit_entries' ) || current_user_can( 'administrator' ) ) {
667 + // Only strip unsafe HTML like scripts for a privileged user submitting a form.
668 + self::sanitize_value( 'wp_kses_post', $value );
669 + } else {
670 + self::sanitize_value( self::class . '::strip_most_html', $value );
671 + }
611 672 self::decode_specialchars( $value );
612 673 }
613 674
614 675 /**
676 + * Allow only a small set of very basic HTML for unprivileged users.
677 + *
678 + * @since 6.7.1
679 + *
680 + * @param string $value
681 + */
682 + public static function strip_most_html( $value ) {
683 + $allowed_html = array(
684 + 'b' => array(),
685 + 'br' => array(),
686 + 'strong' => array(),
687 + 'p' => array(),
688 + 'i' => array(),
689 + 'ul' => array(),
690 + 'ol' => array(),
691 + 'li' => array(),
692 + );
693 +
694 + /**
695 + * @since 6.7.1
696 + *
697 + * @param array $allowed_html
698 + */
699 + $allowed_html = apply_filters( 'frm_allowed_form_input_html', $allowed_html );
700 +
701 + return wp_kses( $value, $allowed_html );
702 + }
703 +
704 + /**
615 705 * Do wp_specialchars_decode to get back '&' that wp_kses_post might have turned to '&'
616 706 * this MUST be done, else we'll be back to the '& entity' problem.
617 707 *
618 708 * @since 4.0.04
@@ -646,10 +736,12 @@
646 736 $translation = array(
647 737 '"' => '"',
648 738 '"' => '"',
649 739 '"' => '"',
650 - '&lt; ' => '< ', // The space preserves the HTML.
651 - '&#060; ' => '< ', // The space preserves the HTML.
740 + // The space preserves the HTML.
741 + '&lt; ' => '< ',
742 + // The space preserves the HTML.
743 + '&#060; ' => '< ',
652 744 '&gt;' => '>',
653 745 '&#062;' => '>',
654 746 '&amp;' => '&',
655 747 '&#038;' => '&',
@@ -676,10 +768,10 @@
676 768 * Sanitize the value, and allow some HTML
677 769 *
678 770 * @since 2.0
679 771 *
680 - * @param string $value
681 - * @param array|string $allowed 'all' for everything included as defaults
772 + * @param string $value
773 + * @param array|string $allowed 'all' for everything included as defaults.
682 774 *
683 775 * @return string
684 776 */
685 777 public static function kses( $value, $allowed = array() ) {
@@ -915,9 +1007,9 @@
915 1007 *
916 1008 * @since 2.0
917 1009 */
918 1010 public static function remove_get_action() {
919 - if ( ! isset( $_GET ) ) {
1011 + if ( empty( $_GET ) ) {
920 1012 return;
921 1013 }
922 1014
923 1015 $action_name = isset( $_GET['action'] ) ? 'action' : ( isset( $_GET['action2'] ) ? 'action2' : '' );
@@ -966,14 +1058,16 @@
966 1058 $html_atts = self::array_to_html_params( $atts );
967 1059
968 1060 $icon = trim( str_replace( array( 'frm_icon_font', 'frmfont ' ), '', $class ) );
969 1061
970 - // Replace icons that have been removed.
1062 + // Replace icons that have been removed or renamed.
971 1063 $deprecated = array(
972 - 'frm_clone_solid_icon' => 'frm_clone_icon',
1064 + 'frm_clone_solid_icon' => 'frm_clone_icon',
1065 + 'frm_keyalt_icon' => 'frm_key_icon',
1066 + 'frm_keyalt_solid_icon' => 'frm_key_solid_icon',
973 1067 );
974 1068 if ( isset( $deprecated[ $icon ] ) ) {
975 - $icon = $deprecated[ $icon ];
1069 + $icon = $deprecated[ $icon ];
976 1070 $class = str_replace( $icon, $deprecated[ $icon ], $class );
977 1071 }
978 1072
979 1073 if ( $icon === $class ) {
@@ -1073,11 +1167,18 @@
1073 1167 /**
1074 1168 * Include svg images.
1075 1169 *
1076 1170 * @since 4.0.02
1171 + * @return void
1077 1172 */
1078 1173 public static function include_svg() {
1079 - include_once self::plugin_path() . '/images/icons.svg';
1174 + if ( self::$included_svg ) {
1175 + return;
1176 + }
1177 +
1178 + // Use readfile instead of include_once because of a default security rule in Snuffleupagus.
1179 + readfile( self::plugin_path() . '/images/icons.svg' );
1180 + self::$included_svg = true;
1080 1181 }
1081 1182
1082 1183 /**
1083 1184 * Convert an associative array to HTML values.
@@ -1194,8 +1295,10 @@
1194 1295 * Render a button for a new item (Form, Application, etc).
1195 1296 *
1196 1297 * @since 3.0
1197 1298 * @param array $atts {
1299 + * Details about the button.
1300 + *
1198 1301 * @type array $link_hook Custom link hook, calls do_action and exits early.
1199 1302 * @type string $new_link Href value, default #.
1200 1303 * @type string $class Custom class names, space separated.
1201 1304 * @type string $button_text Button text. Default "Add New".
@@ -1207,9 +1310,9 @@
1207 1310 do_action( $atts['link_hook']['hook'], $atts['link_hook']['param'] );
1208 1311 return;
1209 1312 }
1210 1313
1211 - if ( empty( $atts['new_link'] ) && empty( $atts['trigger_new_form_modal'] ) && empty( $atts['class'] ) ) {
1314 + if ( empty( $atts['new_link'] ) && empty( $atts['create_form'] ) && empty( $atts['class'] ) ) {
1212 1315 // Do not render a button if none of these attributes are set.
1213 1316 return;
1214 1317 }
1215 1318
@@ -1215,12 +1318,8 @@
1215 1318
1216 1319 $href = ! empty( $atts['new_link'] ) ? esc_url( $atts['new_link'] ) : '#';
1217 1320 $class = 'button button-primary frm-button-primary';
1218 1321
1219 - if ( ! empty( $atts['trigger_new_form_modal'] ) ) {
1220 - $class .= ' frm-trigger-new-form-modal';
1221 - }
1222 -
1223 1322 if ( ! empty( $atts['class'] ) ) {
1224 1323 $class .= ' ' . $atts['class'];
1225 1324 }
1226 1325
@@ -1285,11 +1384,14 @@
1285 1384 }
1286 1385 }
1287 1386
1288 1387 /**
1289 - * Save all front-end js scripts into a single file
1388 + * Save all front-end js scripts into a single file.
1389 + * And save an additional single file of all front-end Stripe JS scripts.
1290 1390 *
1291 1391 * @since 3.0
1392 + *
1393 + * @return void
1292 1394 */
1293 1395 public static function save_combined_js() {
1294 1396 $file_atts = apply_filters(
1295 1397 'frm_js_location',
@@ -1302,10 +1404,34 @@
1302 1404
1303 1405 $files = array(
1304 1406 self::plugin_path() . '/js/formidable.min.js',
1305 1407 );
1408 + /**
1409 + * @param array $files
1410 + */
1306 1411 $files = apply_filters( 'frm_combined_js_files', $files );
1307 1412 $new_file->combine_files( $files );
1413 +
1414 + // Create the minified Stripe Script.
1415 + $file_atts = apply_filters(
1416 + 'frm_stripe_js_location',
1417 + array(
1418 + 'file_name' => 'frmstrp.min.js',
1419 + 'new_file_path' => self::plugin_path() . '/js',
1420 + )
1421 + );
1422 + $new_file = new FrmCreateFile( $file_atts );
1423 + $files = array(
1424 + FrmStrpLiteAppHelper::plugin_path() . 'js/frmstrp.min.js',
1425 + );
1426 +
1427 + /**
1428 + * @since 6.5
1429 + *
1430 + * @param array $files
1431 + */
1432 + $files = apply_filters( 'frm_stripe_combined_js_files', $files );
1433 + $new_file->combine_files( $files );
1308 1434 }
1309 1435
1310 1436 /**
1311 1437 * Check a value from a shortcode to see if true or false.
@@ -1312,9 +1438,9 @@
1312 1438 * True when value is 1, true, 'true', 'yes'
1313 1439 *
1314 1440 * @since 1.07.10
1315 1441 *
1316 - * @param string $value The value to compare
1442 + * @param string $value The value to compare.
1317 1443 *
1318 1444 * @return boolean True or False
1319 1445 */
1320 1446 public static function is_true( $value ) {
@@ -1537,11 +1663,11 @@
1537 1663 return $link;
1538 1664 }
1539 1665
1540 1666 /**
1541 - * @param string $field_name
1542 - * @param string|array $capability
1543 - * @param string $multiple 'single' and 'multiple'
1667 + * @param string $field_name
1668 + * @param string|array $capability
1669 + * @param string $multiple 'single' and 'multiple'.
1544 1670 */
1545 1671 public static function wp_roles_dropdown( $field_name, $capability, $multiple = 'single' ) {
1546 1672 ?>
1547 1673 <select name="<?php echo esc_attr( $field_name ); ?>" id="<?php echo esc_attr( $field_name ); ?>"
@@ -1554,9 +1680,9 @@
1554 1680
1555 1681 /**
1556 1682 * @since 4.07
1557 1683 * @param array|string $selected
1558 - * @param string $current
1684 + * @param string $current
1559 1685 */
1560 1686 private static function selected( $selected, $current ) {
1561 1687 if ( is_callable( 'FrmProAppHelper::selected' ) ) {
1562 1688 FrmProAppHelper::selected( $selected, $current );
@@ -1602,9 +1728,8 @@
1602 1728 $pro_cap = array(
1603 1729 'frm_create_entries' => __( 'Add Entries from Admin Area', 'formidable' ),
1604 1730 'frm_edit_entries' => __( 'Edit Entries from Admin Area', 'formidable' ),
1605 1731 'frm_view_reports' => __( 'View Reports', 'formidable' ),
1606 - 'frm_edit_displays' => __( 'Add/Edit Views', 'formidable' ),
1607 1732 );
1608 1733 /**
1609 1734 * @since 5.3.1
1610 1735 *
@@ -1611,8 +1736,14 @@
1611 1736 * @param array<string,string> $pro_cap
1612 1737 */
1613 1738 $pro_cap = apply_filters( 'frm_pro_capabilities', $pro_cap );
1614 1739
1740 + if ( ! array_key_exists( 'frm_edit_displays', $pro_cap ) && is_callable( 'FrmProAppHelper::views_is_installed' ) && FrmProAppHelper::views_is_installed() ) {
1741 + // For backward compatibility, add the Add/Edit Views permission if Pro is not up to date.
1742 + // This was added in 6.5.4. Remove this in the future.
1743 + $pro_cap['frm_edit_displays'] = __( 'Add/Edit Views', 'formidable' );
1744 + }
1745 +
1615 1746 if ( 'pro_only' === $type ) {
1616 1747 return $pro_cap;
1617 1748 }
1618 1749
@@ -1627,9 +1758,9 @@
1627 1758 * @return array<string,string>
1628 1759 */
1629 1760 private static function get_lite_capabilities() {
1630 1761 return array(
1631 - 'frm_view_forms' => __( 'View Forms', 'formidable' ),
1762 + 'frm_view_forms' => __( 'View Forms List', 'formidable' ),
1632 1763 'frm_edit_forms' => __( 'Add and Edit Forms', 'formidable' ),
1633 1764 'frm_delete_forms' => __( 'Delete Forms', 'formidable' ),
1634 1765 'frm_change_settings' => __( 'Access this Settings Page', 'formidable' ),
1635 1766 'frm_view_entries' => __( 'View Entries from Admin Area', 'formidable' ),
@@ -1838,9 +1969,9 @@
1838 1969 foreach ( $array as $key => $value ) {
1839 1970 if ( is_array( $value ) ) {
1840 1971 $return = array_merge( $return, self::array_flatten( $value, $keys ) );
1841 1972 } else {
1842 - if ( $keys == 'keep' ) {
1973 + if ( $keys === 'keep' ) {
1843 1974 $return[ $key ] = $value;
1844 1975 } else {
1845 1976 $return[] = $value;
1846 1977 }
@@ -1924,9 +2055,9 @@
1924 2055 return $user_id;
1925 2056 }
1926 2057
1927 2058 $user_id = sanitize_text_field( $user_id );
1928 - if ( $user_id == 'current' ) {
2059 + if ( $user_id === 'current' ) {
1929 2060 $user_id = get_current_user_id();
1930 2061 } else {
1931 2062 if ( is_email( $user_id ) ) {
1932 2063 $user = get_user_by( 'email', $user_id );
@@ -2006,9 +2137,9 @@
2006 2137 ++$suffix;
2007 2138 } while ( in_array( $key_check, $similar_keys, true ) );
2008 2139
2009 2140 $key = $key_check;
2010 - }
2141 + }//end if
2011 2142
2012 2143 return $key;
2013 2144 }
2014 2145
@@ -2052,9 +2183,11 @@
2052 2183 * @return string
2053 2184 */
2054 2185 private static function generate_new_key( $num_chars ) {
2055 2186 $max_slug_value = pow( 36, $num_chars );
2056 - $min_slug_value = 37; // we want to have at least 2 characters in the slug
2187 +
2188 + // We want to have at least 2 characters in the slug.
2189 + $min_slug_value = 37;
2057 2190 return base_convert( rand( $min_slug_value, $max_slug_value ), 10, 36 );
2058 2191 }
2059 2192
2060 2193 /**
@@ -2083,9 +2216,14 @@
2083 2216
2084 2217 /**
2085 2218 * Editing a Form or Entry
2086 2219 *
2087 - * @param string $table
2220 + * @param object $record
2221 + * @param string $table
2222 + * @param array|string $fields
2223 + * @param bool $default
2224 + * @param array $post_values
2225 + * @param array $args
2088 2226 *
2089 2227 * @return bool|array
2090 2228 */
2091 2229 public static function setup_edit_vars( $record, $table, $fields = '', $default = false, $post_values = array(), $args = array() ) {
@@ -2159,9 +2297,9 @@
2159 2297 );
2160 2298 } else {
2161 2299 $meta_value = FrmEntryMeta::get_meta_value( $record, $field->id );
2162 2300 }
2163 - }
2301 + }//end if
2164 2302
2165 2303 $field_type = isset( $post_values['field_options'][ 'type_' . $field->id ] ) ? $post_values['field_options'][ 'type_' . $field->id ] : $field->type;
2166 2304 if ( isset( $post_values['item_meta'][ $field->id ] ) ) {
2167 2305 $new_value = $post_values['item_meta'][ $field->id ];
@@ -2209,9 +2347,12 @@
2209 2347 );
2210 2348 }
2211 2349
2212 2350 /**
2351 + * @param object $record
2213 2352 * @param string $table
2353 + * @param array $post_values
2354 + * @param array $values
2214 2355 */
2215 2356 private static function fill_form_opts( $record, $table, $post_values, array &$values ) {
2216 2357 if ( $table == 'entries' ) {
2217 2358 $form = $record->form_id;
@@ -2325,11 +2466,37 @@
2325 2466
2326 2467 unset( $total_len, $word );
2327 2468 }
2328 2469
2470 + $sub = self::maybe_force_truncate_on_string_with_no_spaces( $sub, $length );
2471 +
2329 2472 return $sub . ( ( $len < $original_len ) ? $continue : '' );
2330 2473 }
2331 2474
2475 + /**
2476 + * If the string is still too long because there may not have been any spaces, force truncate.
2477 + *
2478 + * @since 6.5.4
2479 + *
2480 + * @param string $sub Current substring.
2481 + * @param int $length The length limit.
2482 + * @return string
2483 + */
2484 + private static function maybe_force_truncate_on_string_with_no_spaces( $sub, $length ) {
2485 + if ( strlen( $sub ) < $length + 50 ) {
2486 + // If the string isn't way over the limit, leave it.
2487 + return $sub;
2488 + }
2489 +
2490 + $first_space = strpos( $sub, ' ', $length );
2491 + if ( false !== $first_space ) {
2492 + // Ignore anything with spaces.
2493 + return $sub;
2494 + }
2495 +
2496 + return substr( $sub, 0, $length + 10 );
2497 + }
2498 +
2332 2499 public static function mb_function( $function_names, $args ) {
2333 2500 $mb_function_name = $function_names[0];
2334 2501 $function_name = $function_names[1];
2335 2502 if ( function_exists( $mb_function_name ) ) {
@@ -2386,12 +2553,12 @@
2386 2553 return date_i18n( $date_format, strtotime( $date ) );
2387 2554 }
2388 2555
2389 2556 /**
2390 - * Gets the time ago in words
2557 + * Gets the time ago in words.
2391 2558 *
2392 - * @param int $from in seconds
2393 - * @param int|string $to in seconds
2559 + * @param int $from In seconds.
2560 + * @param int|string $to In seconds.
2394 2561 *
2395 2562 * @return string $time_ago
2396 2563 */
2397 2564 public static function human_time_diff( $from, $to = '', $levels = 1 ) {
@@ -2554,9 +2721,12 @@
2554 2721
2555 2722 // Pagination Methods.
2556 2723
2557 2724 /**
2725 + * @param integer $r_count
2558 2726 * @param integer $current_p
2727 + * @param integer $p_size
2728 + * @return int
2559 2729 */
2560 2730 public static function get_last_record_num( $r_count, $current_p, $p_size ) {
2561 2731 return ( ( $r_count < ( $current_p * $p_size ) ) ? $r_count : ( $current_p * $p_size ) );
2562 2732 }
@@ -2561,9 +2731,12 @@
2561 2731 return ( ( $r_count < ( $current_p * $p_size ) ) ? $r_count : ( $current_p * $p_size ) );
2562 2732 }
2563 2733
2564 2734 /**
2735 + * @param integer $r_count
2565 2736 * @param integer $current_p
2737 + * @param integer $p_size
2738 + * @return int
2566 2739 */
2567 2740 public static function get_first_record_num( $r_count, $current_p, $p_size ) {
2568 2741 if ( $current_p == 1 ) {
2569 2742 return 1;
@@ -2617,12 +2790,12 @@
2617 2790 self::add_value_to_array( $name, $l4, $this_val, $vars[ $l1 ][ $l2 ][ $l3 ] );
2618 2791 }
2619 2792
2620 2793 unset( $this_val, $n );
2621 - }
2794 + }//end foreach
2622 2795
2623 2796 unset( $last, $jv );
2624 - }
2797 + }//end foreach
2625 2798
2626 2799 return $vars;
2627 2800 }
2628 2801
@@ -2879,12 +3052,14 @@
2879 3052 return $value;
2880 3053 }
2881 3054
2882 3055 /**
3056 + * Echo The javascript to open and highlight the Formidable menu
3057 + *
2883 3058 * @since 1.07.10
2884 3059 *
2885 - * @param string $post_type The name of the post type that may need to be highlighted
2886 - * echo The javascript to open and highlight the Formidable menu
3060 + * @param string $post_type The name of the post type that may need to be highlighted.
3061 + * @return void
2887 3062 */
2888 3063 public static function maybe_highlight_menu( $post_type ) {
2889 3064 global $post;
2890 3065
@@ -2939,13 +3114,10 @@
2939 3114 */
2940 3115 public static function localize_script( $location ) {
2941 3116 global $wp_scripts;
2942 3117
2943 - $ajax_url = admin_url( 'admin-ajax.php', is_ssl() ? 'admin' : 'http' );
2944 - $ajax_url = apply_filters( 'frm_ajax_url', $ajax_url );
2945 -
2946 3118 $script_strings = array(
2947 - 'ajax_url' => $ajax_url,
3119 + 'ajax_url' => esc_url_raw( self::get_ajax_url() ),
2948 3120 'images_url' => self::plugin_url() . '/images',
2949 3121 'loading' => __( 'Loading&hellip;', 'formidable' ),
2950 3122 'remove' => __( 'Remove', 'formidable' ),
2951 3123 'offset' => apply_filters( 'frm_scroll_offset', 4 ),
@@ -2959,75 +3131,103 @@
2959 3131 'include_alert_role' => self::should_include_alert_role_on_field_errors(),
2960 3132 );
2961 3133
2962 3134 $data = $wp_scripts->get_data( 'formidable', 'data' );
2963 - if ( empty( $data ) ) {
3135 + if ( ! $data ) {
2964 3136 wp_localize_script( 'formidable', 'frm_js', $script_strings );
2965 3137 }
2966 3138
2967 - if ( $location == 'admin' ) {
3139 + if ( $location === 'admin' ) {
2968 3140 $frm_settings = self::get_settings();
2969 3141 $admin_script_strings = array(
2970 - 'desc' => __( '(Click to add description)', 'formidable' ),
2971 - 'blank' => __( '(Blank)', 'formidable' ),
2972 - 'no_label' => __( '(no label)', 'formidable' ),
2973 - 'saving' => '', // Deprecated in 6.0.
2974 - 'saved' => '', // Deprecated in 6.0.
2975 - 'ok' => __( 'OK', 'formidable' ),
2976 - 'cancel' => __( 'Cancel', 'formidable' ),
2977 - 'default_label' => __( 'Default', 'formidable' ),
2978 - 'clear_default' => __( 'Clear default value when typing', 'formidable' ),
2979 - 'no_clear_default' => __( 'Do not clear default value when typing', 'formidable' ),
2980 - 'valid_default' => __( 'Default value will pass form validation', 'formidable' ),
2981 - 'no_valid_default' => __( 'Default value will NOT pass form validation', 'formidable' ),
2982 - 'confirm' => __( 'Are you sure?', 'formidable' ),
2983 - 'conf_delete' => __( 'Are you sure you want to delete this field and all data associated with it?', 'formidable' ),
2984 - 'conf_delete_sec' => __( 'All fields inside this Section will be deleted along with their data. Are you sure you want to delete this group of fields?', 'formidable' ),
2985 - 'conf_no_repeat' => __( 'Warning: If you have entries with multiple rows, all but the first row will be lost.', 'formidable' ),
2986 - 'default_unique' => $frm_settings->unique_msg,
2987 - 'default_conf' => __( 'The entered values do not match', 'formidable' ),
2988 - 'enter_email' => __( 'Enter Email', 'formidable' ),
2989 - 'confirm_email' => __( 'Confirm Email', 'formidable' ),
2990 - 'conditional_text' => __( 'Conditional content here', 'formidable' ),
2991 - 'new_option' => __( 'New Option', 'formidable' ),
2992 - 'css_invalid_size' => __( 'In certain browsers (e.g. Firefox) text will not display correctly if the field height is too small relative to the field padding and text size. Please increase your field height or decrease your field padding.', 'formidable' ),
2993 - 'enter_password' => __( 'Enter Password', 'formidable' ),
2994 - 'confirm_password' => __( 'Confirm Password', 'formidable' ),
2995 - 'import_complete' => __( 'Import Complete', 'formidable' ),
2996 - 'updating' => __( 'Please wait while your site updates.', 'formidable' ),
2997 - 'no_save_warning' => __( 'Warning: There is no way to retrieve unsaved entries.', 'formidable' ),
2998 - 'private_label' => __( 'Private', 'formidable' ),
2999 - 'jquery_ui_url' => '',
3000 - 'pro_url' => is_callable( 'FrmProAppHelper::plugin_url' ) ? FrmProAppHelper::plugin_url() : '',
3001 - 'no_licenses' => __( 'No new licenses were found', 'formidable' ),
3002 - 'unmatched_parens' => __( 'This calculation has at least one unmatched ( ) { } [ ].', 'formidable' ),
3003 - 'view_shortcodes' => __( 'This calculation may have shortcodes that work in Views but not forms.', 'formidable' ),
3004 - 'text_shortcodes' => __( 'This calculation may have shortcodes that work in text calculations but not numeric calculations.', 'formidable' ),
3005 - 'only_one_action' => __( 'This form action is limited to one per form. Please edit the existing form action.', 'formidable' ),
3006 - 'unsafe_params' => FrmFormsHelper::reserved_words(),
3142 + 'desc' => __( '(Click to add description)', 'formidable' ),
3143 + 'blank' => __( '(Blank)', 'formidable' ),
3144 + 'no_label' => __( '(no label)', 'formidable' ),
3145 + 'ok' => __( 'OK', 'formidable' ),
3146 + 'cancel' => __( 'Cancel', 'formidable' ),
3147 + 'default_label' => __( 'Default', 'formidable' ),
3148 + 'clear_default' => __( 'Clear default value when typing', 'formidable' ),
3149 + 'no_clear_default' => __( 'Do not clear default value when typing', 'formidable' ),
3150 + 'valid_default' => __( 'Default value will pass form validation', 'formidable' ),
3151 + 'no_valid_default' => __( 'Default value will NOT pass form validation', 'formidable' ),
3152 + 'confirm' => __( 'Are you sure?', 'formidable' ),
3153 + 'conf_delete' => __( 'Are you sure you want to delete this field and all data associated with it?', 'formidable' ),
3154 + 'conf_delete_sec' => __( 'All fields inside this Section will be deleted along with their data. Are you sure you want to delete this group of fields?', 'formidable' ),
3155 + 'conf_no_repeat' => __( 'Warning: If you have entries with multiple rows, all but the first row will be lost.', 'formidable' ),
3156 + 'default_unique' => $frm_settings->unique_msg,
3157 + 'default_conf' => __( 'The entered values do not match', 'formidable' ),
3158 + 'enter_email' => __( 'Enter Email', 'formidable' ),
3159 + 'confirm_email' => __( 'Confirm Email', 'formidable' ),
3160 + 'conditional_text' => __( 'Conditional content here', 'formidable' ),
3161 + 'new_option' => __( 'New Option', 'formidable' ),
3162 + 'css_invalid_size' => __( 'In certain browsers (e.g. Firefox) text will not display correctly if the field height is too small relative to the field padding and text size. Please increase your field height or decrease your field padding.', 'formidable' ),
3163 + 'enter_password' => __( 'Enter Password', 'formidable' ),
3164 + 'confirm_password' => __( 'Confirm Password', 'formidable' ),
3165 + 'import_complete' => __( 'Import Complete', 'formidable' ),
3166 + 'updating' => __( 'Please wait while your site updates.', 'formidable' ),
3167 + 'no_save_warning' => __( 'Warning: There is no way to retrieve unsaved entries.', 'formidable' ),
3168 + 'private_label' => __( 'Private', 'formidable' ),
3169 + 'jquery_ui_url' => '',
3170 + 'pro_url' => is_callable( 'FrmProAppHelper::plugin_url' ) ? FrmProAppHelper::plugin_url() : '',
3171 + 'no_licenses' => __( 'No new licenses were found', 'formidable' ),
3172 + 'unmatched_parens' => __( 'This calculation has at least one unmatched ( ) { } [ ].', 'formidable' ),
3173 + 'view_shortcodes' => __( 'This calculation may have shortcodes that work in Views but not forms.', 'formidable' ),
3174 + 'text_shortcodes' => __( 'This calculation may have shortcodes that work in text calculations but not numeric calculations.', 'formidable' ),
3175 + 'only_one_action' => __( 'This form action is limited to one per form. Please edit the existing form action.', 'formidable' ),
3176 + 'unsafe_params' => FrmFormsHelper::reserved_words(),
3007 3177 /* Translators: %s is the name of a Detail Page Slug that is a reserved word.*/
3008 - 'slug_is_reserved' => sprintf( __( 'The Detail Page Slug "%s" is reserved by WordPress. This may cause problems. Is this intentional?', 'formidable' ), '****' ),
3178 + 'slug_is_reserved' => sprintf( __( 'The Detail Page Slug "%s" is reserved by WordPress. This may cause problems. Is this intentional?', 'formidable' ), '****' ),
3009 3179 /* Translators: %s is the name of a parameter that is a reserved word. More than one word could be listed here, though that would not be common. */
3010 - 'param_is_reserved' => sprintf( __( 'The parameter "%s" is reserved by WordPress. This may cause problems when included in the URL. Is this intentional? ', 'formidable' ), '****' ),
3011 - 'reserved_words' => __( 'See the list of reserved words in WordPress.', 'formidable' ),
3012 - 'repeat_limit_min' => __( 'Please enter a Repeat Limit that is greater than 1.', 'formidable' ),
3013 - 'checkbox_limit' => __( 'Please select a limit between 0 and 200.', 'formidable' ),
3014 - 'install' => __( 'Install', 'formidable' ),
3015 - 'active' => __( 'Active', 'formidable' ),
3016 - 'select_a_field' => __( 'Select a Field', 'formidable' ),
3017 - 'no_items_found' => __( 'No items found.', 'formidable' ),
3180 + 'param_is_reserved' => sprintf( __( 'The parameter "%s" is reserved by WordPress. This may cause problems when included in the URL. Is this intentional? ', 'formidable' ), '****' ),
3181 + 'reserved_words' => __( 'See the list of reserved words in WordPress.', 'formidable' ),
3182 + 'repeat_limit_min' => __( 'Please enter a Repeat Limit that is greater than 1.', 'formidable' ),
3183 + 'checkbox_limit' => __( 'Please select a limit between 0 and 200.', 'formidable' ),
3184 + 'install' => __( 'Install', 'formidable' ),
3185 + 'active' => __( 'Active', 'formidable' ),
3186 + 'installed' => __( 'Installed', 'formidable' ),
3187 + 'not_installed' => __( 'Not Installed', 'formidable' ),
3188 + 'select_a_field' => __( 'Select a Field', 'formidable' ),
3189 + 'no_items_found' => __( 'No items found.', 'formidable' ),
3018 3190 'field_already_used' => __( 'Oops. You have already used that field.', 'formidable' ),
3191 +
3192 + // Deprecated in 6.0.
3193 + 'saving' => '',
3194 +
3195 + // Deprecated in 6.0.
3196 + 'saved' => '',
3197 +
3198 + // translators: %1$s: HTML open tag, %2$s: HTML end tag.
3199 + 'holdShiftMsg' => esc_html__( 'You can hold %1$sShift%2$s on your keyboard to select multiple fields', 'formidable' ),
3019 3200 );
3201 + /**
3202 + * @param array $admin_script_strings
3203 + */
3020 3204 $admin_script_strings = apply_filters( 'frm_admin_script_strings', $admin_script_strings );
3021 3205
3022 3206 $data = $wp_scripts->get_data( 'formidable_admin', 'data' );
3023 - if ( empty( $data ) ) {
3207 + if ( ! $data ) {
3024 3208 wp_localize_script( 'formidable_admin', 'frm_admin_js', $admin_script_strings );
3025 3209 }
3026 - }
3210 + }//end if
3027 3211 }
3028 3212
3029 3213 /**
3214 + * @since 6.5
3215 + *
3216 + * @return string
3217 + */
3218 + public static function get_ajax_url() {
3219 + $ajax_url = admin_url( 'admin-ajax.php', is_ssl() ? 'admin' : 'http' );
3220 +
3221 + /**
3222 + * @since 2.0.13
3223 + *
3224 + * @param string $ajax_url
3225 + */
3226 + return apply_filters( 'frm_ajax_url', $ajax_url );
3227 + }
3228 +
3229 + /**
3030 3230 * Returns whether or not the first errored input should be auto-focused (default true).
3031 3231 *
3032 3232 * @since 5.2.05
3033 3233 *
@@ -3052,9 +3252,9 @@
3052 3252 * Echo the message on the plugins listing page
3053 3253 *
3054 3254 * @since 1.07.10
3055 3255 *
3056 - * @param float $min_version The version the add-on requires
3256 + * @param float $min_version The version the add-on requires.
3057 3257 */
3058 3258 public static function min_version_notice( $min_version ) {
3059 3259 $frm_version = self::plugin_version();
3060 3260
@@ -3380,8 +3580,18 @@
3380 3580 return apply_filters( 'frm_images_dropdown_input_attrs', $input_attrs_str, $args );
3381 3581 }
3382 3582
3383 3583 /**
3584 + * @since 6.7.1
3585 + */
3586 + public static function get_images_dropdown_atts( $option, $args ) {
3587 + $image = self::get_images_dropdown_option_image( $option, $args );
3588 + $classes = self::get_images_dropdown_option_classes( $option, $args );
3589 + $custom_attrs = self::get_images_dropdown_option_html_attrs( $option, $args );
3590 + return compact( 'image', 'classes', 'custom_attrs' );
3591 + }
3592 +
3593 + /**
3384 3594 * Gets the image of each option in images_dropdown() method.
3385 3595 *
3386 3596 * @since 5.0.04
3387 3597 *
@@ -3538,9 +3748,9 @@
3538 3748 *
3539 3749 * @since 5.0.13
3540 3750 *
3541 3751 * @param string $value
3542 - * @param array|string $allowed 'all' for everything included as defaults
3752 + * @param array|string $allowed 'all' for everything included as defaults.
3543 3753 * @return string
3544 3754 */
3545 3755 public static function maybe_kses( $value, $allowed = 'all' ) {
3546 3756 if ( self::should_never_allow_unfiltered_html() ) {
@@ -3586,9 +3796,9 @@
3586 3796
3587 3797 /**
3588 3798 * @since 5.0.17
3589 3799 *
3590 - * @param string
3800 + * @param string $feature
3591 3801 * @return bool
3592 3802 */
3593 3803 public static function show_new_feature( $feature ) {
3594 3804 $link = FrmAddonsController::install_link( $feature );
@@ -3661,9 +3871,9 @@
3661 3871 public static function show_pill_text( $text = null ) {
3662 3872 if ( null === $text ) {
3663 3873 $text = __( 'NEW', 'formidable' );
3664 3874 }
3665 - echo '<span class="frm-new-pill">' . esc_html( $text ) . '</span>';
3875 + echo '<span class="frm-meta-tag frm-new-pill">' . esc_html( $text ) . '</span>';
3666 3876 }
3667 3877
3668 3878 /**
3669 3879 * Count the number of decimals digits.
@@ -3905,6 +4115,28 @@
3905 4115 update_option( $option, true, 'no' );
3906 4116 }
3907 4117
3908 4118 wp_send_json_success();
4119 + }
4120 +
4121 + /**
4122 + * Lite license copy.
4123 + * Used in FrmDashboardController & FrmSettingsController
4124 + *
4125 + * @since 6.8
4126 + *
4127 + * @return string
4128 + */
4129 + public static function copy_for_lite_license() {
4130 + $message = __( 'You\'re using Formidable Forms Lite - no license needed. Enjoy!', 'formidable' ) . ' 🙂';
4131 +
4132 + if ( is_callable( 'FrmProAddonsController::get_readable_license_type' ) && ! class_exists( 'FrmProDashboardController' ) ) {
4133 + // Manage PRO versions without PRO dashboard functionality.
4134 + $license_type = FrmProAddonsController::get_readable_license_type();
4135 + if ( 'lite' !== strtolower( $license_type ) ) {
4136 + $message = 'Formidable Pro ' . $license_type;
4137 + }
4138 + }
4139 +
4140 + return apply_filters( 'frm_license_type_text', $message );
3909 4141 }
3910 4142 }