Quantity   A
last analyzed

Complexity

Total Complexity 6

Size/Duplication

Total Lines 34
Duplicated Lines 0 %

Coupling/Cohesion

Components 0
Dependencies 2

Importance

Changes 3
Bugs 0 Features 1
Metric Value
wmc 6
c 3
b 0
f 1
lcom 0
cbo 2
dl 0
loc 34
rs 10

1 Method

Rating   Name   Duplication   Size   Complexity  
B format() 0 22 6
1
<?php
2
namespace nochso\Omni\Format;
3
4
use nochso\Omni\Dot;
5
use nochso\Omni\Numeric;
6
7
/**
8
 * Quantity formats a string depending on quantity (many, one or zero).
9
 *
10
 * The plural, singular and empty formats of the string can be defined like this:
11
 *
12
 * `(plural|singular|zero)`
13
 *
14
 * The singular and zero formats are optional:
15
 *
16
 * ```php
17
 * Quantity::format('day(s)', 1); // day
18
 * Quantity::format('day(s)', 0); // days
19
 * ```
20
 *
21
 * You can also use `%s` as a placeholder for the quantity:
22
 *
23
 * ```php
24
 * Quantity::format('%s day(s)', 2); // 2 days
25
 * ```
26
 *
27
 * If the `zero` format is not defined, the plural form will be used instead.
28
 * Alternatively you can use an empty string:
29
 *
30
 * ```php
31
 * Quantity::format('(many|one|)', 0); // empty string
32
 * ```
33
 *
34
 * Example with all three formats:
35
 *
36
 * ```php
37
 * Quantity::format('(bugs|bug|no bugs at all)', 5) // bugs
38
 * Quantity::format('(bugs|bug|no bugs at all)', 1) // bug
39
 * Quantity::format('(bugs|bug|no bugs at all)', 0) // no bugs at all
40
 * ```
41
 */
42
class Quantity {
43
	/**
44
	 * Format a string depending on a quantity.
45
	 *
46
	 * See the class documentation for defining `$format`.
47
	 *
48
	 * @param string $format
49
	 * @param string $quantity
50
	 *
51
	 * @return mixed
52
	 */
53
	public static function format($format, $quantity) {
54
		$quantity = Numeric::ensure($quantity);
55
		$callback = function ($matches) use ($quantity) {
56
			// Get available choices
57
			$choices = preg_split('/\|/', $matches[2]);
58
			// Assume plural
59
			$choice = 0;
60
			// Choose singular
61
			if ($quantity === 1.0 || $quantity === 1) {
62
				$choice = 1;
63
			}
64
			// Choose zero if it's defined, otherwise keep using plural format
65
			if (($quantity === 0 || $quantity === 0.0) && isset($choices[2])) {
66
				$choice = 2;
67
			}
68
			return Dot::get($choices, $choice, '');
69
		};
70
		$pattern = '/(?<!\\\\)(\\((.+?(?<!\\\\))\\))/';
71
		$out = preg_replace_callback($pattern, $callback, $format);
72
		$out = sprintf($out, $quantity);
73
		return $out;
74
	}
75
}
76