Completed
Push — master ( 933836...32a7c2 )
by Mike
08:12
created

wc-formatting-functions.php ➔ wc_sanitize_permalink()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 13
Code Lines 8

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 1 Features 0
Metric Value
cc 2
eloc 8
c 1
b 1
f 0
nc 2
nop 1
dl 0
loc 13
rs 9.4285
1
<?php
2
/**
3
 * WooCommerce Formatting
4
 *
5
 * Functions for formatting data.
6
 *
7
 * @author 		WooThemes
8
 * @category 	Core
9
 * @package 	WooCommerce/Functions
10
 * @version     2.1.0
11
 */
12
13
if ( ! defined( 'ABSPATH' ) ) {
14
	exit; // Exit if accessed directly
15
}
16
17
/**
18
 * Sanitize taxonomy names. Slug format (no spaces, lowercase).
19
 *
20
 * urldecode is used to reverse munging of UTF8 characters.
21
 *
22
 * @param mixed $taxonomy
23
 * @return string
24
 */
25
function wc_sanitize_taxonomy_name( $taxonomy ) {
26
	return apply_filters( 'sanitize_taxonomy_name', urldecode( sanitize_title( $taxonomy ) ), $taxonomy );
27
}
28
29
/**
30
 * Sanitize permalink values before insertion into DB.
31
 *
32
 * Cannot use wc_clean because it sometimes strips % chars and breaks the user's setting.
33
 *
34
 * @since 2.6.0
35
 * @param string $taxonomy
0 ignored issues
show
Bug introduced by
There is no parameter named $taxonomy. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
36
 * @return string
37
 */
38
function wc_sanitize_permalink( $value ) {
39
	global $wpdb;
40
41
	$value = $wpdb->strip_invalid_text_for_column( $wpdb->options, 'option_value', $value );
42
43
	if ( is_wp_error( $value ) ) {
44
		$value = '';
45
	}
46
47
	$value = esc_url_raw( $value );
48
	$value = str_replace( 'http://', '', $value );
49
	return untrailingslashit( $value );
50
}
51
52
/**
53
 * Gets the filename part of a download URL.
54
 *
55
 * @param string $file_url
56
 * @return string
57
 */
58
function wc_get_filename_from_url( $file_url ) {
59
	$parts = parse_url( $file_url );
60
	if ( isset( $parts['path'] ) ) {
61
		return basename( $parts['path'] );
62
	}
63
}
64
65
/**
66
 * Normalise dimensions, unify to cm then convert to wanted unit value.
67
 *
68
 * Usage:
69
 * wc_get_dimension(55, 'in');
70
 * wc_get_dimension(55, 'in', 'm');
71
 *
72
 * @param int|float $dimension
73
 * @param string $to_unit 'in', 'm', 'cm', 'm'
74
 * @param string $from_unit (optional) 'in', 'm', 'cm', 'm'
75
 * @return float
76
 */
77
function wc_get_dimension( $dimension, $to_unit, $from_unit = '' ) {
78
	$to_unit = strtolower( $to_unit );
79
80
	if ( empty( $from_unit ) ) {
81
		$from_unit = strtolower( get_option( 'woocommerce_dimension_unit' ) );
82
	}
83
84
	// Unify all units to cm first.
85
	if ( $from_unit !== $to_unit ) {
86 View Code Duplication
		switch ( $from_unit ) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
87
			case 'in' :
88
				$dimension *= 2.54;
89
				break;
90
			case 'm' :
91
				$dimension *= 100;
92
				break;
93
			case 'mm' :
94
				$dimension *= 0.1;
95
				break;
96
			case 'yd' :
97
				$dimension *= 91.44;
98
				break;
99
		}
100
101
		// Output desired unit.
102 View Code Duplication
		switch ( $to_unit ) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
103
			case 'in' :
104
				$dimension *= 0.3937;
105
				break;
106
			case 'm' :
107
				$dimension *= 0.01;
108
				break;
109
			case 'mm' :
110
				$dimension *= 10;
111
				break;
112
			case 'yd' :
113
				$dimension *= 0.010936133;
114
				break;
115
		}
116
	}
117
118
	return ( $dimension < 0 ) ? 0 : $dimension;
119
}
120
121
/**
122
 * Normalise weights, unify to kg then convert to wanted unit value.
123
 *
124
 * Usage:
125
 * wc_get_weight(55, 'kg');
126
 * wc_get_weight(55, 'kg', 'lbs');
127
 *
128
 * @param int|float $weight
129
 * @param string $to_unit 'g', 'kg', 'lbs', 'oz'
130
 * @param string $from_unit (optional) 'g', 'kg', 'lbs', 'oz'
131
 * @return float
132
 */
133
function wc_get_weight( $weight, $to_unit, $from_unit = '' ) {
134
	$to_unit = strtolower( $to_unit );
135
136
	if ( empty( $from_unit ) ) {
137
		$from_unit = strtolower( get_option( 'woocommerce_weight_unit' ) );
138
	}
139
140
	// Unify all units to kg first.
141
	if ( $from_unit !== $to_unit ) {
142
		switch ( $from_unit ) {
143
			case 'g' :
144
				$weight *= 0.001;
145
				break;
146
			case 'lbs' :
147
				$weight *= 0.453592;
148
				break;
149
			case 'oz' :
150
				$weight *= 0.0283495;
151
				break;
152
		}
153
154
		// Output desired unit.
155
		switch ( $to_unit ) {
156
			case 'g' :
157
				$weight *= 1000;
158
				break;
159
			case 'lbs' :
160
				$weight *= 2.20462;
161
				break;
162
			case 'oz' :
163
				$weight *= 35.274;
164
				break;
165
		}
166
	}
167
168
	return ( $weight < 0 ) ? 0 : $weight;
169
}
170
171
/**
172
 * Trim trailing zeros off prices.
173
 *
174
 * @param mixed $price
175
 * @return string
176
 */
177
function wc_trim_zeros( $price ) {
178
	return preg_replace( '/' . preg_quote( wc_get_price_decimal_separator(), '/' ) . '0++$/', '', $price );
179
}
180
181
/**
182
 * Round a tax amount.
183
 *
184
 * @param mixed $tax
185
 * @return double
186
 */
187
function wc_round_tax_total( $tax ) {
188
	$dp = wc_get_price_decimals();
189
190
	// @codeCoverageIgnoreStart
191
	if ( version_compare( phpversion(), '5.3', '<' ) ) {
192
		$rounded_tax = round( $tax, $dp );
193
	} else {
194
		// @codeCoverageIgnoreEnd
195
		$rounded_tax = round( $tax, $dp, WC_TAX_ROUNDING_MODE );
196
	}
197
	return apply_filters( 'wc_round_tax_total', $rounded_tax, $tax, $dp, WC_TAX_ROUNDING_MODE );
198
}
199
200
/**
201
 * Make a refund total negative.
202
 * @return float
203
 */
204
function wc_format_refund_total( $amount ) {
205
	return $amount * -1;
206
}
207
208
/**
209
 * Format decimal numbers ready for DB storage.
210
 *
211
 * Sanitize, remove locale formatting, and optionally round + trim off zeros.
212
 *
213
 * @param  float|string $number Expects either a float or a string with a decimal separator only (no thousands)
214
 * @param  mixed $dp number of decimal points to use, blank to use woocommerce_price_num_decimals, or false to avoid all rounding.
215
 * @param  bool $trim_zeros from end of string
216
 * @return string
217
 */
218
function wc_format_decimal( $number, $dp = false, $trim_zeros = false ) {
219
	$locale   = localeconv();
220
	$decimals = array( wc_get_price_decimal_separator(), $locale['decimal_point'], $locale['mon_decimal_point'] );
221
222
	// Remove locale from string
223
	if ( ! is_float( $number ) ) {
224
		$number = wc_clean( str_replace( $decimals, '.', $number ) );
225
	}
226
227
	if ( $dp !== false ) {
228
		$dp     = intval( $dp == "" ? wc_get_price_decimals() : $dp );
229
		$number = number_format( floatval( $number ), $dp, '.', '' );
230
231
	// DP is false - don't use number format, just return a string in our format
232
	} elseif ( is_float( $number ) ) {
233
		$number = wc_clean( str_replace( $decimals, '.', strval( $number ) ) );
234
	}
235
236
	if ( $trim_zeros && strstr( $number, '.' ) ) {
237
		$number = rtrim( rtrim( $number, '0' ), '.' );
238
	}
239
240
	return $number;
241
}
242
243
/**
244
 * Convert a float to a string without locale formatting which PHP adds when changing floats to strings.
245
 * @param  float $float
246
 * @return string
247
 */
248
function wc_float_to_string( $float ) {
249
	if ( ! is_float( $float ) ) {
250
		return $float;
251
	}
252
253
	$locale = localeconv();
254
	$string = strval( $float );
255
	$string = str_replace( $locale['decimal_point'], '.', $string );
256
257
	return $string;
258
}
259
260
/**
261
 * Format a price with WC Currency Locale settings.
262
 * @param  string $value
263
 * @return string
264
 */
265
function wc_format_localized_price( $value ) {
266
	return str_replace( '.', wc_get_price_decimal_separator(), strval( $value ) );
267
}
268
269
/**
270
 * Format a decimal with PHP Locale settings.
271
 * @param  string $value
272
 * @return string
273
 */
274
function wc_format_localized_decimal( $value ) {
275
	$locale = localeconv();
276
	return str_replace( '.', $locale['decimal_point'], strval( $value ) );
277
}
278
279
/**
280
 * Clean variables using sanitize_text_field. Arrays are cleaned recursively.
281
 * Non-scalar values are ignored.
282
 * @param string|array $var
283
 * @return string|array
284
 */
285
function wc_clean( $var ) {
286
	if ( is_array( $var ) ) {
287
		return array_map( 'wc_clean', $var );
288
	} else {
289
		return is_scalar( $var ) ? sanitize_text_field( $var ) : $var;
290
	}
291
}
292
293
/**
294
 * Sanitize a string destined to be a tooltip.
295
 *
296
 * @since 2.3.10 Tooltips are encoded with htmlspecialchars to prevent XSS. Should not be used in conjunction with esc_attr()
297
 * @param string $var
298
 * @return string
299
 */
300
function wc_sanitize_tooltip( $var ) {
301
	return htmlspecialchars( wp_kses( html_entity_decode( $var ), array(
302
		'br'     => array(),
303
		'em'     => array(),
304
		'strong' => array(),
305
		'small'  => array(),
306
		'span'   => array(),
307
		'ul'     => array(),
308
		'li'     => array(),
309
		'ol'     => array(),
310
		'p'      => array(),
311
    ) ) );
312
}
313
314
/**
315
 * Merge two arrays.
316
 *
317
 * @param array $a1
318
 * @param array $a2
319
 * @return array
320
 */
321
function wc_array_overlay( $a1, $a2 ) {
322
	foreach ( $a1 as $k => $v ) {
323
		if ( ! array_key_exists( $k, $a2 ) ) {
324
			continue;
325
		}
326
		if ( is_array( $v ) && is_array( $a2[ $k ] ) ) {
327
			$a1[ $k ] = wc_array_overlay( $v, $a2[ $k ] );
328
		} else {
329
			$a1[ $k ] = $a2[ $k ];
330
		}
331
	}
332
	return $a1;
333
}
334
335
/**
336
 * Formats a stock amount by running it through a filter.
337
 * @param  int|float $amount
338
 * @return int|float
339
 */
340
function wc_stock_amount( $amount ) {
341
	return apply_filters( 'woocommerce_stock_amount', $amount );
342
}
343
344
/**
345
 * Get the price format depending on the currency position.
346
 *
347
 * @return string
348
 */
349
function get_woocommerce_price_format() {
350
	$currency_pos = get_option( 'woocommerce_currency_pos' );
351
	$format = '%1$s%2$s';
352
353
	switch ( $currency_pos ) {
354
		case 'left' :
355
			$format = '%1$s%2$s';
356
		break;
357
		case 'right' :
358
			$format = '%2$s%1$s';
359
		break;
360
		case 'left_space' :
361
			$format = '%1$s&nbsp;%2$s';
362
		break;
363
		case 'right_space' :
364
			$format = '%2$s&nbsp;%1$s';
365
		break;
366
	}
367
368
	return apply_filters( 'woocommerce_price_format', $format, $currency_pos );
369
}
370
371
/**
372
 * Return the thousand separator for prices.
373
 * @since  2.3
374
 * @return string
375
 */
376
function wc_get_price_thousand_separator() {
377
	$separator = stripslashes( get_option( 'woocommerce_price_thousand_sep' ) );
378
	return $separator;
379
}
380
381
/**
382
 * Return the decimal separator for prices.
383
 * @since  2.3
384
 * @return string
385
 */
386
function wc_get_price_decimal_separator() {
387
	$separator = stripslashes( get_option( 'woocommerce_price_decimal_sep' ) );
388
	return $separator ? $separator : '.';
389
}
390
391
/**
392
 * Return the number of decimals after the decimal point.
393
 * @since  2.3
394
 * @return int
395
 */
396
function wc_get_price_decimals() {
397
	return absint( get_option( 'woocommerce_price_num_decimals', 2 ) );
398
}
399
400
/**
401
 * Format the price with a currency symbol.
402
 *
403
 * @param float $price
404
 * @param array $args (default: array())
405
 * @return string
406
 */
407
function wc_price( $price, $args = array() ) {
408
	extract( apply_filters( 'wc_price_args', wp_parse_args( $args, array(
409
		'ex_tax_label'       => false,
410
		'currency'           => '',
411
		'decimal_separator'  => wc_get_price_decimal_separator(),
412
		'thousand_separator' => wc_get_price_thousand_separator(),
413
		'decimals'           => wc_get_price_decimals(),
414
		'price_format'       => get_woocommerce_price_format()
415
	) ) ) );
416
417
	$negative        = $price < 0;
418
	$price           = apply_filters( 'raw_woocommerce_price', floatval( $negative ? $price * -1 : $price ) );
419
	$price           = apply_filters( 'formatted_woocommerce_price', number_format( $price, $decimals, $decimal_separator, $thousand_separator ), $price, $decimals, $decimal_separator, $thousand_separator );
420
421
	if ( apply_filters( 'woocommerce_price_trim_zeros', false ) && $decimals > 0 ) {
422
		$price = wc_trim_zeros( $price );
423
	}
424
425
	$formatted_price = ( $negative ? '-' : '' ) . sprintf( $price_format, '<span class="woocommerce-Price-currencySymbol">' . get_woocommerce_currency_symbol( $currency ) . '</span>', $price );
426
	$return          = '<span class="woocommerce-Price-amount amount">' . $formatted_price . '</span>';
427
428
	if ( $ex_tax_label && wc_tax_enabled() ) {
429
		$return .= ' <small class="woocommerce-Price-taxLabel tax_label">' . WC()->countries->ex_tax_or_vat() . '</small>';
430
	}
431
432
	return apply_filters( 'wc_price', $return, $price, $args );
433
}
434
435
/**
436
 * let_to_num function.
437
 *
438
 * This function transforms the php.ini notation for numbers (like '2M') to an integer.
439
 *
440
 * @param $size
441
 * @return int
442
 */
443
function wc_let_to_num( $size ) {
444
	$l   = substr( $size, -1 );
445
	$ret = substr( $size, 0, -1 );
446
	switch ( strtoupper( $l ) ) {
447
		case 'P':
448
			$ret *= 1024;
449
		case 'T':
450
			$ret *= 1024;
451
		case 'G':
452
			$ret *= 1024;
453
		case 'M':
454
			$ret *= 1024;
455
		case 'K':
456
			$ret *= 1024;
457
	}
458
	return $ret;
459
}
460
461
/**
462
 * WooCommerce Date Format - Allows to change date format for everything WooCommerce.
463
 *
464
 * @return string
465
 */
466
function wc_date_format() {
467
	return apply_filters( 'woocommerce_date_format', get_option( 'date_format' ) );
468
}
469
470
/**
471
 * WooCommerce Time Format - Allows to change time format for everything WooCommerce.
472
 *
473
 * @return string
474
 */
475
function wc_time_format() {
476
	return apply_filters( 'woocommerce_time_format', get_option( 'time_format' ) );
477
}
478
479
/**
480
 * WooCommerce Timezone - helper to retrieve the timezone string for a site until.
481
 * a WP core method exists (see https://core.trac.wordpress.org/ticket/24730).
482
 *
483
 * Adapted from https://secure.php.net/manual/en/function.timezone-name-from-abbr.php#89155.
484
 *
485
 * @since 2.1
486
 * @return string a valid PHP timezone string for the site
487
 */
488
function wc_timezone_string() {
489
490
	// if site timezone string exists, return it
491
	if ( $timezone = get_option( 'timezone_string' ) ) {
492
		return $timezone;
493
	}
494
495
	// get UTC offset, if it isn't set then return UTC
496
	if ( 0 === ( $utc_offset = get_option( 'gmt_offset', 0 ) ) ) {
497
		return 'UTC';
498
	}
499
500
	// adjust UTC offset from hours to seconds
501
	$utc_offset *= 3600;
502
503
	// attempt to guess the timezone string from the UTC offset
504
	$timezone = timezone_name_from_abbr( '', $utc_offset, 0 );
505
506
	// last try, guess timezone string manually
507
	if ( false === $timezone ) {
508
		$is_dst = date( 'I' );
509
510
		foreach ( timezone_abbreviations_list() as $abbr ) {
511
			foreach ( $abbr as $city ) {
512
				if ( $city['dst'] == $is_dst && $city['offset'] == $utc_offset ) {
513
					return $city['timezone_id'];
514
				}
515
			}
516
		}
517
518
		// fallback to UTC
519
		return 'UTC';
520
	}
521
522
	return $timezone;
523
}
524
525
if ( ! function_exists( 'wc_rgb_from_hex' ) ) {
526
527
	/**
528
	 * Hex darker/lighter/contrast functions for colours.
529
	 *
530
	 * @param mixed $color
531
	 * @return string
532
	 */
533
	function wc_rgb_from_hex( $color ) {
534
		$color = str_replace( '#', '', $color );
535
		// Convert shorthand colors to full format, e.g. "FFF" -> "FFFFFF"
536
		$color = preg_replace( '~^(.)(.)(.)$~', '$1$1$2$2$3$3', $color );
537
538
		$rgb      = array();
539
		$rgb['R'] = hexdec( $color{0}.$color{1} );
540
		$rgb['G'] = hexdec( $color{2}.$color{3} );
541
		$rgb['B'] = hexdec( $color{4}.$color{5} );
542
543
		return $rgb;
544
	}
545
}
546
547 View Code Duplication
if ( ! function_exists( 'wc_hex_darker' ) ) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
548
549
	/**
550
	 * Hex darker/lighter/contrast functions for colours.
551
	 *
552
	 * @param mixed $color
553
	 * @param int $factor (default: 30)
554
	 * @return string
555
	 */
556
	function wc_hex_darker( $color, $factor = 30 ) {
557
		$base  = wc_rgb_from_hex( $color );
558
		$color = '#';
559
560
		foreach ( $base as $k => $v ) {
561
			$amount      = $v / 100;
562
			$amount      = round( $amount * $factor );
563
			$new_decimal = $v - $amount;
564
565
			$new_hex_component = dechex( $new_decimal );
566
			if ( strlen( $new_hex_component ) < 2 ) {
567
				$new_hex_component = "0" . $new_hex_component;
568
			}
569
			$color .= $new_hex_component;
570
		}
571
572
		return $color;
573
	}
574
}
575
576 View Code Duplication
if ( ! function_exists( 'wc_hex_lighter' ) ) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
577
578
	/**
579
	 * Hex darker/lighter/contrast functions for colours.
580
	 *
581
	 * @param mixed $color
582
	 * @param int $factor (default: 30)
583
	 * @return string
584
	 */
585
	function wc_hex_lighter( $color, $factor = 30 ) {
586
		$base  = wc_rgb_from_hex( $color );
587
		$color = '#';
588
589
		foreach ( $base as $k => $v ) {
590
			$amount      = 255 - $v;
591
			$amount      = $amount / 100;
592
			$amount      = round( $amount * $factor );
593
			$new_decimal = $v + $amount;
594
595
			$new_hex_component = dechex( $new_decimal );
596
			if ( strlen( $new_hex_component ) < 2 ) {
597
				$new_hex_component = "0" . $new_hex_component;
598
			}
599
			$color .= $new_hex_component;
600
		}
601
602
		return $color;
603
	}
604
}
605
606
if ( ! function_exists( 'wc_light_or_dark' ) ) {
607
608
	/**
609
	 * Detect if we should use a light or dark colour on a background colour.
610
	 *
611
	 * @param mixed $color
612
	 * @param string $dark (default: '#000000')
613
	 * @param string $light (default: '#FFFFFF')
614
	 * @return string
615
	 */
616
	function wc_light_or_dark( $color, $dark = '#000000', $light = '#FFFFFF' ) {
617
618
		$hex = str_replace( '#', '', $color );
619
620
		$c_r = hexdec( substr( $hex, 0, 2 ) );
621
		$c_g = hexdec( substr( $hex, 2, 2 ) );
622
		$c_b = hexdec( substr( $hex, 4, 2 ) );
623
624
		$brightness = ( ( $c_r * 299 ) + ( $c_g * 587 ) + ( $c_b * 114 ) ) / 1000;
625
626
		return $brightness > 155 ? $dark : $light;
627
	}
628
}
629
630
if ( ! function_exists( 'wc_format_hex' ) ) {
631
632
	/**
633
	 * Format string as hex.
634
	 *
635
	 * @param string $hex
636
	 * @return string
637
	 */
638
	function wc_format_hex( $hex ) {
639
640
		$hex = trim( str_replace( '#', '', $hex ) );
641
642
		if ( strlen( $hex ) == 3 ) {
643
			$hex = $hex[0] . $hex[0] . $hex[1] . $hex[1] . $hex[2] . $hex[2];
644
		}
645
646
		return $hex ? '#' . $hex : null;
647
	}
648
}
649
650
/**
651
 * Format the postcode according to the country and length of the postcode.
652
 *
653
 * @param string $postcode
654
 * @param string $country
655
 * @return string Formatted postcode.
656
 */
657
function wc_format_postcode( $postcode, $country ) {
658
	$postcode = wc_normalize_postcode( $postcode );
659
660
	switch ( $country ) {
661
		case 'CA' :
662
		case 'GB' :
663
			$postcode = trim( substr_replace( $postcode, ' ', -3, 0 ) );
664
			break;
665
		case 'BR' :
666
			$postcode = trim( substr_replace( $postcode, '-', -3, 0 ) );
667
			break;
668
	}
669
670
	return apply_filters( 'woocommerce_format_postcode', $postcode, $country );
671
}
672
673
/**
674
 * Normalize postcodes.
675
 *
676
 * Remove spaces and convert characters to uppercase.
677
 *
678
 * @since 2.6.0
679
 * @param string $postcode
680
 * @return string Sanitized postcode.
681
 */
682
function wc_normalize_postcode( $postcode ) {
683
	return trim( preg_replace( '/[\s\-]/', '', strtoupper( $postcode ) ) );
684
}
685
686
/**
687
 * format_phone function.
688
 *
689
 * @param mixed $tel
690
 * @return string
691
 */
692
function wc_format_phone_number( $tel ) {
693
	return str_replace( '.', '-', $tel );
694
}
695
696
/**
697
 * Make a string lowercase.
698
 * Try to use mb_strtolower() when available.
699
 *
700
 * @since  2.3
701
 * @param  string $string
702
 * @return string
703
 */
704
function wc_strtolower( $string ) {
705
	return function_exists( 'mb_strtolower' ) ? mb_strtolower( $string ) : strtolower( $string );
706
}
707
708
/**
709
 * Trim a string and append a suffix.
710
 * @param  string  $string
711
 * @param  integer $chars
712
 * @param  string  $suffix
713
 * @return string
714
 */
715
function wc_trim_string( $string, $chars = 200, $suffix = '...' ) {
716
	if ( strlen( $string ) > $chars ) {
717
		if ( function_exists( 'mb_substr' ) ) {
718
			$string = mb_substr( $string, 0, ( $chars - mb_strlen( $suffix ) ) ) . $suffix;
719
		} else {
720
			$string = substr( $string, 0, ( $chars - strlen( $suffix ) ) ) . $suffix;
721
		}
722
	}
723
	return $string;
724
}
725
726
/**
727
 * Format content to display shortcodes.
728
 *
729
 * @since  2.3.0
730
 * @param  string $raw_string
731
 * @return string
732
 */
733
function wc_format_content( $raw_string ) {
734
	return apply_filters( 'woocommerce_format_content', do_shortcode( shortcode_unautop( wpautop( $raw_string ) ) ), $raw_string );
735
}
736
737
/**
738
 * Format product short description.
739
 * Adds support for Jetpack Markdown.
740
 *
741
 * @since  2.4.0
742
 * @param  string $content
743
 * @return string
744
 */
745
function wc_format_product_short_description( $content ) {
746
	// Add support for Jetpack Markdown
747
	if ( class_exists( 'WPCom_Markdown' ) ) {
748
		$markdown = WPCom_Markdown::get_instance();
749
750
		return wpautop( $markdown->transform( $content, array( 'unslash' => false ) ) );
751
	}
752
753
	return $content;
754
}
755
756
add_filter( 'woocommerce_short_description', 'wc_format_product_short_description', 9999999 );
757
758
/**
759
 * Formats curency symbols when saved in settings.
760
 * @param  string $value
761
 * @param  array $option
762
 * @param  string $raw_value
763
 * @return string
764
 */
765
function wc_format_option_price_separators( $value, $option, $raw_value ) {
0 ignored issues
show
Unused Code introduced by
The parameter $value is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
Unused Code introduced by
The parameter $option is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
766
	return wp_kses_post( $raw_value );
767
}
768
add_filter( 'woocommerce_admin_settings_sanitize_option_woocommerce_price_decimal_sep', 'wc_format_option_price_separators', 10, 3 );
769
add_filter( 'woocommerce_admin_settings_sanitize_option_woocommerce_price_thousand_sep', 'wc_format_option_price_separators', 10, 3 );
770
771
/**
772
 * Formats decimals when saved in settings.
773
 * @param  string $value
774
 * @param  array $option
775
 * @param  string $raw_value
776
 * @return string
777
 */
778
function wc_format_option_price_num_decimals( $value, $option, $raw_value ) {
0 ignored issues
show
Unused Code introduced by
The parameter $value is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
Unused Code introduced by
The parameter $option is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
779
	return is_null( $raw_value ) ? 2 : absint( $raw_value );
780
}
781
add_filter( 'woocommerce_admin_settings_sanitize_option_woocommerce_price_num_decimals', 'wc_format_option_price_num_decimals', 10, 3 );
782
783
/**
784
 * Formats hold stock option and sets cron event up.
785
 * @param  string $value
786
 * @param  array $option
787
 * @param  string $raw_value
788
 * @return string
789
 */
790
function wc_format_option_hold_stock_minutes( $value, $option, $raw_value ) {
0 ignored issues
show
Unused Code introduced by
The parameter $value is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
Unused Code introduced by
The parameter $option is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
791
	$value = ! empty( $raw_value ) ? absint( $raw_value ) : ''; // Allow > 0 or set to ''
792
793
	wp_clear_scheduled_hook( 'woocommerce_cancel_unpaid_orders' );
794
795
	if ( '' !== $value ) {
796
		wp_schedule_single_event( time() + ( absint( $value ) * 60 ), 'woocommerce_cancel_unpaid_orders' );
797
	}
798
799
	return $value;
800
}
801
add_filter( 'woocommerce_admin_settings_sanitize_option_woocommerce_hold_stock_minutes', 'wc_format_option_hold_stock_minutes', 10, 3 );
802
803
/**
804
 * Sanitize terms from an attribute text based.
805
 *
806
 * @since  2.4.5
807
 * @param  string $term
808
 * @return string
809
 */
810
function wc_sanitize_term_text_based( $term ) {
811
	return trim( wp_unslash( strip_tags( $term ) ) );
812
}
813
814
if ( ! function_exists( 'wc_make_numeric_postcode' ) ) {
815
	/**
816
	 * Make numeric postcode.
817
	 *
818
	 * Converts letters to numbers so we can do a simple range check on postcodes.
819
	 * E.g. PE30 becomes 16050300 (P = 16, E = 05, 3 = 03, 0 = 00)
820
	 *
821
	 * @since 2.6.0
822
	 * @param string $postcode Regular postcode
823
	 * @return string
824
	 */
825
	function wc_make_numeric_postcode( $postcode ) {
826
		$postcode_length    = strlen( $postcode );
827
		$letters_to_numbers = array_merge( array( 0 ), range( 'A', 'Z' ) );
828
		$letters_to_numbers = array_flip( $letters_to_numbers );
829
		$numeric_postcode   = '';
830
831
		for ( $i = 0; $i < $postcode_length; $i ++ ) {
832
			if ( is_numeric( $postcode[ $i ] ) ) {
833
				$numeric_postcode .= str_pad( $postcode[ $i ], 2, '0', STR_PAD_LEFT );
834
			} elseif ( isset( $letters_to_numbers[ $postcode[ $i ] ] ) ) {
835
				$numeric_postcode .= str_pad( $letters_to_numbers[ $postcode[ $i ] ], 2, '0', STR_PAD_LEFT );
836
			} else {
837
				$numeric_postcode .= '00';
838
			}
839
		}
840
841
		return $numeric_postcode;
842
	}
843
}
844