PluginProbe ʕ •ᴥ•ʔ
Tracking Code Manager / 2.7.0
Tracking Code Manager v2.7.0
2.8.0 2.7.0 trunk 1.11.8 1.11.9 1.12.0 1.12.1 1.12.2 1.12.3 1.4 1.5 2.0.0 2.0.1 2.0.13 2.0.14 2.0.15 2.0.16 2.0.2 2.0.3 2.0.4 2.0.5 2.0.6 2.0.7 2.1.0 2.2.0 2.3.0 2.4.0 2.5.0 2.6.0
tracking-code-manager / includes / classes / utils / Utils.php
tracking-code-manager / includes / classes / utils Last commit date
Cron.php 4 years ago Ecommerce.php 4 years ago Language.php 4 years ago Logger.php 1 month ago MobileDetect.php 1 month ago Options.php 1 month ago Plugin.php 1 month ago Properties.php 4 years ago Tracking.php 1 month ago Utils.php 1 month ago
Utils.php
2091 lines
1 <?php
2 if ( ! defined( 'ABSPATH' ) ) {
3 exit;
4 }
5
6 class TCMP_Utils {
7 const FORMAT_DATETIME = 'd/m/Y H:i';
8 const FORMAT_COMPACT_DATETIME = 'd/m H:i';
9 const FORMAT_DATE = 'd/m/Y';
10 const FORMAT_TIME = 'H:i';
11
12 const FORMAT_SQL_DATETIME = 'Y-m-d H:i:s';
13 const FORMAT_SQL_DATE = 'Y-m-d';
14 const FORMAT_SQL_TIME = 'H:i:s';
15
16 private $color_index;
17 private $default_currency_symbol;
18
19 public function __construct() {
20 $this->color_index = 0;
21 }
22
23 public function setDefaultCurrencySymbol( $value ) {
24 $this->default_currency_symbol = $value;
25 }
26 public function getDefaultCurrencySymbol() {
27 return ( '' == $this->default_currency_symbol ? 'USD' : $this->default_currency_symbol );
28 }
29 function format( $message, $v1 = null, $v2 = null, $v3 = null, $v4 = null, $v5 = null ) {
30 if ( $v1 || $v2 || $v3 || $v4 || $v5 ) {
31 $message = sprintf( $message, $v1, $v2, $v3, $v4, $v5 );
32 }
33 return $message;
34 }
35 function starts_with( $haystack, $needle ) {
36 $length = strlen( $needle );
37 return ( substr( $haystack, 0, $length ) === $needle );
38 }
39
40 function ends_with( $haystack, $needle ) {
41 $length = strlen( $needle );
42 $start = $length * -1; //negative
43 return ( substr( $haystack, $start ) === $needle );
44 }
45 function substr( $text, $start = 0, $end = -1 ) {
46 if ( $end < 0 ) {
47 $end = strlen( $text );
48 }
49 $length = $end - $start;
50 return substr( $text, $start, $length );
51 }
52
53 function shortcode_args( $args, $defaults ) {
54 $args = $this->sanitize_shortcode_keys( $args );
55 $defaults = $this->sanitize_shortcode_keys( $defaults );
56 $args = shortcode_atts( $defaults, $args );
57 return $args;
58 }
59 function sanitize_shortcode_keys( $array ) {
60 $result = array();
61 foreach ( $array as $k => $v ) {
62 if ( is_string( $k ) ) {
63 $k = strtolower( $k );
64 }
65 $result[ $k ] = $v;
66 }
67 return $result;
68 }
69
70 //WOW! $end is passed as reference due to we can change it if we found \n character after
71 //substring to avoid having these characters after or before
72 function substrln( $text, $start = 0, &$end = -1 ) {
73 if ( $end < 0 ) {
74 $end = strlen( $text );
75 }
76
77 do {
78 $loop = false;
79 $c = substr( $text, $end, 1 );
80 if ( "\n" == $c || "\r" == $c || '.' == $c ) {
81 $end += 1;
82 $loop = true;
83 }
84 } while ( $loop );
85
86 $length = $end - $start;
87 return substr( $text, $start, $length );
88 }
89
90 function toCommaArray( $array, $is_numeric = true, $is_trim = true ) {
91 if ( is_string( $array ) ) {
92 if ( trim( $array ) == '' ) {
93 $array = array();
94 } else {
95 $array = explode( ',', $array );
96 }
97 } elseif ( is_numeric( $array ) ) {
98 $array = array( $array );
99 }
100 if ( ! is_array( $array ) ) {
101 $array = array();
102 }
103 for ( $i = 0; $i < count( $array ); $i++ ) {
104 if ( $is_trim ) {
105 $array[ $i ] = trim( $array[ $i ] );
106 }
107 if ( $is_numeric ) {
108 $array[ $i ] = floatval( $array[ $i ] );
109 }
110 }
111 return $array;
112 }
113 function in_all_array( $search, $where ) {
114 return ( $this->inArray( -1, $where ) || $this->inArray( $search, $where ) );
115 }
116 function inArray( $search, $where ) {
117 $result = false;
118 $where = $this->to_array( $where );
119 $search = $this->to_array( $search );
120 if ( 0 == count( $where ) || 0 == count( $search ) ) {
121 return false;
122 }
123
124 foreach ( $where as $v ) {
125 $v .= '';
126 foreach ( $search as $c ) {
127 $c .= '';
128 if ( $v == $c ) {
129 $result = true;
130 break;
131 }
132 }
133
134 if ( $result ) {
135 break;
136 }
137 }
138 return $result;
139 }
140
141 function is( $name, $compare, $default = '', $ignore_case = true ) {
142 $what = $this->qs( $name, $default );
143 $result = false;
144 if ( is_string( $compare ) ) {
145 $compare = explode( ',', $compare );
146 }
147 if ( $ignore_case ) {
148 $what = strtolower( $what );
149 }
150
151 foreach ( $compare as $v ) {
152 if ( $ignore_case ) {
153 $v = strtolower( $v );
154 }
155 if ( $what == $v ) {
156 $result = true;
157 break;
158 }
159 }
160 return $result;
161 }
162
163 public function twitter( $name ) {
164 // Self-contained X (formerly Twitter) follow link. The old markup relied on
165 // Twitter's platform.twitter.com/widgets.js to turn a `.twitter-follow-button`
166 // anchor into a logo button; that widget was retired after the X rebrand, so it
167 // rendered as bare text with no logo. Inline the X mark as SVG instead — no
168 // external script, works offline, and shows the correct current brand.
169 // Styling lives in the .tcmp-x-follow rules in assets/css/style.css.
170 ?>
171 <a href="https://x.com/<?php echo esc_attr( $name ); ?>" target="_blank" rel="noopener noreferrer" class="tcmp-x-follow">
172 <svg viewBox="0 0 24 24" width="16" height="16" fill="currentColor" aria-hidden="true" focusable="false"><path d="M18.244 2.25h3.308l-7.227 8.26 8.502 11.24H16.17l-5.214-6.817L4.99 21.75H1.68l7.73-8.835L1.254 2.25H8.08l4.713 6.231zm-1.161 17.52h1.833L7.084 4.126H5.117z"/></svg>
173 <span>Follow @<?php echo esc_html( $name ); ?></span>
174 </a>
175 <?php
176 }
177
178 public function sort( $is_associative, $a1, $a2 = null, $a3 = null, $a4 = null, $a5 = null ) {
179 $array = $this->merge( $is_associative, $a1, $a2, $a3, $a4, $a5 );
180 ksort( $array );
181 return $array;
182 }
183 public function merge( $is_associative, $a1, $a2 = null, $a3 = null, $a4 = null, $a5 = null ) {
184 $result = array();
185 if ( $is_associative ) {
186 $array = array( $a1, $a2, $a3, $a4, $a5 );
187 foreach ( $array as $a ) {
188 if ( ! is_array( $a ) ) {
189 continue;
190 }
191
192 foreach ( $a as $k => $v ) {
193 if ( ! isset( $result[ $k ] ) ) {
194 $result[ $k ] = $v;
195 }
196 }
197 }
198 } else {
199 $result = array_merge( $a1, $a2, $a3, $a4, $a5 );
200 }
201 return $result;
202 }
203
204 function bget( $instance, $name, $index = -1 ) {
205 $v = $this->get( $instance, $name, false, $index );
206 $v = $this->isTrue( $v );
207 return $v;
208 }
209 function dget( $instance, $name, $index = -1 ) {
210 $v = $this->get( $instance, $name, false, $index );
211 $v = $this->parse_date_to_time( $v );
212 return $v;
213 }
214 function aget( $instance, $name, $index = -1 ) {
215 $v = $this->get( $instance, $name, false, $index );
216 $v = $this->to_array( $v );
217 return $v;
218 }
219 function get( $instance, $name, $default = '', $index = -1 ) {
220 if ( $this->is_empty( $instance ) ) {
221 return $default;
222 }
223 $options = array();
224 //assolutamente da non fare altrimenti succede un disastro in quanto i metodi del inputComponent
225 //gli passano come name il valore...insomma un disastro!
226 //$name=$this->to_array($name);
227 //$name=implode('.', $name);
228
229 $result = $default;
230 if ( is_array( $instance ) || is_object( $instance ) ) {
231 if ( $this->propertyReflect( $instance, $name, $options ) ) {
232 $result = $options['get'];
233 }
234 }
235 if ( $index > -1 ) {
236 $result = $this->to_array( $result );
237 if ( isset( $result[ $index ] ) ) {
238 $result = $result[ $index ];
239 } else {
240 $result = $default;
241 }
242 }
243 return $result;
244 }
245 function has( $instance, $name ) {
246 return $this->propertyReflect( $instance, $name );
247 }
248 function set( &$instance, $name, $value ) {
249 $options = array( 'set' => $value );
250 $result = $this->propertyReflect( $instance, $name, $options );
251 if ( ! $result ) {
252 }
253 return $result;
254 }
255 function iget( $array, $name, $default = '' ) {
256 return intval( $this->get( $array, $name, $default ) );
257 }
258
259 private function propertyReflect( &$instance, $name, &$options = array() ) {
260 if ( ! is_object( $instance ) && ! is_array( $instance ) ) {
261 return false;
262 }
263
264 if ( false === $options || ! is_array( $options ) ) {
265 $options = array();
266 }
267 $options['has'] = false;
268 $options['get'] = false;
269
270 $current = $instance;
271 $names = explode( '.', $name );
272 $value = false;
273 $result = true;
274 for ( $i = 0; $i < count( $names ); $i++ ) {
275 $name = $names[ $i ];
276 if ( ! is_object( $current ) && ! is_array( $current ) ) {
277 return false;
278 }
279 if ( is_null( $current ) ) {
280 return false;
281 }
282
283 if ( is_object( $current ) ) {
284 if ( get_class( $current ) == 'stdClass' ) {
285 if ( isset( $current->$name ) ) {
286 $value = $current->$name;
287 } else {
288 $result = false;
289 }
290 } else {
291 $r = new ReflectionClass( $current );
292 try {
293 if ( $r->getProperty( $name ) !== false ) {
294 $value = $current->$name;
295 } else {
296 $result = false;
297 }
298 } catch ( Exception $ex ) {
299 if ( isset( $current->$name ) ) {
300 $value = $current->$name;
301 } else {
302 $result = false;
303 }
304 }
305 }
306 } elseif ( is_array( $current ) ) {
307 if ( isset( $current[ $name ] ) ) {
308 $value = $current[ $name ];
309 } else {
310 $result = false;
311 }
312 }
313
314 if ( ! $result ) {
315 break;
316 } elseif ( $i < ( count( $names ) - 1 ) ) {
317 $current = $value;
318 } else {
319 $options['get'] = $value;
320 if ( isset( $options['set'] ) ) {
321 if ( is_object( $current ) ) {
322 $current->$name = $options['set'];
323 } elseif ( is_array( $current ) ) {
324 $current[ $name ] = $options['set'];
325 }
326 }
327 }
328 }
329 return $result;
330 }
331 function isTrue( $value ) {
332 $result = false;
333 if ( is_bool( $value ) ) {
334 $result = (bool) $value;
335 } elseif ( is_numeric( $value ) ) {
336 $result = floatval( $value ) > 0;
337 } else {
338 $result = strtolower( $value );
339 if ( 'ok' == $result || 'yes' == $result || 'true' == $result || 'on' == $result ) {
340 $result = true;
341 } else {
342 $result = false;
343 }
344 }
345 return $result;
346 }
347 function aqs( $prefix, $remove_prefix = true ) {
348 $result = array();
349 $array = $this->merge( true, $_POST, $_GET );
350 foreach ( $array as $k => $v ) {
351 if ( $this->starts_with( $k, $prefix ) ) {
352 if ( $remove_prefix ) {
353 $k = substr( $k, strlen( $prefix ) );
354 }
355 $result[ $k ] = $v;
356 }
357 }
358 return $result;
359 }
360 function iqs( $name, $default = 0, $min = 0, $max = 0 ) {
361 $result = floatval( $this->qs( $name, $default ) );
362 if ( $min != $max ) {
363 if ( $result < $min ) {
364 $result = $min;
365 } elseif ( $result > $max ) {
366 $result = $max;
367 }
368 }
369 return $result;
370 }
371 function dqs( $name, $default = 0 ) {
372 $result = ( $this->qs( $name, $default ) );
373 $result = $this->parse_date_to_time( $result );
374 if ( 0 == $result ) {
375 $result = $default;
376 }
377 return $result;
378 }
379 //per ottenere un campo dal $_GET oppure dal $_POST
380 function qs( $name, $default = '' ) {
381 global $tcmp_allowed_html_tags;
382 $result = $default;
383 if ( isset( $_POST[ $name ] ) ) {
384 $result = $this->sanitize_post_or_get( $_POST[ $name ], $name );
385 } elseif ( isset( $_GET[ $name ] ) ) {
386 $result = $this->sanitize_post_or_get( $_GET[ $name ], $name );
387 }
388
389 if ( is_string( $result ) ) {
390 //The superglobals $_GET and $_REQUEST are already decoded.
391 //Using urldecode() on an element in $_GET or $_REQUEST
392 //could have unexpected and dangerous results.
393 //$result=urldecode($result);
394 $result = trim( $result );
395 }
396 return $result;
397 }
398
399 private function sanitize_post_or_get( $array, $name = '' ) {
400 global $tcmp_allowed_html_tags;
401 // The snippet "code" fields hold raw tracking markup on purpose; they are
402 // sanitized on output via TCMP_Manager::esc_js_code(). Everything else is
403 // treated as plain text so that qs() is safe by default (see F-06).
404 $is_code = ( 'code' === $name || 'tcmp_code' === $name );
405 if ( is_array( $array ) ) {
406 foreach ( $array as $k => &$v ) {
407 if ( 'code' == $k ) {
408 $v = wp_kses( $v, $tcmp_allowed_html_tags );
409 } elseif ( is_string( $v ) ) {
410 $v = sanitize_text_field( $v );
411 }
412 }
413 unset( $v );
414 } elseif ( is_string( $array ) && ! $is_code ) {
415 $array = sanitize_text_field( $array );
416 }
417 return $array;
418 }
419
420 var $_taxonomyType;
421
422 function query( $query, $options = null ) {
423 global $tcmp;
424
425 $parent = '';
426 $defaults = array(
427 'post_type' => '',
428 'all' => false,
429 'select' => false,
430 'taxonomy' => '',
431 );
432 $options = wp_parse_args( $options, $defaults );
433
434 if ( ! isset( $options['type'] ) ) {
435 if ( '' != $options['post_type'] ) {
436 $options['type'] = $options['post_type'];
437 } elseif ( '' != $options['taxonomy'] ) {
438 $options['type'] = $options['taxonomy'];
439 } else {
440 $options['type'] = '';
441 }
442 }
443
444 if ( TCMP_QUERY_CONVERSION_PLUGINS == $query ) {
445 $array = $tcmp->ecommerce->getPlugins( false );
446 $result = array();
447 foreach ( $array as $k => $v ) {
448 $result[] = $v;
449 }
450 } else {
451 $key = array( 'Query', $query . '_' . $options['type'] );
452 $result = $tcmp->options->getCache( $key );
453 if ( ! is_array( $result ) || 0 == count( $result ) ) {
454 $q = null;
455 $id = 'ID';
456 $name = 'post_title';
457 $function = '';
458 switch ( $query ) {
459 case TCMP_QUERY_POSTS_OF_TYPE:
460 // get_posts() instead of a direct $wpdb query: it goes
461 // through WordPress's object cache and avoids the
462 // DirectDatabaseQuery / NoCaching warnings. The WP_Post
463 // objects it returns expose the same ID and post_title
464 // fields the loop below reads, and get_posts() already
465 // sets no_found_rows, so this is no heavier than the
466 // two-column SELECT it replaces. The empty-type check keeps
467 // the old semantics: the previous `post_type = ''` SELECT
468 // matched nothing, whereas get_posts() would silently fall
469 // back to listing ordinary posts.
470 if ( '' !== (string) $options['type'] ) {
471 $q = get_posts(
472 array(
473 'post_type' => $options['type'],
474 'post_status' => 'publish',
475 'posts_per_page' => -1,
476 'orderby' => 'title',
477 'order' => 'ASC',
478 )
479 );
480 }
481 $function = 'get_permalink';
482 break;
483 case TCMP_QUERY_CATEGORIES:
484 break;
485 case TCMP_QUERY_TAGS:
486 break;
487 case TCMP_QUERY_TAXONOMIES_OF_TYPE:
488 break;
489 }
490
491 $result = array();
492 if ( $q ) {
493 if ( ! is_wp_error( $q ) ) {
494 foreach ( $q as $v ) {
495 $item = array(
496 'id' => $v->$id,
497 'name' => $v->$name,
498 );
499 if ( '' != $parent ) {
500 $item['parent'] = $v->$parent;
501 }
502 $result[] = $item;
503 }
504 }
505 } elseif ( TCMP_QUERY_POST_TYPES == $query ) {
506 global $wp_post_types;
507 $result = array();
508 foreach ( $wp_post_types as $k => $v ) {
509 $is_public = $tcmp->utils->bget( $v, 'public' );
510 if ( $is_public && 'attachment' != $k ) {
511 $v = $tcmp->utils->get( $v, 'labels.singular_name' );
512 if ( 'post' == $k || 'page' == $k ) {
513 $result[ $k ] = $v;
514 }
515 }
516 }
517 $result = $tcmp->utils->toFormatListArrayFromListObjects( $result, false, '{text} ({id})' );
518 } elseif ( TCMP_QUERY_TAXONOMY_TYPES == $query ) {
519
520 }
521
522 if ( $this->functionExists( $function ) ) {
523 for ( $i = 0; $i < count( $result ); $i++ ) {
524 $v = $result[ $i ];
525 $v['url'] = $this->functionCall( $function, array( $v['id'] ) );
526 $result[ $i ] = $v;
527 }
528 }
529 $tcmp->options->setCache( $key, $result );
530 }
531 }
532
533 if ( $options['all'] ) {
534 $first = array();
535 $first[] = array(
536 'id' => -1,
537 'name' => '[' . $tcmp->lang->L( 'All' ) . ']',
538 'url' => '',
539 );
540 $result = array_merge( $first, $result );
541 }
542 if ( $options['select'] ) {
543 $first = array();
544 $first[] = array(
545 'id' => 0,
546 'name' => '[' . $tcmp->lang->L( 'Select' ) . ']',
547 'url' => '',
548 );
549 $result = array_merge( $first, $result );
550 }
551 $result = $this->sortOptions( $result );
552 $this->_taxonomyType = '';
553 return $result;
554 }
555
556 //wp_parse_args with null correction
557 function parseArgs( $options, $defaults ) {
558 if ( is_null( $options ) ) {
559 $options = array();
560 } elseif ( is_object( $options ) ) {
561 $options = (array) $options;
562 } elseif ( ! is_array( $options ) ) {
563 $options = array();
564 }
565 if ( is_null( $defaults ) ) {
566 $defaults = array();
567 } elseif ( is_object( $defaults ) ) {
568 $defaults = (array) $defaults;
569 } elseif ( ! is_array( $defaults ) ) {
570 $defaults = array();
571 }
572
573 foreach ( $defaults as $k => $v ) {
574 if ( is_null( $v ) ) {
575 unset( $defaults[ $k ] );
576 }
577 }
578
579 foreach ( $options as $k => $v ) {
580 if ( isset( $defaults[ $k ] ) ) {
581 if ( is_null( $v ) ) {
582 //so can take the default value
583 unset( $options[ $k ] );
584 } elseif ( is_string( $v ) && ( '' === $v ) && isset( $defaults[ $k ] ) && is_array( $defaults[ $k ] ) ) {
585 //a very strange case, i have a blank string for rappresenting an empty array
586 unset( $options[ $k ] );
587 } else {
588 unset( $defaults[ $k ] );
589 }
590 }
591 }
592 foreach ( $defaults as $k => $v ) {
593 $options[ $k ] = $v;
594 }
595 return $options;
596 }
597
598 function redirect( $location ) {
599 if ( '' == $location ) {
600 return;
601 }
602 ?>
603 <div id="tcmpRedirect" href="<?php echo esc_attr( $location ); ?>"></div>
604 <?php
605 die();
606 }
607
608 //return the element inside array with the specified key
609 function getArrayValue( $key, $array, $value = '' ) {
610 $result = false;
611 if ( isset( $array[ $key ] ) ) {
612 $result = $array[ $key ];
613 $result['name'] = $key;
614 }
615 if ( false !== $result && '' != $value ) {
616 if ( isset( $result[ $value ] ) ) {
617 $result = $result[ $value ];
618 }
619 }
620 return $result;
621 }
622
623 var $_sort_field;
624 var $_ignore_case;
625 function aksort( &$array, $sort_field = 'name', $ignore_case = true ) {
626 $this->_sort_field = $sort_field;
627 $this->_ignore_case = $ignore_case;
628 usort( $array, array( $this, 'aksortCompare' ) );
629 }
630 //not thread-safe!
631 private function aksortCompare( $a, $b ) {
632 if ( $a === $b || $a == $b ) {
633 return 0;
634 }
635
636 $result = 0;
637 $a = $a[ $this->_sort_field ];
638 $b = $b[ $this->_sort_field ];
639 if ( is_numeric( $a ) && is_numeric( $b ) ) {
640 $result = ( $a < $b ) ? -1 : 1;
641 } else {
642 $a .= '';
643 $b .= '';
644 if ( $this->_ignore_case ) {
645 $result = strcasecmp( $a, $b );
646 } else {
647 $result = strcmp( $a . '', $b );
648 }
649 }
650 return $result;
651 }
652
653 public function formatCustomDate( $time, $format ) {
654 $time = $this->parse_date_to_time( $time );
655 if ( $time > 0 ) {
656 $time = date( $format, $time );
657 } else {
658 $time = '';
659 }
660 return $time;
661 }
662
663 public function formatDatetime( $time = 'now' ) {
664 return $this->formatCustomDate( $time, TCMP_Utils::FORMAT_DATETIME );
665 }
666 public function formatCompactDatetime( $time = 'now' ) {
667 return $this->formatCustomDate( $time, TCMP_Utils::FORMAT_COMPACT_DATETIME );
668 }
669 public function formatDate( $time = 'date' ) {
670 return $this->formatCustomDate( $time, TCMP_Utils::FORMAT_DATE );
671 }
672 public function formatSmartDatetime( $time = 'now' ) {
673 $time = $this->parse_date_to_time( $time );
674 $result = '';
675 if ( $time > 0 ) {
676 $h = intval( date( 'H', $time ) );
677 $i = intval( date( 'i', $time ) );
678 $s = intval( date( 's', $time ) );
679 if ( 0 == $h && 0 == $i && 0 == $s ) {
680 $result = $this->formatDate( $time );
681 } else {
682 $result = $this->formatDatetime( $time );
683 }
684 }
685 return $result;
686 }
687 public function formatTime( $time = 'now' ) {
688 return $this->formatCustomTime( $time, TCMP_Utils::FORMAT_TIME );
689 }
690 public function formatSqlDatetime( $time = 'now' ) {
691 return $this->formatCustomDate( $time, TCMP_Utils::FORMAT_SQL_DATETIME );
692 }
693 public function formatSqlDate( $time = 'date' ) {
694 return $this->formatCustomDate( $time, TCMP_Utils::FORMAT_SQL_DATE );
695 }
696 public function formatSqlTime( $time = 'now' ) {
697 return $this->formatCustomTime( $time, TCMP_Utils::FORMAT_SQL_TIME );
698 }
699
700 private function formatCustomTime( $time, $format ) {
701 $time = $this->parse_date_to_time( $time );
702 if ( $time > 86400 ) {
703 $h = date( 'H', $time );
704 $i = date( 'i', $time );
705 $s = date( 's', $time );
706 $time = $h * 3600 + $i * 60 + $s;
707 }
708
709 $s = $time % 60;
710 $time = ( $time - $s ) / 60;
711 $i = $time % 60;
712 $h = ( $time - $i ) / 60;
713 $s = str_pad( $s, 2, '0', STR_PAD_LEFT );
714 $i = str_pad( $i, 2, '0', STR_PAD_LEFT );
715 $h = str_pad( $h, 2, '0', STR_PAD_LEFT );
716 $format = str_replace( 'H', $h, $format );
717 $format = str_replace( 'i', $i, $format );
718 $format = str_replace( 's', $s, $format );
719 return $format;
720 }
721
722 public function parseNumber( $what, $default = 0 ) {
723 $result = $default;
724 if ( is_array( $what ) ) {
725 if ( count( $what ) > 0 ) {
726 $result = doubleval( $what[0] );
727 }
728 } elseif ( is_numeric( $what ) ) {
729 $result = doubleval( $what );
730 } elseif ( is_string( $what ) || is_bool( $what ) ) {
731 $result = ( $this->isTrue( $what ) ? 1 : 0 );
732 }
733 return $result;
734 }
735 public function parseDateToArray( $date ) {
736 global $tcmp;
737
738 $pm = false;
739 $date = strtoupper( trim( $date ) );
740 if ( $tcmp->utils->ends_with( $date, 'AM' ) ) {
741 $date = substr( $date, 0, strlen( $date ) - 2 );
742 $date = trim( $date );
743 } elseif ( $tcmp->utils->ends_with( $date, 'PM' ) ) {
744 $date = substr( $date, 0, strlen( $date ) - 2 );
745 $date = trim( $date );
746 $pm = true;
747 }
748
749 $date = explode( ' ', $date );
750 if ( 1 == count( $date ) ) {
751 $result = array();
752 $date = $date[0];
753 $date = str_replace( '/', '-', $date );
754 if ( strpos( $date, '-' ) !== false ) {
755 $date = explode( '-', $date );
756 if ( count( $date ) >= 3 ) {
757 $d = intval( $date[0] );
758 $m = intval( $date[1] );
759 $y = intval( $date[2] );
760 if ( $d > 1900 ) {
761 $t = $d;
762 $d = $y;
763 $y = $t;
764 }
765 if ( $y > 0 && $m > 0 && $d > 0 ) {
766 $result['y'] = $y;
767 $result['m'] = $m;
768 $result['d'] = $d;
769 }
770 }
771 } elseif ( strpos( $date, ':' ) !== false ) {
772 $date = explode( ':', $date );
773 if ( 2 == count( $date ) ) {
774 $date[] = 0;
775 }
776 if ( count( $date ) >= 3 ) {
777 $h = intval( $date[0] );
778 $i = intval( $date[1] );
779 $s = intval( $date[2] );
780 if ( $h >= 0 && $i >= 0 && $s >= 0 ) {
781 $result['h'] = $h;
782 $result['i'] = $i;
783 $result['s'] = $s;
784 }
785 }
786 }
787 } else {
788 $a1 = $this->parseDateToArray( $date[0] );
789 $a2 = $this->parseDateToArray( $date[1] );
790 $result = $tcmp->utils->parseArgs( $a1, $a2 );
791 }
792
793 if ( $pm && isset( $result['h'] ) ) {
794 $result['h'] = intval( $result['h'] ) + 12;
795 }
796 return $result;
797 }
798 public function parse_date_to_time( $date ) {
799 global $tcmp;
800 if ( is_null($date) ) {
801 $date = 'now';
802 }
803 if ( is_numeric( $date ) || trim( $date ) == '' ) {
804 $date = intval( $date );
805 return $date;
806 }
807
808 $date = strtolower( $date );
809 if ( 'now' == $date ) {
810 $date = time();
811 return $date;
812 } elseif ( 'date' == $date ) {
813 $date = strtotime( date( 'Y-m-d', time() ) );
814 return $date;
815 } elseif ( 'time' == $date ) {
816 $date = date( 'H:i:s', time() );
817 }
818 $result = $this->parseDateToArray( $date );
819 $defaults = array(
820 'y' => 0,
821 'm' => 0,
822 'd' => 0,
823 'h' => 0,
824 'i' => 0,
825 's' => 0,
826 );
827 $a = $tcmp->utils->parseArgs( $result, $defaults );
828 if ( 0 == $a['y'] && 0 == $a['m'] && 0 == $a['d'] ) {
829 $result = $a['h'] * 3600 + $a['i'] * 60 + $a['s'];
830 } else {
831 $result = mktime( $a['h'], $a['i'], $a['s'], $a['m'], $a['d'], $a['y'] );
832 }
833 if ( $result < 0 ) {
834 $result = 0;
835 }
836 return $result;
837 }
838 public function getIntDate( $time, $separator = '' ) {
839 $time = $this->parse_date_to_time( $time );
840 if ( $time > 0 ) {
841 if ( '' == $separator ) {
842 $time = date( 'Ymd', $time );
843 $time = intval( $time );
844 } else {
845 $time = date( 'Y', $time ) . $separator . date( 'm', $time ) . $separator . date( 'd', $time );
846 }
847 }
848
849 return $time;
850 }
851 public function getIntMinute( $h, $m, $separator = '' ) {
852 $h = intval( $h );
853 $m = intval( $m );
854 if ( $m < 10 ) {
855 $m = '0' . $m;
856 }
857 $result = $h . $separator . $m;
858 if ( '' == $separator ) {
859 $result = intval( $result );
860 }
861 return $result;
862 }
863
864 //args can be a string or an associative array if you want
865 public function get_text_args( $args, $defaults = array(), $excludes = array() ) {
866 $result = $args;
867 $excludes = $this->to_array( $excludes );
868 if ( is_array( $result ) && count( $result ) > 0 ) {
869 $result = '';
870 foreach ( $args as $k => $v ) {
871 if ( is_array( $v ) || is_object( $v ) ) {
872 continue;
873 }
874
875 if ( 0 == count( $excludes ) || ! in_array( $k, $excludes ) ) {
876 $v = trim( $v );
877 $result .= ' ' . $k . '="' . $v . '"';
878 }
879 }
880 } elseif ( ! $args ) {
881 $result = '';
882 }
883 if ( is_array( $defaults ) && count( $defaults ) > 0 ) {
884 foreach ( $defaults as $k => $v ) {
885 if ( 0 == count( $excludes ) || ! in_array( $k, $excludes ) ) {
886 if ( ! isset( $args[ $k ] ) ) {
887 $v = trim( $v );
888 $result .= ' ' . $k . '="' . $v . '"';
889 }
890 }
891 }
892 }
893 return $result;
894 }
895
896 public function iuarray( $ids, $positive = false ) {
897 $array = $this->iarray( $ids, $positive );
898 $array = array_unique( $array );
899 sort( $array );
900 return $array;
901 }
902 public function iarray( $ids, $positive = false ) {
903 if ( is_string( $ids ) ) {
904 $ids = explode( ',', $ids );
905 } elseif ( is_numeric( $ids ) ) {
906 $ids = array( $ids );
907 } elseif ( ! is_array( $ids ) ) {
908 $ids = array();
909 }
910
911 $array = array();
912 foreach ( $ids as $v ) {
913 $v = trim( $v );
914 if ( '' != $v ) {
915 $v = intval( $v );
916 if ( ! $positive || $v > 0 ) {
917 $array[] = $v;
918 }
919 }
920 }
921 return $array;
922 }
923 public function dbarray( $ids ) {
924 if ( is_string( $ids ) ) {
925 $ids = explode( ',', $ids );
926 } elseif ( is_numeric( $ids ) ) {
927 $ids = array( $ids );
928 } elseif ( ! is_array( $ids ) ) {
929 $ids = array();
930 }
931
932 $array = array();
933 foreach ( $ids as $v ) {
934 $v = trim( $v );
935 if ( '' != $v ) {
936 if ( is_numeric( $v ) ) {
937 $v = intval( $v );
938 }
939 $array[] = $v;
940 }
941 }
942 return $array;
943 }
944
945 function is_associativeArray( $array ) {
946 if ( ! is_array( $array ) ) {
947 return false;
948 }
949
950 $isArray = true;
951 $i = 0;
952 foreach ( $array as $k => $v ) {
953 if ( $k !== $i ) {
954 $isArray = false;
955 break;
956 }
957 ++$i;
958 }
959 return ! $isArray;
960 }
961 function trim( $value ) {
962 if ( is_null( $value ) ) {
963
964 } elseif ( is_string( $value ) ) {
965 $value = trim( $value );
966 } elseif ( is_numeric( $value ) ) {
967
968 } elseif ( $this->is_associativeArray( $value ) ) {
969 foreach ( $value as $k => $v ) {
970 $value[ $k ] = $this->trim( $v );
971 }
972 } elseif ( is_object( $value ) ) {
973 foreach ( $value as $k => $v ) {
974 $value->$k = $this->trim( $v );
975 }
976 } elseif ( is_array( $value ) ) {
977 for ( $i = 0; $i < count( $value ); $i++ ) {
978 $v = $value[ $i ];
979 $this->trim( $v );
980 $value[ $i ] = $v;
981 }
982 }
983 return $value;
984 }
985 function implode( $open, $close, $join, $array ) {
986 $result = '';
987 foreach ( $array as $v ) {
988 if ( '' != $result ) {
989 $result .= $join;
990 }
991 $result .= $open . $v . $close;
992 }
993 return $result;
994 }
995 function to_array( $text, $index = -1, $default = '' ) {
996 if ( is_array( $text ) ) {
997 if ( is_string( $index ) ) {
998 $array = array();
999 foreach ( $text as $v ) {
1000 $v = $this->get( $v, $index, false );
1001 if ( false !== $v ) {
1002 $array[] = $v;
1003 }
1004 }
1005 } else {
1006 $array = $text;
1007 }
1008 return $array;
1009 } elseif ( is_numeric( $text ) ) {
1010 return array( $text );
1011 } elseif ( is_bool( $text ) || '' === $text ) {
1012 return array();
1013 }
1014
1015 if ( ( $this->starts_with( $text, '[' ) && $this->ends_with( $text, ']' ) )
1016 || ( $this->starts_with( $text, '{' ) && $this->ends_with( $text, '}' ) ) ) {
1017 $text = substr( $text, 1, strlen( $text ) - 2 );
1018 }
1019 $text = str_replace( '|', ',', $text );
1020 $text = explode( ',', $text );
1021
1022 //exclude empty string
1023 $array = array();
1024 foreach ( $text as $t ) {
1025 if ( '' !== $t ) {
1026 $array[] = $t;
1027 }
1028 }
1029 $text = $array;
1030 if ( $index > -1 ) {
1031 $result = $default;
1032 if ( isset( $text[ $index ] ) ) {
1033 $result = $text[ $index ];
1034 }
1035 $text = $result;
1036 }
1037 return $text;
1038 }
1039 function dirToFlatArray( $dir, &$output ) {
1040 if ( ! isset( $output['dirs'] ) ) {
1041 $output['dirs'] = array();
1042 }
1043 if ( ! isset( $output['files'] ) ) {
1044 $output['files'] = array();
1045 }
1046
1047 $cdir = scandir( $dir );
1048 foreach ( $cdir as $k => $v ) {
1049 if ( ! in_array( $v, array( '.', '..' ) ) ) {
1050 if ( is_dir( $dir . DIRECTORY_SEPARATOR . $v ) ) {
1051 $i = $dir . DIRECTORY_SEPARATOR . $v;
1052 array_push( $output['dirs'], $i );
1053 $this->dirToFlatArray( $i, $output );
1054 } else {
1055 $i = $this->getFileInfo( $dir . DIRECTORY_SEPARATOR . $v );
1056 array_push( $output['files'], $i );
1057 }
1058 }
1059 }
1060 }
1061 function dirToArray( $dir ) {
1062 $result = array();
1063 if ( ! is_string( $dir ) ) {
1064 return $result;
1065 }
1066
1067 $cdir = scandir( $dir );
1068 foreach ( $cdir as $k => $v ) {
1069 if ( ! in_array( $v, array( '.', '..' ) ) ) {
1070 if ( is_dir( $dir . DIRECTORY_SEPARATOR . $v ) ) {
1071 $result[ $v ] = $this->dirToArray( $dir . DIRECTORY_SEPARATOR . $v );
1072 } else {
1073 $result[] = $this->getFileInfo( $dir . DIRECTORY_SEPARATOR . $v );
1074 }
1075 }
1076 }
1077 return $result;
1078 }
1079 function getFileInfo( $source ) {
1080 $source = $this->toDirectory( $source );
1081 if ( ! file_exists( $source ) ) {
1082 return false;
1083 }
1084
1085 $array = explode( DIRECTORY_SEPARATOR, $source );
1086 $size = filesize( $source );
1087 $source = array_pop( $array );
1088 $directory = implode( DIRECTORY_SEPARATOR, $array ) . DIRECTORY_SEPARATOR;
1089
1090 $pos = strrpos( $source, '.' );
1091 $ext = '';
1092 if ( false !== $pos ) {
1093 $name = substr( $source, 0, $pos );
1094 $ext = strtolower( substr( $source, $pos ) );
1095 }
1096 $array = array(
1097 'directory' => $directory,
1098 'name' => $name,
1099 'file' => $source,
1100 'size' => $size,
1101 'textSize' => $this->getFileTextSize( $size ),
1102 'ext' => $ext,
1103 'textExt' => $this->getFileTextExt( $source ),
1104 );
1105 return $array;
1106 }
1107 function getFileTextSize( $size ) {
1108 $units = array( 'B', 'KB', 'MB', 'GB' );
1109 for ( $i = 0; $i < count( $units ); $i++ ) {
1110 if ( $size < 1024 ) {
1111 break;
1112 } else {
1113 $size /= 1024;
1114 }
1115 }
1116 return intval( $size ) . ' ' . $units[ $i ];
1117 }
1118 function getFileTextExt( $source ) {
1119 $ext = strrpos( $source, '.' );
1120 if ( false !== $ext ) {
1121 $ext = strtolower( substr( $source, $ext + 1 ) );
1122 } else {
1123 $ext = $source;
1124 }
1125 $ext = strtolower( $ext );
1126 $text = 'text';
1127 switch ( $ext ) {
1128 case 'doc':
1129 case 'docx':
1130 case 'odt':
1131 $text = 'word';
1132 break;
1133 case 'xls':
1134 case 'xlsx':
1135 case 'ods':
1136 $text = 'excel';
1137 break;
1138 case 'ppt':
1139 case 'pptx':
1140 case 'odp':
1141 $text = 'powerpoint';
1142 break;
1143 case 'zip':
1144 case 'tar':
1145 case 'gzip':
1146 case 'rar':
1147 case '7z':
1148 $text = 'archive';
1149 break;
1150 case 'mp3':
1151 case 'wav':
1152 $text = 'audio';
1153 break;
1154 case 'mpeg':
1155 case 'mpg':
1156 case 'avi':
1157 case 'mp4':
1158 $text = 'video';
1159 break;
1160 case 'gif':
1161 case 'jpg':
1162 case 'jpeg':
1163 case 'png':
1164 case 'bmp':
1165 $text = 'image';
1166 break;
1167 case 'pdf':
1168 $text = 'pdf';
1169 break;
1170 }
1171 return $text;
1172 }
1173 function match( $value, $array, $default = '', $ignore_case = true ) {
1174 $result = $default;
1175 if ( $ignore_case ) {
1176 $value = strtolower( $value );
1177 }
1178 foreach ( $array as $k => $v ) {
1179 $v = $this->to_array( $v );
1180 foreach ( $v as $c ) {
1181 if ( $ignore_case ) {
1182 $c = strtolower( $c );
1183 }
1184 if ( $value == $c || strpos( $value, $c ) !== false ) {
1185 $result = $k;
1186 break;
1187 }
1188 }
1189
1190 if ( $result !== $default ) {
1191 break;
1192 }
1193 }
1194 return $result;
1195 }
1196
1197 function pickColor() {
1198 $names = explode( '|', 'primary|success|warning|danger|info|alert|system|dark' );
1199 $colors = explode( '|', '3498db|70ca63|f6bb42|df5640|3bafda|967adc|37bc9b|666' );
1200
1201 $i = ( $this->color_index % count( $colors ) );
1202 $names = $names[ $i ];
1203 $colors = $colors[ $i ];
1204 ++$this->color_index;
1205 return array( $names, '#' . $colors );
1206 }
1207 function upperUnderscoreCase( $text ) {
1208 $text = $this->arrayCase( $text );
1209 $text = implode( '_', $text );
1210 $text = strtoupper( $text );
1211 return $text;
1212 }
1213 function lowerUnderscoreCase( $text ) {
1214 $text = $this->upperUnderscoreCase( $text );
1215 $text = strtolower( $text );
1216 return $text;
1217 }
1218 function toDirectory( $file, $mkdirs = false ) {
1219 $file = str_replace( '\\', DIRECTORY_SEPARATOR, $file );
1220 $file = str_replace( '/', DIRECTORY_SEPARATOR, $file );
1221 $file = str_replace( DIRECTORY_SEPARATOR . DIRECTORY_SEPARATOR, DIRECTORY_SEPARATOR, $file );
1222
1223 if ( is_dir( $file ) && ! file_exists( $file ) && $mkdirs ) {
1224 mkdir( $file, 0777, true );
1225 }
1226 return $file;
1227 }
1228 function getUploadName( $name ) {
1229 if ( '' == $name ) {
1230 return '';
1231 }
1232
1233 $name = $this->toDirectory( $name );
1234 $name = explode( DIRECTORY_SEPARATOR, $name );
1235 $name = $name[ count( $name ) - 1 ];
1236 $ext = '';
1237 $pos = strpos( $name, '.' );
1238 if ( false !== $pos ) {
1239 $ext = substr( $name, $pos );
1240 $name = substr( $name, 0, $pos );
1241 }
1242
1243 $buffer = '';
1244 $name = str_split( strtolower( $name ) );
1245 for ( $i = 0; $i < count( $name ); $i++ ) {
1246 if ( $name[ $i ] >= 'a' && $name[ $i ] <= 'z' ) {
1247 $buffer .= $name[ $i ];
1248 } else {
1249 $buffer .= ' ';
1250 }
1251 }
1252 while ( strpos( $buffer, ' ' ) !== false ) {
1253 $buffer = str_replace( ' ', ' ', $buffer );
1254 }
1255 $buffer = trim( $buffer );
1256 $buffer = str_replace( ' ', '-', $buffer );
1257 $buffer .= '-' . date( 'Ymd-His', time() ) . $ext;
1258 return $buffer;
1259 }
1260 function toListArrayFromClass( $array, $id = false, $value = false ) {
1261 global $tcmp;
1262 $result = array();
1263 if ( false !== $array && count( $array ) > 0 ) {
1264 foreach ( $array as $k => $v ) {
1265 if ( false !== $id ) {
1266 $k = $tcmp->utils->get( $v, $id );
1267 }
1268 if ( false !== $value ) {
1269 $v = $tcmp->utils->get( $v, $value );
1270 }
1271
1272 if ( '' != $k && '' != $v ) {
1273 $result[] = array(
1274 'id' => $k,
1275 'text' => $v,
1276 'name' => $v,
1277 );
1278 }
1279 }
1280 }
1281 return $result;
1282 }
1283 function toFormatListArrayFromListObjects( $array, $id_field, $textFormat ) {
1284 global $tcmp;
1285 $result = array();
1286 if ( false !== $array && count( $array ) > 0 ) {
1287 foreach ( $array as $i => $e ) {
1288 $text = $textFormat;
1289 $id_exists = false;
1290 if ( is_array( $e ) || is_object( $e ) ) {
1291 foreach ( $e as $k => $v ) {
1292 if ( 'id' == $k ) {
1293 $id_exists = true;
1294 }
1295 if ( is_array( $v ) ) {
1296 $v = implode( ', ', $v );
1297 }
1298 $text = str_replace( '{' . $k . '}', $v, $text );
1299 }
1300 } else {
1301 $text = str_replace( '{text}', $e, $text );
1302 }
1303
1304 $id = $i;
1305 if ( false !== $id_field && '' !== $id_field ) {
1306 $id = $tcmp->utils->get( $e, $id_field, '' );
1307 }
1308
1309 if ( ! $id_exists ) {
1310 $text = str_replace( '{id}', $id, $text );
1311 }
1312 if ( '' != $id ) {
1313 $result[] = array(
1314 'id' => $id,
1315 'text' => $text,
1316 'name' => $text,
1317 );
1318 }
1319 }
1320 }
1321 return $result;
1322 }
1323 function toListArrayFromListObjects( $array, $id_from = false, $textFrom = 'name', $idTo = 'id', $textTo = 'text' ) {
1324
1325 $result = array();
1326 foreach ( $array as $v ) {
1327 $s_id = $v;
1328 $s_text = $v;
1329 if ( false !== $id_from ) {
1330 $s_id = $this->get( $v, $id_from, false );
1331 $s_text = $this->get( $v, $textFrom, false );
1332 }
1333 if ( false !== $s_id && '' != $s_text ) {
1334 if ( '' != $s_id ) {
1335 $result[] = array(
1336 $idTo => $s_id,
1337 $textTo => $s_text,
1338 );
1339 }
1340 }
1341 }
1342 return $result;
1343 }
1344 function toColorListArrayFromListObjects( $array, $colors, $id = 'id', $text = 'name' ) {
1345 global $tcmp;
1346 $result = array();
1347 foreach ( $array as $instance ) {
1348 $s_id = $this->get( $instance, $id, false );
1349 $s_text = $this->get( $instance, $text, false );
1350 foreach ( $colors as $color => $when ) {
1351 $success = false;
1352 foreach ( $when['conditions'] as $conditionKey => $condition_value ) {
1353 $condition_value = $tcmp->utils->to_array( $condition_value );
1354 $c = $this->get( $instance, $conditionKey, false );
1355 if ( false !== $c ) {
1356 $c .= '';
1357 foreach ( $condition_value as $v ) {
1358 $v .= '';
1359 if ( $c === $v ) {
1360 $success = true;
1361 break;
1362 }
1363 }
1364 }
1365 if ( $success ) {
1366 break;
1367 }
1368 }
1369
1370 if ( $success ) {
1371 $style = 'color:' . $color . '; ';
1372 if ( isset( $when['bold'] ) && $when['bold'] ) {
1373 $style .= 'font-weight:bold; ';
1374 }
1375 $s_text = '<span style="' . $style . '">' . $s_text . '</span>';
1376 }
1377 }
1378 if ( '' != $s_id && false !== $s_text ) {
1379 $result[] = array(
1380 'id' => $s_id,
1381 'text' => $s_text,
1382 'name' => $s_text,
1383 );
1384 }
1385 }
1386 return $result;
1387 }
1388 function md5() {
1389 $array = func_get_args();
1390 $buffer = '';
1391 foreach ( $array as $v ) {
1392 $buffer .= ':)' . $v;
1393 }
1394 $buffer = md5( $buffer );
1395 return $buffer;
1396 }
1397 function arrayCase( $text ) {
1398 $buffer = '';
1399 $array = array();
1400 $text = str_split( $text );
1401 $prev_upper = false;
1402 $next_upper = false;
1403 foreach ( $text as $c ) {
1404 if ( $c >= 'a' && $c <= 'z' ) {
1405 if ( $next_upper ) {
1406 if ( '' != $buffer ) {
1407 $array[] = $buffer;
1408 $buffer = '';
1409 }
1410 $c = strtoupper( $c );
1411 }
1412 $buffer .= $c;
1413 $next_upper = false;
1414 $prev_upper = false;
1415 } elseif ( $c >= '0' && $c <= '9' ) {
1416 $buffer .= $c;
1417 $next_upper = true;
1418 } elseif ( $c >= 'A' && $c <= 'Z' ) {
1419 if ( ! $prev_upper ) {
1420 if ( '' != $buffer ) {
1421 $array[] = $buffer;
1422 $buffer = '';
1423 }
1424 }
1425 $buffer .= $c;
1426 $next_upper = false;
1427 $prev_upper = true;
1428 } else {
1429 if ( '' != $buffer ) {
1430 $array[] = $buffer;
1431 $buffer = '';
1432 }
1433 $next_upper = true;
1434 $prev_upper = false;
1435 }
1436 }
1437 if ( '' != $buffer ) {
1438 $array[] = $buffer;
1439 }
1440 return $array;
1441 }
1442 function lowerCamelCase( $text ) {
1443 $buffer = '';
1444 if ( strpos( $text, '_' ) !== false || strpos( $text, '-' ) !== false ) {
1445 $text = strtolower( $text );
1446 }
1447
1448 $text = str_split( $text );
1449 $all_upper = true;
1450 $next_upper = false;
1451 foreach ( $text as $c ) {
1452 if ( $c >= 'a' && $c <= 'z' ) {
1453 $all_upper = false;
1454 if ( $next_upper ) {
1455 $c = strtoupper( $c );
1456 }
1457 $buffer .= $c;
1458 $next_upper = false;
1459 } elseif ( $c >= '0' && $c <= '9' ) {
1460 $buffer .= $c;
1461 $next_upper = true;
1462 } elseif ( $c >= 'A' && $c <= 'Z' ) {
1463 $buffer .= $c;
1464 $next_upper = false;
1465 } else {
1466 $next_upper = true;
1467 }
1468 }
1469 if ( $all_upper ) {
1470 $buffer = strtolower( $buffer );
1471 } else {
1472 $buffer = lcfirst( $buffer );
1473 }
1474 return $buffer;
1475 }
1476 function upperCamelCase( $text ) {
1477 $text = $this->lowerCamelCase( $text );
1478 $text = ucfirst( $text );
1479 return $text;
1480 }
1481
1482 function castStdClass( $a ) {
1483 $a = (array) $a;
1484 $r = new stdClass();
1485 foreach ( $a as $k => $v ) {
1486 $r->$k = $v;
1487 }
1488 return $r;
1489 }
1490 function castArray( $a ) {
1491 $r = $a;
1492 if ( is_object( $a ) ) {
1493 $r = (array) $a;
1494 }
1495
1496 if ( ! is_array( $r ) ) {
1497 $r = array();
1498 }
1499 return $r;
1500 }
1501 public function copyArray( $array ) {
1502 $temp = array();
1503 foreach ( $array as $k => $v ) {
1504 $temp[ $k ] = $v;
1505 }
1506 return $temp;
1507 }
1508 public function isObject( $v ) {
1509 return ( false !== $v && ! is_null( $v ) && is_object( $v ) );
1510 }
1511 public function isArray( $v ) {
1512 return ( false !== $v && ! is_null( $v ) && is_array( $v ) );
1513 }
1514 public function getConstants( $class, $prefix, $reverse = false ) {
1515 global $tcmp;
1516 if ( is_object( $class ) ) {
1517 $class = get_class( $class );
1518 }
1519 $class = str_replace( 'Search', '', $class );
1520 $class = str_replace( 'Constants', '', $class );
1521 $class .= 'Constants';
1522 if ( ! class_exists( $class ) ) {
1523 $class = TCMP_PLUGIN_PREFIX . $class;
1524 }
1525
1526 $result = array();
1527 if ( class_exists( $class ) ) {
1528 $reflection = new ReflectionClass( $class );
1529 $array = $reflection->getConstants();
1530 foreach ( $array as $k => $v ) {
1531 $pos = 0;
1532 if ( '' != $prefix ) {
1533 $pos = stripos( $k, $prefix );
1534 }
1535 if ( 0 === $pos ) {
1536 if ( $reverse ) {
1537 $result[ $v ] = $k;
1538 } else {
1539 $result[ $k ] = $v;
1540 }
1541 }
1542 }
1543 }
1544 return $result;
1545 }
1546 public function getConstantValue( $class, $prefix, $name, $default = false ) {
1547 /* @var $ec TCMP_Singleton */
1548 global $ec;
1549 $result = $default;
1550 if ( is_object( $class ) ) {
1551 $class = get_class( $class );
1552 }
1553 $class = str_replace( 'Search', '', $class );
1554 $class = str_replace( 'Constants', '', $class );
1555 $class .= 'Constants';
1556 if ( ! class_exists( $class ) ) {
1557 $class = TCMP_PLUGIN_PREFIX . $class;
1558 }
1559
1560 if ( class_exists( $class ) ) {
1561 $name = $prefix . '_' . $name;
1562 $name = $ec->utils->upperUnderscoreCase( $name );
1563 $reflection = new ReflectionClass( $class );
1564 $result = $reflection->getConstant( $name );
1565 }
1566 return $result;
1567 }
1568 public function getConstantName( $class, $prefix, $value, $default = false ) {
1569 /* @var $ec TCMP_Singleton */
1570 $constants = $this->getConstants( $class, $prefix, true );
1571 $result = $default;
1572 if ( isset( $constants[ $value ] ) ) {
1573 $result = $constants[ $value ];
1574 }
1575 return $result;
1576 }
1577 public function daysDiff( $dt1, $dt2 ) {
1578 $dt1 = $this->parse_date_to_time( $dt1 );
1579 $dt2 = $this->parse_date_to_time( $dt2 );
1580 $result = ( $dt2 - $dt1 ) / 86400;
1581 $result = intval( $result );
1582 return $result;
1583 }
1584
1585 public function getText( $text, $args ) {
1586 if ( false === $args || 0 == count( $args ) ) {
1587 return $text;
1588 }
1589
1590 foreach ( $args as $k => $v ) {
1591 $text = str_replace( '{' . $k . '}', $v, $text );
1592 }
1593 return $text;
1594 }
1595 public function arrayExtends( $options, $defaults ) {
1596 global $tcmp;
1597 $options = $tcmp->utils->parseArgs( $options, $defaults );
1598 foreach ( $options as $k => $v ) {
1599 if ( is_bool( $v ) ) {
1600 $v = ( $v ? 1 : 0 );
1601 }
1602 if ( isset( $defaults[ $k ] ) ) {
1603 if ( $this->is_associativeArray( $v ) ) {
1604 $v = $this->arrayExtends( $v, $defaults[ $k ] );
1605 } else {
1606 $v = $tcmp->utils->to_array( $v );
1607 $old = $defaults[ $k ];
1608 $old = $tcmp->utils->to_array( $old );
1609 if ( ! $this->is_associativeArray( $old ) ) {
1610 $v = array_merge( $v, $old );
1611 $v = array_unique( $v );
1612 }
1613 }
1614 } else {
1615 $v = $tcmp->utils->to_array( $v );
1616 }
1617 $options[ $k ] = $v;
1618 }
1619 return $options;
1620 }
1621 //send remote request to our server to store tracking and feedback
1622 function remotePost( $action, $data = '' ) {
1623 global $tcmp;
1624
1625 $data['secret'] = 'WYSIWYG';
1626 $response = wp_remote_post(
1627 TCMP_INTELLYWP_ENDPOINT . '?iwpm_action=' . $action,
1628 array(
1629 'method' => 'POST',
1630 'timeout' => 20,
1631 'redirection' => 5,
1632 'httpversion' => '1.1',
1633 'blocking' => true,
1634 'body' => $data,
1635 'user-agent' => TCMP_PLUGIN_NAME . '/' . TCMP_PLUGIN_VERSION . '; ' . get_bloginfo( 'url' ),
1636 )
1637 );
1638 $data = json_decode( wp_remote_retrieve_body( $response ), true );
1639 if ( is_wp_error( $response ) || wp_remote_retrieve_response_code( $response ) != 200
1640 || ! isset( $data['success'] ) || ! $data['success']
1641 ) {
1642 $tcmp->log->error( 'ERRORS SENDING REMOTE-POST ACTION=%s DUE TO REASON=%s', $action, $response );
1643 $data = false;
1644 } else {
1645 $tcmp->log->debug( 'SUCCESSFULLY SENT REMOTE-POST ACTION=%s RESPONSE=%s', $action, $data );
1646 }
1647 return $data;
1648 }
1649
1650 function isPluginPage() {
1651 global $tcmp;
1652 $page = tcmp_sqs( 'page' );
1653 $result = ( $this->starts_with( $page, TCMP_PLUGIN_SLUG ) );
1654 return $result;
1655 }
1656
1657 public function arrayPush( &$array, $another ) {
1658 if ( ! is_array( $another ) ) {
1659 array_push( $array, $another );
1660 } elseif ( is_array( $another ) ) {
1661 foreach ( $another as $v ) {
1662 array_push( $array, $v );
1663 }
1664 }
1665 return $array;
1666 }
1667
1668 public function getConstantsValues( $class, $prefix = '', $glue = false ) {
1669 $array = $this->getConstants( $class, $prefix );
1670 $result = array_values( $array );
1671 if ( false !== $glue ) {
1672 $result = implode( $glue, $result );
1673 }
1674 return $result;
1675
1676 }
1677 public function getValue( $array, $index, $default = false ) {
1678 $result = $this->get_index( $array, $index, $default );
1679 if ( $result !== $default ) {
1680 $result = $result['v'];
1681 }
1682 return $result;
1683 }
1684 public function get_key( $array, $index, $default = false ) {
1685 $result = $this->get_index( $array, $index, $default );
1686 if ( $result !== $default ) {
1687 $result = $result['k'];
1688 }
1689 return $result;
1690 }
1691 public function get_index( $array, $index, $default = false ) {
1692 $result = $default;
1693 if ( is_array( $array ) && count( $array ) > 0 ) {
1694 if ( $this->is_associativeArray( $array ) ) {
1695 $i = 0;
1696 foreach ( $array as $k => $v ) {
1697 if ( $index == $i ) {
1698 $result = array(
1699 'k' => $k,
1700 'v' => $v,
1701 );
1702 break;
1703 }
1704 $i++;
1705 }
1706 } else {
1707 if ( $index < count( $array ) && $index >= 0 ) {
1708 $result = $array[ $index ];
1709 }
1710 }
1711 }
1712 return $result;
1713 }
1714 public function is_empty( $v ) {
1715 if ( ! $v ) {
1716 return true;
1717 }
1718
1719 $result = false;
1720 if ( is_string( $v ) ) {
1721 $result = ( '' == $v );
1722 } elseif ( is_array( $v ) ) {
1723 $result = 0 == count( $v );
1724 } elseif ( is_object( $v ) ) {
1725 $result = true;
1726 foreach ( $v as $k => $w ) {
1727 if ( ! is_null( $w ) && '' !== $w ) {
1728 $result = false;
1729 break;
1730 }
1731 }
1732 }
1733 return $result;
1734 }
1735 public function httpEncode( $v ) {
1736 $v = gzcompress( $v );
1737 $v = bin2hex( $v );
1738 return $v;
1739 }
1740 public function httpDecode( $v ) {
1741 $v = hex2bin( $v );
1742 $v = gzuncompress( $v );
1743 return $v;
1744 }
1745 public function trimHttp( $uri ) {
1746 $uri = str_replace( 'http://', '', $uri );
1747 $uri = str_replace( 'https://', '', $uri );
1748 return $uri;
1749 }
1750 function getClientIpAddress() {
1751 $ipaddress = '';
1752 if ( getenv( 'HTTP_CLIENT_IP' ) ) {
1753 $ipaddress = getenv( 'HTTP_CLIENT_IP' );
1754 } elseif ( getenv( 'HTTP_X_FORWARDED_FOR' ) ) {
1755 $ipaddress = getenv( 'HTTP_X_FORWARDED_FOR' );
1756 } elseif ( getenv( 'HTTP_X_FORWARDED' ) ) {
1757 $ipaddress = getenv( 'HTTP_X_FORWARDED' );
1758 } elseif ( getenv( 'HTTP_FORWARDED_FOR' ) ) {
1759 $ipaddress = getenv( 'HTTP_FORWARDED_FOR' );
1760 } elseif ( getenv( 'HTTP_FORWARDED' ) ) {
1761 $ipaddress = getenv( 'HTTP_FORWARDED' );
1762 } elseif ( getenv( 'REMOTE_ADDR' ) ) {
1763 $ipaddress = getenv( 'REMOTE_ADDR' );
1764 } else {
1765 $ipaddress = 'UNKNOWN';
1766 }
1767 $ipaddress = ( '::1' == $ipaddress ) ? '192.168.0.1' : $ipaddress;
1768 return $ipaddress;
1769 }
1770 public function isMail( $mail ) {
1771 $at = strpos( $mail, '@' );
1772 $dot = strrpos( $mail, '.' );
1773 $result = false;
1774 if ( false !== $at && false !== $dot && $at < $dot ) {
1775 $result = true;
1776 }
1777 return $result;
1778 }
1779 public function getNameFromListArray( $array, $id, $default = false ) {
1780 $result = $default;
1781 foreach ( $array as $v ) {
1782 if ( $v['id'] == $id ) {
1783 if ( isset( $v['text'] ) ) {
1784 $result = $v['text'];
1785 break;
1786 } elseif ( isset( $v['name'] ) ) {
1787 $result = $v['name'];
1788 break;
1789 }
1790 }
1791 }
1792 return $result;
1793 }
1794 function bqs( $name, $default = false ) {
1795 $v = $this->qs( $name, '' );
1796 $result = $default;
1797 if ( '' != $v ) {
1798 if ( is_numeric( $v ) ) {
1799 $v = intval( $v );
1800 $result = ( $v > 0 );
1801 } else {
1802 $result = $this->isTrue( $v );
1803 }
1804 }
1805 return $result;
1806 }
1807
1808 function getFunctionName( $function ) {
1809 $result = false;
1810 if ( is_string( $function ) ) {
1811 $result = $function;
1812 } elseif ( is_array( $function ) ) {
1813 $result = $function[1];
1814 }
1815 return $result;
1816 }
1817 function functionExists( $function ) {
1818 $result = false;
1819 if ( is_string( $function ) ) {
1820 $result = function_exists( $function );
1821 } elseif ( is_array( $function ) ) {
1822 $result = method_exists( $function[0], $function[1] );
1823 } elseif ( is_callable( $function ) ) {
1824 $result = true;
1825 }
1826 return $result;
1827 }
1828 function functionCall() {
1829 $args = func_get_args();
1830 if ( false === $args || 0 == count( $args ) ) {
1831 return;
1832 }
1833
1834 $function = array_shift( $args );
1835 $result = null;
1836 if ( $this->functionExists( $function ) ) {
1837 $result = call_user_func_array( $function, $args );
1838 }
1839 return $result;
1840 }
1841
1842 public function contains( $v1, $v2, $ignore_case = true ) {
1843 $result = false;
1844 if ( $ignore_case ) {
1845 $result = stripos( $v1, $v2 ) !== false;
1846 } else {
1847 $result = strpos( $v1, $v2 ) !== false;
1848 }
1849 return $result;
1850 }
1851
1852 private function getHtmlCode( $value ) {
1853 $value = str_replace( '\"', '', $value );
1854 $value = str_replace( '"', '', $value );
1855 return $value;
1856 }
1857
1858 public function dequeueScripts( $array ) {
1859 if ( ! function_exists( 'wp_scripts' ) || function_exists( 'wp_dequeue_script' ) ) {
1860 return;
1861 }
1862
1863 $array = $this->to_array( $array );
1864 $scripts = wp_scripts();
1865 /* @var $v _WP_Dependency */
1866 foreach ( $scripts->registered as $k => $v ) {
1867 foreach ( $array as $pattern ) {
1868 if ( $this->contains( $v->src, $pattern ) || $this->contains( $v->handle, $pattern ) ) {
1869 wp_dequeue_script( $v->handle );
1870 break;
1871 }
1872 }
1873 }
1874 }
1875 public function dequeueStyles( $array ) {
1876 if ( ! function_exists( 'wp_styles' ) || function_exists( 'wp_dequeue_style' ) ) {
1877 return;
1878 }
1879
1880 $array = $this->to_array( $array );
1881 $styles = wp_styles();
1882 /* @var $v _WP_Dependency */
1883 foreach ( $styles->registered as $k => $v ) {
1884 foreach ( $array as $pattern ) {
1885 if ( $this->contains( $v->src, $pattern ) || $this->contains( $v->handle, $pattern ) ) {
1886 wp_dequeue_style( $v->handle );
1887 break;
1888 }
1889 }
1890 }
1891 }
1892 public function formatSeconds( $time ) {
1893 if ( '' === $time ) {
1894 return '';
1895 }
1896
1897 $time = intval( $time );
1898 $seconds = ( $time % 60 );
1899 $time = ( ( $time - $seconds ) / 60 );
1900 $minutes = ( $time % 60 );
1901 $time = ( ( $time - $minutes ) / 60 );
1902 $hours = ( $time % 24 );
1903 $time = ( ( $time - $hours ) / 24 );
1904 $days = $time;
1905
1906 $array = array();
1907 if ( $seconds > 0 ) {
1908 $array[] = $seconds . 's';
1909 }
1910 if ( $minutes > 0 ) {
1911 $array[] = $minutes . 'm';
1912 }
1913 if ( $hours > 0 ) {
1914 $array[] = $hours . 'h';
1915 }
1916 if ( $days > 0 ) {
1917 $array[] = $days . 'd';
1918 }
1919 $array = array_reverse( $array );
1920 $text = implode( ' ', $array );
1921 return $text;
1922 }
1923
1924 function formatPercentage( $value, $options = array() ) {
1925 if ( is_bool( $options ) ) {
1926 $options = array( 'symbol' => $options );
1927 }
1928 $defaults = array( 'symbol' => true );
1929 $options = $this->parseArgs( $options, $defaults );
1930
1931 $value = floatval( $value );
1932 $value = round( $value, 3 );
1933 $value = number_format( $value, 3, ',', '' );
1934 if ( $options['symbol'] ) {
1935 $value .= ' %';
1936 }
1937 return $value;
1938 }
1939 function formatCurrencyMoney( $value, $options = array() ) {
1940 $defaults = array( 'currency' => $this->getDefaultCurrencySymbol() );
1941 $options = $this->parseArgs( $options, $defaults );
1942
1943 $value = $this->formatMoney( $value, $options );
1944 return $value;
1945 }
1946 function formatMoney( $value, $options = array() ) {
1947 if ( is_string( $options ) ) {
1948 $options = array( 'currency' => $options );
1949 }
1950 $defaults = array( 'currency' => false );
1951 $options = $this->parseArgs( $options, $defaults );
1952
1953 $value = floatval( $value );
1954 $value = round( $value, 3 );
1955 $value = number_format( $value, 3, ',', '.' );
1956 if ( '' != $options['currency'] ) {
1957 $symbol = $options['currency'];
1958 if ( strlen( $symbol ) > 1 ) {
1959 $symbol = $this->getCurrencySymbol( $symbol );
1960 }
1961 $value .= ' ' . $symbol;
1962 }
1963 return $value;
1964 }
1965 function sortOptions( &$options ) {
1966 if ( ! is_array( $options ) ) {
1967 return $options;
1968 }
1969
1970 usort( $options, array( $this, 'sortOptions_Compare' ) );
1971 return $options;
1972 }
1973 public function sortOptions_Compare( $o1, $o2 ) {
1974 global $tcmp;
1975 $v1 = $tcmp->utils->get( $o1, 'text', false );
1976 if ( false == $v1 ) {
1977 $v1 = $tcmp->utils->get( $o1, 'name', false );
1978 }
1979 $v2 = $tcmp->utils->get( $o2, 'text', false );
1980 if ( false == $v2 ) {
1981 $v2 = $tcmp->utils->get( $o2, 'name', false );
1982 }
1983
1984 //to order properly
1985 if ( $tcmp->utils->starts_with( $v1, '[' ) ) {
1986 $v1 = ' ' . $v1;
1987 }
1988 if ( $tcmp->utils->starts_with( $v2, '[' ) ) {
1989 $v2 = ' ' . $v2;
1990 }
1991 return strcasecmp( $v1, $v2 );
1992 }
1993
1994 private function validate_ip( $ip ) {
1995 if ( filter_var( $ip, FILTER_VALIDATE_IP ) ) {
1996 return $ip;
1997 }
1998 return '';
1999 }
2000
2001 public function getVisitorIpAddress() {
2002 // Only REMOTE_ADDR is set by the web server and cannot be spoofed by the
2003 // client. HTTP_CLIENT_IP / HTTP_X_FORWARDED_FOR are attacker-controllable
2004 // request headers and must never be trusted for a security decision, so
2005 // they are intentionally NOT consulted here. Also calls the real instance
2006 // method $this->validate_ip() (the previous global validate_ip() call
2007 // would have fatal-errored). (See F-12.)
2008 $ip = '';
2009 if ( ! empty( $_SERVER['REMOTE_ADDR'] ) ) {
2010 $ip = $this->validate_ip( sanitize_text_field( wp_unslash( $_SERVER['REMOTE_ADDR'] ) ) );
2011 }
2012 return $ip;
2013 }
2014
2015 function getCurrencySymbol( $currency ) {
2016 // Create a NumberFormatter
2017 $locale = 'en_US';
2018 $formatter = new NumberFormatter( $locale, NumberFormatter::CURRENCY );
2019
2020 // Figure out what 0.00 looks like with the currency symbol
2021 $withCurrency = $formatter->formatCurrency( 0, $currency );
2022
2023 // Figure out what 0.00 looks like without the currency symbol
2024 $formatter->setPattern( str_replace( '¤', '', $formatter->getPattern() ) );
2025 $without_currency = $formatter->formatCurrency( 0, $currency );
2026
2027 // Extract just the currency symbol from the first string
2028 return str_replace( $without_currency, '', $withCurrency );
2029 }
2030 function encodeUri( $string ) {
2031 $entities = array( '%21', '%2A', '%27', '%28', '%29', '%3B', '%3A', '%40', '%26', '%3D', '%2B', '%24', '%2C', '%2F', '%3F', '%23', '%5B', '%5D' );
2032 $replacements = array( '!', '*', "'", '(', ')', ';', ':', '@', '&', '=', '+', '$', ',', '/', '?', '#', '[', ']' );
2033 $result = urlencode( $string );
2034 //$result=str_replace($replacements, $entities, $result);
2035 return $result;
2036 }
2037
2038 public function formatTimer( $time ) {
2039 if ( ! is_int( $time ) ) {
2040 if ( is_string( $time ) ) {
2041 $time = str_replace( ' ', ':', $time );
2042 $time = str_replace( '.', ':', $time );
2043 $time = str_replace( '/', ':', $time );
2044 $time = explode( ':', $time );
2045
2046 $length = count( $time );
2047 $days = 0;
2048 $hours = 0;
2049 $minutes = 0;
2050 $secs = intval( $time[ $length - 1 ] );
2051
2052 if ( $length > 1 ) {
2053 $minutes = intval( $time[ $length - 2 ] );
2054 if ( $length > 2 ) {
2055 $hours = intval( $time[ $length - 3 ] );
2056 if ( $length > 3 ) {
2057 $days = intval( $time[ $length - 4 ] );
2058 }
2059 }
2060 }
2061 $time = $days * 86400 + $hours * 3600 + $minutes * 60 + $secs;
2062 } else {
2063 $time = 0;
2064 }
2065 } else {
2066 $time = intval( $time );
2067 }
2068
2069 $secs = $time % 60;
2070 $time = ( $time - $secs ) / 60;
2071 $minutes = $time % 60;
2072 $time = ( $time - $minutes ) / 60;
2073 $hours = $time % 24;
2074 $days = ( $time - $hours ) / 24;
2075
2076 $result = array();
2077 $result[] = $days;
2078 $result[] = ( $hours < 10 ? '0' : '' ) . $hours;
2079 $result[] = ( $minutes < 10 ? '0' : '' ) . $minutes;
2080 $result[] = ( $secs < 10 ? '0' : '' ) . $secs;
2081 $result = implode( ':', $result );
2082 return $result;
2083 }
2084 public function parseTimer( $time ) {
2085 $time = $this->formatTimer( $time );
2086 $time = explode( ':', $time );
2087 $result = intval( $time[0] ) * 86400 + intval( $time[1] ) * 3600 + intval( $time[2] ) * 60 + intval( $time[3] );
2088 return $result;
2089 }
2090 }
2091