woocommerce-pos
/
vendor_prefixed
/
chillerlan
/
php-qrcode
/
src
/
Detector
/
PerspectiveTransform.php
PerspectiveTransform.php in WCPOS – Point of Sale (POS) plugin for WooCommerce 1.10.18, at vendor_prefixed/chillerlan/php-qrcode/src/Detector/PerspectiveTransform.php
| 1 | <?php |
| 2 | |
| 3 | /** |
| 4 | * Class PerspectiveTransform |
| 5 | * |
| 6 | * @created 17.01.2021 |
| 7 | * @author ZXing Authors |
| 8 | * @author Smiley <[email protected]> |
| 9 | * @copyright 2021 Smiley |
| 10 | * @license Apache-2.0 |
| 11 | */ |
| 12 | namespace WCPOS\Vendor\chillerlan\QRCode\Detector; |
| 13 | |
| 14 | use function count; |
| 15 | /** |
| 16 | * This class implements a perspective transform in two dimensions. Given four source and four |
| 17 | * destination points, it will compute the transformation implied between them. The code is based |
| 18 | * directly upon section 3.4.2 of George Wolberg's "Digital Image Warping"; see pages 54-56. |
| 19 | * |
| 20 | * @author Sean Owen |
| 21 | */ |
| 22 | final class PerspectiveTransform |
| 23 | { |
| 24 | private float $a11; |
| 25 | private float $a12; |
| 26 | private float $a13; |
| 27 | private float $a21; |
| 28 | private float $a22; |
| 29 | private float $a23; |
| 30 | private float $a31; |
| 31 | private float $a32; |
| 32 | private float $a33; |
| 33 | /** |
| 34 | * |
| 35 | */ |
| 36 | private function set(float $a11, float $a21, float $a31, float $a12, float $a22, float $a32, float $a13, float $a23, float $a33) : self |
| 37 | { |
| 38 | $this->a11 = $a11; |
| 39 | $this->a12 = $a12; |
| 40 | $this->a13 = $a13; |
| 41 | $this->a21 = $a21; |
| 42 | $this->a22 = $a22; |
| 43 | $this->a23 = $a23; |
| 44 | $this->a31 = $a31; |
| 45 | $this->a32 = $a32; |
| 46 | $this->a33 = $a33; |
| 47 | return $this; |
| 48 | } |
| 49 | /** |
| 50 | * @SuppressWarnings(PHPMD.ExcessiveParameterList) |
| 51 | */ |
| 52 | public function quadrilateralToQuadrilateral(float $x0, float $y0, float $x1, float $y1, float $x2, float $y2, float $x3, float $y3, float $x0p, float $y0p, float $x1p, float $y1p, float $x2p, float $y2p, float $x3p, float $y3p) : self |
| 53 | { |
| 54 | return (new self())->squareToQuadrilateral($x0p, $y0p, $x1p, $y1p, $x2p, $y2p, $x3p, $y3p)->times($this->quadrilateralToSquare($x0, $y0, $x1, $y1, $x2, $y2, $x3, $y3)); |
| 55 | } |
| 56 | /** |
| 57 | * |
| 58 | */ |
| 59 | private function quadrilateralToSquare(float $x0, float $y0, float $x1, float $y1, float $x2, float $y2, float $x3, float $y3) : self |
| 60 | { |
| 61 | // Here, the adjoint serves as the inverse: |
| 62 | return $this->squareToQuadrilateral($x0, $y0, $x1, $y1, $x2, $y2, $x3, $y3)->buildAdjoint(); |
| 63 | } |
| 64 | /** |
| 65 | * |
| 66 | */ |
| 67 | private function buildAdjoint() : self |
| 68 | { |
| 69 | // Adjoint is the transpose of the cofactor matrix: |
| 70 | return $this->set($this->a22 * $this->a33 - $this->a23 * $this->a32, $this->a23 * $this->a31 - $this->a21 * $this->a33, $this->a21 * $this->a32 - $this->a22 * $this->a31, $this->a13 * $this->a32 - $this->a12 * $this->a33, $this->a11 * $this->a33 - $this->a13 * $this->a31, $this->a12 * $this->a31 - $this->a11 * $this->a32, $this->a12 * $this->a23 - $this->a13 * $this->a22, $this->a13 * $this->a21 - $this->a11 * $this->a23, $this->a11 * $this->a22 - $this->a12 * $this->a21); |
| 71 | } |
| 72 | /** |
| 73 | * |
| 74 | */ |
| 75 | private function squareToQuadrilateral(float $x0, float $y0, float $x1, float $y1, float $x2, float $y2, float $x3, float $y3) : self |
| 76 | { |
| 77 | $dx3 = $x0 - $x1 + $x2 - $x3; |
| 78 | $dy3 = $y0 - $y1 + $y2 - $y3; |
| 79 | if ($dx3 === 0.0 && $dy3 === 0.0) { |
| 80 | // Affine |
| 81 | return $this->set($x1 - $x0, $x2 - $x1, $x0, $y1 - $y0, $y2 - $y1, $y0, 0.0, 0.0, 1.0); |
| 82 | } |
| 83 | $dx1 = $x1 - $x2; |
| 84 | $dx2 = $x3 - $x2; |
| 85 | $dy1 = $y1 - $y2; |
| 86 | $dy2 = $y3 - $y2; |
| 87 | $denominator = $dx1 * $dy2 - $dx2 * $dy1; |
| 88 | $a13 = ($dx3 * $dy2 - $dx2 * $dy3) / $denominator; |
| 89 | $a23 = ($dx1 * $dy3 - $dx3 * $dy1) / $denominator; |
| 90 | return $this->set($x1 - $x0 + $a13 * $x1, $x3 - $x0 + $a23 * $x3, $x0, $y1 - $y0 + $a13 * $y1, $y3 - $y0 + $a23 * $y3, $y0, $a13, $a23, 1.0); |
| 91 | } |
| 92 | /** |
| 93 | * |
| 94 | */ |
| 95 | private function times(PerspectiveTransform $other) : self |
| 96 | { |
| 97 | return $this->set($this->a11 * $other->a11 + $this->a21 * $other->a12 + $this->a31 * $other->a13, $this->a11 * $other->a21 + $this->a21 * $other->a22 + $this->a31 * $other->a23, $this->a11 * $other->a31 + $this->a21 * $other->a32 + $this->a31 * $other->a33, $this->a12 * $other->a11 + $this->a22 * $other->a12 + $this->a32 * $other->a13, $this->a12 * $other->a21 + $this->a22 * $other->a22 + $this->a32 * $other->a23, $this->a12 * $other->a31 + $this->a22 * $other->a32 + $this->a32 * $other->a33, $this->a13 * $other->a11 + $this->a23 * $other->a12 + $this->a33 * $other->a13, $this->a13 * $other->a21 + $this->a23 * $other->a22 + $this->a33 * $other->a23, $this->a13 * $other->a31 + $this->a23 * $other->a32 + $this->a33 * $other->a33); |
| 98 | } |
| 99 | /** |
| 100 | * @return array[] [$xValues, $yValues] |
| 101 | */ |
| 102 | public function transformPoints(array $xValues, ?array $yValues = null) : array |
| 103 | { |
| 104 | $max = count($xValues); |
| 105 | if ($yValues !== null) { |
| 106 | // unused |
| 107 | for ($i = 0; $i < $max; $i++) { |
| 108 | $x = $xValues[$i]; |
| 109 | $y = $yValues[$i]; |
| 110 | $denominator = $this->a13 * $x + $this->a23 * $y + $this->a33; |
| 111 | $xValues[$i] = ($this->a11 * $x + $this->a21 * $y + $this->a31) / $denominator; |
| 112 | $yValues[$i] = ($this->a12 * $x + $this->a22 * $y + $this->a32) / $denominator; |
| 113 | } |
| 114 | return [$xValues, $yValues]; |
| 115 | } |
| 116 | for ($i = 0; $i < $max; $i += 2) { |
| 117 | $x = $xValues[$i]; |
| 118 | $y = $xValues[$i + 1]; |
| 119 | $denominator = $this->a13 * $x + $this->a23 * $y + $this->a33; |
| 120 | $xValues[$i] = ($this->a11 * $x + $this->a21 * $y + $this->a31) / $denominator; |
| 121 | $xValues[$i + 1] = ($this->a12 * $x + $this->a22 * $y + $this->a32) / $denominator; |
| 122 | } |
| 123 | return [$xValues, []]; |
| 124 | } |
| 125 | } |
| 126 |