Completed
Push — master ( e21a4d...f0ee76 )
by Reginaldo
36:32
created

Functions.php ➔ money_format()   F

Complexity

Conditions 31
Paths > 20000

Size

Total Lines 91
Code Lines 74

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 31
eloc 74
c 0
b 0
f 0
nc 645122
nop 2
dl 0
loc 91
rs 2.0658

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
/**
3
 * PHPExcel
4
 *
5
 * Copyright (c) 2006 - 2012 PHPExcel
6
 *
7
 * This library is free software; you can redistribute it and/or
8
 * modify it under the terms of the GNU Lesser General Public
9
 * License as published by the Free Software Foundation; either
10
 * version 2.1 of the License, or (at your option) any later version.
11
 *
12
 * This library is distributed in the hope that it will be useful,
13
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15
 * Lesser General Public License for more details.
16
 *
17
 * You should have received a copy of the GNU Lesser General Public
18
 * License along with this library; if not, write to the Free Software
19
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20
 *
21
 * @category	PHPExcel
22
 * @package		PHPExcel_Calculation
23
 * @copyright	Copyright (c) 2006 - 2012 PHPExcel (http://www.codeplex.com/PHPExcel)
24
 * @license		http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt	LGPL
25
 * @version		1.7.7, 2012-05-19
26
 */
27
28
29
/** PHPExcel root directory */
30 View Code Duplication
if (!defined('PHPEXCEL_ROOT')) {
31
	/**
32
	 * @ignore
33
	 */
34
	define('PHPEXCEL_ROOT', dirname(__FILE__) . '/../../');
35
	require(PHPEXCEL_ROOT . 'PHPExcel/Autoloader.php');
36
}
37
38
39
/** MAX_VALUE */
40
define('MAX_VALUE', 1.2e308);
41
42
/** 2 / PI */
43
define('M_2DIVPI', 0.63661977236758134307553505349006);
44
45
/** MAX_ITERATIONS */
46
define('MAX_ITERATIONS', 256);
47
48
/** PRECISION */
49
define('PRECISION', 8.88E-016);
50
51
52
/**
53
 * PHPExcel_Calculation_Functions
54
 *
55
 * @category	PHPExcel
56
 * @package		PHPExcel_Calculation
57
 * @copyright	Copyright (c) 2006 - 2012 PHPExcel (http://www.codeplex.com/PHPExcel)
58
 */
59
class PHPExcel_Calculation_Functions {
60
61
	/** constants */
62
	const COMPATIBILITY_EXCEL		= 'Excel';
63
	const COMPATIBILITY_GNUMERIC	= 'Gnumeric';
64
	const COMPATIBILITY_OPENOFFICE	= 'OpenOfficeCalc';
65
66
	const RETURNDATE_PHP_NUMERIC	= 'P';
67
	const RETURNDATE_PHP_OBJECT		= 'O';
68
	const RETURNDATE_EXCEL			= 'E';
69
70
71
	/**
72
	 * Compatibility mode to use for error checking and responses
73
	 *
74
	 * @access	private
75
	 * @var string
76
	 */
77
	protected static $compatibilityMode	= self::COMPATIBILITY_EXCEL;
78
79
	/**
80
	 * Data Type to use when returning date values
81
	 *
82
	 * @access	private
83
	 * @var string
84
	 */
85
	protected static $ReturnDateType	= self::RETURNDATE_EXCEL;
86
87
	/**
88
	 * List of error codes
89
	 *
90
	 * @access	private
91
	 * @var array
92
	 */
93
	protected static $_errorCodes	= array( 'null'				=> '#NULL!',
94
											 'divisionbyzero'	=> '#DIV/0!',
95
											 'value'			=> '#VALUE!',
96
											 'reference'		=> '#REF!',
97
											 'name'				=> '#NAME?',
98
											 'num'				=> '#NUM!',
99
											 'na'				=> '#N/A',
100
											 'gettingdata'		=> '#GETTING_DATA'
101
										   );
102
103
104
	/**
105
	 * Set the Compatibility Mode
106
	 *
107
	 * @access	public
108
	 * @category Function Configuration
109
	 * @param	 string		$compatibilityMode		Compatibility Mode
110
	 *												Permitted values are:
111
	 *													PHPExcel_Calculation_Functions::COMPATIBILITY_EXCEL			'Excel'
112
	 *													PHPExcel_Calculation_Functions::COMPATIBILITY_GNUMERIC		'Gnumeric'
113
	 *													PHPExcel_Calculation_Functions::COMPATIBILITY_OPENOFFICE	'OpenOfficeCalc'
114
	 * @return	 boolean	(Success or Failure)
115
	 */
116
	public static function setCompatibilityMode($compatibilityMode) {
117
		if (($compatibilityMode == self::COMPATIBILITY_EXCEL) ||
118
			($compatibilityMode == self::COMPATIBILITY_GNUMERIC) ||
119
			($compatibilityMode == self::COMPATIBILITY_OPENOFFICE)) {
120
			self::$compatibilityMode = $compatibilityMode;
121
			return True;
122
		}
123
		return False;
124
	}	//	function setCompatibilityMode()
125
126
127
	/**
128
	 * Return the current Compatibility Mode
129
	 *
130
	 * @access	public
131
	 * @category Function Configuration
132
	 * @return	 string		Compatibility Mode
133
	 *							Possible Return values are:
134
	 *								PHPExcel_Calculation_Functions::COMPATIBILITY_EXCEL			'Excel'
135
	 *								PHPExcel_Calculation_Functions::COMPATIBILITY_GNUMERIC		'Gnumeric'
136
	 *								PHPExcel_Calculation_Functions::COMPATIBILITY_OPENOFFICE	'OpenOfficeCalc'
137
	 */
138
	public static function getCompatibilityMode() {
139
		return self::$compatibilityMode;
140
	}	//	function getCompatibilityMode()
141
142
143
	/**
144
	 * Set the Return Date Format used by functions that return a date/time (Excel, PHP Serialized Numeric or PHP Object)
145
	 *
146
	 * @access	public
147
	 * @category Function Configuration
148
	 * @param	 string	$returnDateType			Return Date Format
149
	 *												Permitted values are:
150
	 *													PHPExcel_Calculation_Functions::RETURNDATE_PHP_NUMERIC		'P'
151
	 *													PHPExcel_Calculation_Functions::RETURNDATE_PHP_OBJECT		'O'
152
	 *													PHPExcel_Calculation_Functions::RETURNDATE_EXCEL			'E'
153
	 * @return	 boolean							Success or failure
154
	 */
155
	public static function setReturnDateType($returnDateType) {
156
		if (($returnDateType == self::RETURNDATE_PHP_NUMERIC) ||
157
			($returnDateType == self::RETURNDATE_PHP_OBJECT) ||
158
			($returnDateType == self::RETURNDATE_EXCEL)) {
159
			self::$ReturnDateType = $returnDateType;
160
			return True;
161
		}
162
		return False;
163
	}	//	function setReturnDateType()
164
165
166
	/**
167
	 * Return the current Return Date Format for functions that return a date/time (Excel, PHP Serialized Numeric or PHP Object)
168
	 *
169
	 * @access	public
170
	 * @category Function Configuration
171
	 * @return	 string		Return Date Format
172
	 *							Possible Return values are:
173
	 *								PHPExcel_Calculation_Functions::RETURNDATE_PHP_NUMERIC		'P'
174
	 *								PHPExcel_Calculation_Functions::RETURNDATE_PHP_OBJECT		'O'
175
	 *								PHPExcel_Calculation_Functions::RETURNDATE_EXCEL			'E'
176
	 */
177
	public static function getReturnDateType() {
178
		return self::$ReturnDateType;
179
	}	//	function getReturnDateType()
180
181
182
	/**
183
	 * DUMMY
184
	 *
185
	 * @access	public
186
	 * @category Error Returns
187
	 * @return	string	#Not Yet Implemented
188
	 */
189
	public static function DUMMY() {
190
		return '#Not Yet Implemented';
191
	}	//	function DUMMY()
192
193
194
	/**
195
	 * DIV0
196
	 *
197
	 * @access	public
198
	 * @category Error Returns
199
	 * @return	string	#Not Yet Implemented
200
	 */
201
	public static function DIV0() {
202
		return self::$_errorCodes['divisionbyzero'];
203
	}	//	function DIV0()
204
205
206
	/**
207
	 * NA
208
	 *
209
	 * Excel Function:
210
	 *		=NA()
211
	 *
212
	 * Returns the error value #N/A
213
	 *		#N/A is the error value that means "no value is available."
214
	 *
215
	 * @access	public
216
	 * @category Logical Functions
217
	 * @return	string	#N/A!
218
	 */
219
	public static function NA() {
220
		return self::$_errorCodes['na'];
221
	}	//	function NA()
222
223
224
	/**
225
	 * NaN
226
	 *
227
	 * Returns the error value #NUM!
228
	 *
229
	 * @access	public
230
	 * @category Error Returns
231
	 * @return	string	#NUM!
232
	 */
233
	public static function NaN() {
234
		return self::$_errorCodes['num'];
235
	}	//	function NaN()
236
237
238
	/**
239
	 * NAME
240
	 *
241
	 * Returns the error value #NAME?
242
	 *
243
	 * @access	public
244
	 * @category Error Returns
245
	 * @return	string	#NAME?
246
	 */
247
	public static function NAME() {
248
		return self::$_errorCodes['name'];
249
	}	//	function NAME()
250
251
252
	/**
253
	 * REF
254
	 *
255
	 * Returns the error value #REF!
256
	 *
257
	 * @access	public
258
	 * @category Error Returns
259
	 * @return	string	#REF!
260
	 */
261
	public static function REF() {
262
		return self::$_errorCodes['reference'];
263
	}	//	function REF()
264
265
266
	/**
267
	 * NULL
268
	 *
269
	 * Returns the error value #NULL!
270
	 *
271
	 * @access	public
272
	 * @category Error Returns
273
	 * @return	string	#REF!
274
	 */
275
	public static function NULL() {
276
		return self::$_errorCodes['null'];
277
	}	//	function NULL()
278
279
280
	/**
281
	 * VALUE
282
	 *
283
	 * Returns the error value #VALUE!
284
	 *
285
	 * @access	public
286
	 * @category Error Returns
287
	 * @return	string	#VALUE!
288
	 */
289
	public static function VALUE() {
290
		return self::$_errorCodes['value'];
291
	}	//	function VALUE()
292
293
294
	public static function isMatrixValue($idx) {
295
		return ((substr_count($idx,'.') <= 1) || (preg_match('/\.[A-Z]/',$idx) > 0));
296
	}
297
298
299
	public static function isValue($idx) {
300
		return (substr_count($idx,'.') == 0);
301
	}
302
303
304
	public static function isCellValue($idx) {
305
		return (substr_count($idx,'.') > 1);
306
	}
307
308
309
	public static function _ifCondition($condition) {
310
		$condition	= PHPExcel_Calculation_Functions::flattenSingleValue($condition);
311
		if (!in_array($condition{0},array('>', '<', '='))) {
312
			if (!is_numeric($condition)) { $condition = PHPExcel_Calculation::_wrapResult(strtoupper($condition)); }
313
			return '='.$condition;
314
		} else {
315
			preg_match('/([<>=]+)(.*)/',$condition,$matches);
316
			list(,$operator,$operand) = $matches;
317
			if (!is_numeric($operand)) { $operand = PHPExcel_Calculation::_wrapResult(strtoupper($operand)); }
318
			return $operator.$operand;
319
		}
320
	}	//	function _ifCondition()
321
322
323
	/**
324
	 * ERROR_TYPE
325
	 *
326
	 * @param	mixed	$value	Value to check
327
	 * @return	boolean
328
	 */
329
	public static function ERROR_TYPE($value = '') {
330
		$value	= self::flattenSingleValue($value);
331
332
		$i = 1;
333
		foreach(self::$_errorCodes as $errorCode) {
334
			if ($value === $errorCode) {
335
				return $i;
336
			}
337
			++$i;
338
		}
339
		return self::NA();
340
	}	//	function ERROR_TYPE()
341
342
343
	/**
344
	 * IS_BLANK
345
	 *
346
	 * @param	mixed	$value	Value to check
347
	 * @return	boolean
348
	 */
349
	public static function IS_BLANK($value = NULL) {
350
		if (!is_null($value)) {
351
			$value	= self::flattenSingleValue($value);
352
		}
353
354
		return is_null($value);
355
	}	//	function IS_BLANK()
356
357
358
	/**
359
	 * IS_ERR
360
	 *
361
	 * @param	mixed	$value	Value to check
362
	 * @return	boolean
363
	 */
364
	public static function IS_ERR($value = '') {
365
		$value		= self::flattenSingleValue($value);
366
367
		return self::IS_ERROR($value) && (!self::IS_NA($value));
368
	}	//	function IS_ERR()
369
370
371
	/**
372
	 * IS_ERROR
373
	 *
374
	 * @param	mixed	$value	Value to check
375
	 * @return	boolean
376
	 */
377
	public static function IS_ERROR($value = '') {
378
		$value		= self::flattenSingleValue($value);
379
380
		if (!is_string($value))
381
			return false;
382
		return in_array($value, array_values(self::$_errorCodes));
383
	}	//	function IS_ERROR()
384
385
386
	/**
387
	 * IS_NA
388
	 *
389
	 * @param	mixed	$value	Value to check
390
	 * @return	boolean
391
	 */
392
	public static function IS_NA($value = '') {
393
		$value		= self::flattenSingleValue($value);
394
395
		return ($value === self::NA());
396
	}	//	function IS_NA()
397
398
399
	/**
400
	 * IS_EVEN
401
	 *
402
	 * @param	mixed	$value	Value to check
403
	 * @return	boolean
404
	 */
405 View Code Duplication
	public static function IS_EVEN($value = NULL) {
406
		$value = self::flattenSingleValue($value);
407
408
		if ($value === NULL)
409
			return self::NAME();
410
		if ((is_bool($value)) || ((is_string($value)) && (!is_numeric($value))))
411
			return self::VALUE();
412
		return ($value % 2 == 0);
413
	}	//	function IS_EVEN()
414
415
416
	/**
417
	 * IS_ODD
418
	 *
419
	 * @param	mixed	$value	Value to check
420
	 * @return	boolean
421
	 */
422 View Code Duplication
	public static function IS_ODD($value = NULL) {
423
		$value = self::flattenSingleValue($value);
424
425
		if ($value === NULL)
426
			return self::NAME();
427
		if ((is_bool($value)) || ((is_string($value)) && (!is_numeric($value))))
428
			return self::VALUE();
429
		return (abs($value) % 2 == 1);
430
	}	//	function IS_ODD()
431
432
433
	/**
434
	 * IS_NUMBER
435
	 *
436
	 * @param	mixed	$value		Value to check
437
	 * @return	boolean
438
	 */
439
	public static function IS_NUMBER($value = NULL) {
440
		$value		= self::flattenSingleValue($value);
441
442
		if (is_string($value)) {
443
			return False;
444
		}
445
		return is_numeric($value);
446
	}	//	function IS_NUMBER()
447
448
449
	/**
450
	 * IS_LOGICAL
451
	 *
452
	 * @param	mixed	$value		Value to check
453
	 * @return	boolean
454
	 */
455
	public static function IS_LOGICAL($value = NULL) {
456
		$value		= self::flattenSingleValue($value);
457
458
		return is_bool($value);
459
	}	//	function IS_LOGICAL()
460
461
462
	/**
463
	 * IS_TEXT
464
	 *
465
	 * @param	mixed	$value		Value to check
466
	 * @return	boolean
467
	 */
468
	public static function IS_TEXT($value = NULL) {
469
		$value		= self::flattenSingleValue($value);
470
471
		return (is_string($value) && !self::IS_ERROR($value));
472
	}	//	function IS_TEXT()
473
474
475
	/**
476
	 * IS_NONTEXT
477
	 *
478
	 * @param	mixed	$value		Value to check
479
	 * @return	boolean
480
	 */
481
	public static function IS_NONTEXT($value = NULL) {
482
		return !self::IS_TEXT($value);
483
	}	//	function IS_NONTEXT()
484
485
486
	/**
487
	 * VERSION
488
	 *
489
	 * @return	string	Version information
490
	 */
491
	public static function VERSION() {
492
		return 'PHPExcel 1.7.7, 2012-05-19';
493
	}	//	function VERSION()
494
495
496
	/**
497
	 * N
498
	 *
499
	 * Returns a value converted to a number
500
	 *
501
	 * @param	value		The value you want converted
502
	 * @return	number		N converts values listed in the following table
503
	 *		If value is or refers to N returns
504
	 *		A number			That number
505
	 *		A date				The serial number of that date
506
	 *		TRUE				1
507
	 *		FALSE				0
508
	 *		An error value		The error value
509
	 *		Anything else		0
510
	 */
511
	public static function N($value = NULL) {
512
		while (is_array($value)) {
513
			$value = array_shift($value);
514
		}
515
516
		switch (gettype($value)) {
517
			case 'double'	:
518
			case 'float'	:
519
			case 'integer'	:
520
				return $value;
521
				break;
0 ignored issues
show
Unused Code introduced by
break is not strictly necessary here and could be removed.

The break statement is not necessary if it is preceded for example by a return statement:

switch ($x) {
    case 1:
        return 'foo';
        break; // This break is not necessary and can be left off.
}

If you would like to keep this construct to be consistent with other case statements, you can safely mark this issue as a false-positive.

Loading history...
522
			case 'boolean'	:
523
				return (integer) $value;
524
				break;
0 ignored issues
show
Unused Code introduced by
break is not strictly necessary here and could be removed.

The break statement is not necessary if it is preceded for example by a return statement:

switch ($x) {
    case 1:
        return 'foo';
        break; // This break is not necessary and can be left off.
}

If you would like to keep this construct to be consistent with other case statements, you can safely mark this issue as a false-positive.

Loading history...
525
			case 'string'	:
526
				//	Errors
527
				if ((strlen($value) > 0) && ($value{0} == '#')) {
528
					return $value;
529
				}
530
				break;
531
		}
532
		return 0;
533
	}	//	function N()
534
535
536
	/**
537
	 * TYPE
538
	 *
539
	 * Returns a number that identifies the type of a value
540
	 *
541
	 * @param	value		The value you want tested
542
	 * @return	number		N converts values listed in the following table
543
	 *		If value is or refers to N returns
544
	 *		A number			1
545
	 *		Text				2
546
	 *		Logical Value		4
547
	 *		An error value		16
548
	 *		Array or Matrix		64
549
	 */
550
	public static function TYPE($value = NULL) {
551
		$value	= self::flattenArrayIndexed($value);
0 ignored issues
show
Bug introduced by
It seems like $value can also be of type null; however, PHPExcel_Calculation_Fun...::flattenArrayIndexed() does only seem to accept array, maybe add an additional type check?

If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:

/**
 * @return array|string
 */
function returnsDifferentValues($x) {
    if ($x) {
        return 'foo';
    }

    return array();
}

$x = returnsDifferentValues($y);
if (is_array($x)) {
    // $x is an array.
}

If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.

Loading history...
552
		if (is_array($value) && (count($value) > 1)) {
553
			$a = array_keys($value);
554
			$a = array_pop($a);
555
			//	Range of cells is an error
556
			if (self::isCellValue($a)) {
557
				return 16;
558
			//	Test for Matrix
559
			} elseif (self::isMatrixValue($a)) {
560
				return 64;
561
			}
562
		} elseif(empty($value)) {
563
			//	Empty Cell
564
			return 1;
565
		}
566
		$value	= self::flattenSingleValue($value);
567
568
		if (($value === NULL) || (is_float($value)) || (is_int($value))) {
569
				return 1;
570
		} elseif(is_bool($value)) {
571
				return 4;
572
		} elseif(is_array($value)) {
573
				return 64;
574
				break;
575
		} elseif(is_string($value)) {
576
			//	Errors
577
			if ((strlen($value) > 0) && ($value{0} == '#')) {
578
				return 16;
579
			}
580
			return 2;
581
		}
582
		return 0;
583
	}	//	function TYPE()
584
585
586
	/**
587
	 * Convert a multi-dimensional array to a simple 1-dimensional array
588
	 *
589
	 * @param	array	$array	Array to be flattened
590
	 * @return	array	Flattened array
591
	 */
592
	public static function flattenArray($array) {
593
		if (!is_array($array)) {
594
			return (array) $array;
595
		}
596
597
		$arrayValues = array();
598
		foreach ($array as $value) {
599
			if (is_array($value)) {
600
				foreach ($value as $val) {
601
					if (is_array($val)) {
602
						foreach ($val as $v) {
603
							$arrayValues[] = $v;
604
						}
605
					} else {
606
						$arrayValues[] = $val;
607
					}
608
				}
609
			} else {
610
				$arrayValues[] = $value;
611
			}
612
		}
613
614
		return $arrayValues;
615
	}	//	function flattenArray()
616
617
618
	/**
619
	 * Convert a multi-dimensional array to a simple 1-dimensional array, but retain an element of indexing
620
	 *
621
	 * @param	array	$array	Array to be flattened
622
	 * @return	array	Flattened array
623
	 */
624
	public static function flattenArrayIndexed($array) {
625
		if (!is_array($array)) {
626
			return (array) $array;
627
		}
628
629
		$arrayValues = array();
630
		foreach ($array as $k1 => $value) {
631
			if (is_array($value)) {
632
				foreach ($value as $k2 => $val) {
633
					if (is_array($val)) {
634
						foreach ($val as $k3 => $v) {
635
							$arrayValues[$k1.'.'.$k2.'.'.$k3] = $v;
636
						}
637
					} else {
638
						$arrayValues[$k1.'.'.$k2] = $val;
639
					}
640
				}
641
			} else {
642
				$arrayValues[$k1] = $value;
643
			}
644
		}
645
646
		return $arrayValues;
647
	}	//	function flattenArrayIndexed()
648
649
650
	/**
651
	 * Convert an array to a single scalar value by extracting the first element
652
	 *
653
	 * @param	mixed		$value		Array or scalar value
654
	 * @return	mixed
655
	 */
656
	public static function flattenSingleValue($value = '') {
657
		while (is_array($value)) {
658
			$value = array_pop($value);
659
		}
660
661
		return $value;
662
	}	//	function flattenSingleValue()
663
664
}	//	class PHPExcel_Calculation_Functions
665
666
667
//
668
//	There are a few mathematical functions that aren't available on all versions of PHP for all platforms
669
//	These functions aren't available in Windows implementations of PHP prior to version 5.3.0
670
//	So we test if they do exist for this version of PHP/operating platform; and if not we create them
671
//
672
if (!function_exists('acosh')) {
673
	function acosh($x) {
674
		return 2 * log(sqrt(($x + 1) / 2) + sqrt(($x - 1) / 2));
675
	}	//	function acosh()
676
}
677
678
if (!function_exists('asinh')) {
679
	function asinh($x) {
680
		return log($x + sqrt(1 + $x * $x));
681
	}	//	function asinh()
682
}
683
684
if (!function_exists('atanh')) {
685
	function atanh($x) {
686
		return (log(1 + $x) - log(1 - $x)) / 2;
687
	}	//	function atanh()
688
}
689
690
if (!function_exists('money_format')) {
691
	function money_format($format, $number) {
692
		$regex = array( '/%((?:[\^!\-]|\+|\(|\=.)*)([0-9]+)?(?:#([0-9]+))?',
693
						 '(?:\.([0-9]+))?([in%])/'
694
					  );
695
		$regex = implode('', $regex);
696
		if (setlocale(LC_MONETARY, null) == '') {
697
			setlocale(LC_MONETARY, '');
698
		}
699
		$locale = localeconv();
700
		$number = floatval($number);
701
		if (!preg_match($regex, $format, $fmatch)) {
702
			trigger_error("No format specified or invalid format", E_USER_WARNING);
703
			return $number;
704
		}
705
		$flags = array( 'fillchar'	=> preg_match('/\=(.)/', $fmatch[1], $match) ? $match[1] : ' ',
706
						'nogroup'	=> preg_match('/\^/', $fmatch[1]) > 0,
707
						'usesignal'	=> preg_match('/\+|\(/', $fmatch[1], $match) ? $match[0] : '+',
708
						'nosimbol'	=> preg_match('/\!/', $fmatch[1]) > 0,
709
						'isleft'	=> preg_match('/\-/', $fmatch[1]) > 0
710
					  );
711
		$width	= trim($fmatch[2]) ? (int)$fmatch[2] : 0;
712
		$left	= trim($fmatch[3]) ? (int)$fmatch[3] : 0;
713
		$right	= trim($fmatch[4]) ? (int)$fmatch[4] : $locale['int_frac_digits'];
714
		$conversion = $fmatch[5];
715
		$positive = true;
716
		if ($number < 0) {
717
			$positive = false;
718
			$number *= -1;
719
		}
720
		$letter = $positive ? 'p' : 'n';
721
		$prefix = $suffix = $cprefix = $csuffix = $signal = '';
722
		if (!$positive) {
723
			$signal = $locale['negative_sign'];
724
			switch (true) {
725
				case $locale['n_sign_posn'] == 0 || $flags['usesignal'] == '(':
726
					$prefix = '(';
727
					$suffix = ')';
728
					break;
729
				case $locale['n_sign_posn'] == 1:
730
					$prefix = $signal;
731
					break;
732
				case $locale['n_sign_posn'] == 2:
733
					$suffix = $signal;
734
					break;
735
				case $locale['n_sign_posn'] == 3:
736
					$cprefix = $signal;
737
					break;
738
				case $locale['n_sign_posn'] == 4:
739
					$csuffix = $signal;
740
					break;
741
			}
742
		}
743
		if (!$flags['nosimbol']) {
744
			$currency = $cprefix;
745
			$currency .= ($conversion == 'i' ? $locale['int_curr_symbol'] : $locale['currency_symbol']);
746
			$currency .= $csuffix;
747
			$currency = iconv('ISO-8859-1','UTF-8',$currency);
748
		} else {
749
			$currency = '';
750
		}
751
		$space = $locale["{$letter}_sep_by_space"] ? ' ' : '';
752
753
		if (!isset($locale['mon_decimal_point']) || empty($locale['mon_decimal_point'])) {
754
			$locale['mon_decimal_point'] = (!isset($locale['decimal_point']) || empty($locale['decimal_point'])) ?
755
											$locale['decimal_point'] :
756
											'.';
757
		}
758
759
		$number = number_format($number, $right, $locale['mon_decimal_point'], $flags['nogroup'] ? '' : $locale['mon_thousands_sep'] );
760
		$number = explode($locale['mon_decimal_point'], $number);
761
762
		$n = strlen($prefix) + strlen($currency);
763
		if ($left > 0 && $left > $n) {
764
			if ($flags['isleft']) {
765
				$number[0] .= str_repeat($flags['fillchar'], $left - $n);
766
			} else {
767
				$number[0] = str_repeat($flags['fillchar'], $left - $n) . $number[0];
768
			}
769
		}
770
		$number = implode($locale['mon_decimal_point'], $number);
771
		if ($locale["{$letter}_cs_precedes"]) {
772
			$number = $prefix . $currency . $space . $number . $suffix;
773
		} else {
774
			$number = $prefix . $number . $space . $currency . $suffix;
775
		}
776
		if ($width > 0) {
777
			$number = str_pad($number, $width, $flags['fillchar'], $flags['isleft'] ? STR_PAD_RIGHT : STR_PAD_LEFT);
778
		}
779
		$format = str_replace($fmatch[0], $number, $format);
780
		return $format;
781
	}	//	function money_format()
782
}
783
784
785
//
786
//	Strangely, PHP doesn't have a mb_str_replace multibyte function
787
//	As we'll only ever use this function with UTF-8 characters, we can simply "hard-code" the character set
788
//
789
if ((!function_exists('mb_str_replace')) &&
790
	(function_exists('mb_substr')) && (function_exists('mb_strlen')) && (function_exists('mb_strpos'))) {
791
	function mb_str_replace($search, $replace, $subject) {
792
		if(is_array($subject)) {
793
			$ret = array();
794
			foreach($subject as $key => $val) {
795
				$ret[$key] = mb_str_replace($search, $replace, $val);
796
			}
797
			return $ret;
798
		}
799
800
		foreach((array) $search as $key => $s) {
801
			if($s == '') {
802
				continue;
803
			}
804
			$r = !is_array($replace) ? $replace : (array_key_exists($key, $replace) ? $replace[$key] : '');
805
			$pos = mb_strpos($subject, $s, 0, 'UTF-8');
806
			while($pos !== false) {
807
				$subject = mb_substr($subject, 0, $pos, 'UTF-8') . $r . mb_substr($subject, $pos + mb_strlen($s, 'UTF-8'), 65535, 'UTF-8');
808
				$pos = mb_strpos($subject, $s, $pos + mb_strlen($r, 'UTF-8'), 'UTF-8');
809
			}
810
		}
811
		return $subject;
812
	}
813
}
814