mirror of
https://github.com/chillerlan/php-qrcode.git
synced 2026-10-27 22:26:38 +00:00
✨ docblocks galore!
This commit is contained in:
@@ -18,6 +18,9 @@ use function ord, sprintf;
|
||||
|
||||
/**
|
||||
* Alphanumeric mode: 0 to 9, A to Z, space, $ % * + - . / :
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 8.3.3
|
||||
* ISO/IEC 18004:2000 Section 8.4.3
|
||||
*/
|
||||
final class AlphaNum extends QRDataAbstract{
|
||||
|
||||
@@ -41,7 +44,9 @@ final class AlphaNum extends QRDataAbstract{
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws \chillerlan\QRCode\Data\QRCodeDataException
|
||||
* get the code for the given character
|
||||
*
|
||||
* @throws \chillerlan\QRCode\Data\QRCodeDataException on an illegal character occurence
|
||||
*/
|
||||
protected function getCharCode(string $chr):int{
|
||||
|
||||
|
||||
@@ -18,6 +18,9 @@ use function ord;
|
||||
|
||||
/**
|
||||
* Byte mode, ISO-8859-1 or UTF-8
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 8.3.4
|
||||
* ISO/IEC 18004:2000 Section 8.4.4
|
||||
*/
|
||||
final class Byte extends QRDataAbstract{
|
||||
|
||||
|
||||
@@ -18,6 +18,9 @@ use function mb_strlen, ord, sprintf, strlen;
|
||||
|
||||
/**
|
||||
* Kanji mode: double-byte characters from the Shift JIS character set
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 8.3.5
|
||||
* ISO/IEC 18004:2000 Section 8.4.5
|
||||
*/
|
||||
final class Kanji extends QRDataAbstract{
|
||||
|
||||
@@ -34,6 +37,8 @@ final class Kanji extends QRDataAbstract{
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*
|
||||
* @throws \chillerlan\QRCode\Data\QRCodeDataException on an illegal character occurence
|
||||
*/
|
||||
protected function write(string $data):void{
|
||||
$len = strlen($data);
|
||||
|
||||
@@ -17,12 +17,15 @@ use function abs, array_search, call_user_func_array, min;
|
||||
/**
|
||||
* Receives a QRDataInterface object and runs the mask pattern tests on it.
|
||||
*
|
||||
* @link http://www.thonky.com/qr-code-tutorial/data-masking
|
||||
* ISO/IEC 18004:2000 Section 8.8.2 - Evaluation of masking results
|
||||
*
|
||||
* @see http://www.thonky.com/qr-code-tutorial/data-masking
|
||||
*/
|
||||
final class MaskPatternTester{
|
||||
|
||||
protected QRMatrix $matrix;
|
||||
|
||||
/**
|
||||
* The data interface that contains the data matrix to test
|
||||
*/
|
||||
protected QRDataInterface $dataInterface;
|
||||
|
||||
/**
|
||||
@@ -153,7 +156,7 @@ final class MaskPatternTester{
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if there are patterns that look similar to the finder patterns
|
||||
* Checks if there are patterns that look similar to the finder patterns (1:1:3:1:1 ratio)
|
||||
*/
|
||||
protected function testLevel3(QRMatrix $m, int $size):float{
|
||||
$penalty = 0;
|
||||
|
||||
+9
-4
@@ -4,7 +4,7 @@
|
||||
*
|
||||
* @filesource Number.php
|
||||
* @created 26.11.2015
|
||||
* @package QRCode
|
||||
* @package chillerlan\QRCode\Data
|
||||
* @author Smiley <smiley@chillerlan.net>
|
||||
* @copyright 2015 Smiley
|
||||
* @license MIT
|
||||
@@ -17,7 +17,10 @@ use chillerlan\QRCode\QRCode;
|
||||
use function ord, sprintf, substr;
|
||||
|
||||
/**
|
||||
* Numeric mode: decimal digits 0 through 9
|
||||
* Numeric mode: decimal digits 0 to 9
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 8.3.2
|
||||
* ISO/IEC 18004:2000 Section 8.4.2
|
||||
*/
|
||||
final class Number extends QRDataAbstract{
|
||||
|
||||
@@ -50,12 +53,14 @@ final class Number extends QRDataAbstract{
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws \chillerlan\QRCode\Data\QRCodeDataException
|
||||
* get the code for the given numeric string
|
||||
*
|
||||
* @throws \chillerlan\QRCode\Data\QRCodeDataException on an illegal character occurence
|
||||
*/
|
||||
protected function parseInt(string $string):int{
|
||||
$num = 0;
|
||||
|
||||
$len = strlen($string);
|
||||
|
||||
for($i = 0; $i < $len; $i++){
|
||||
$c = ord($string[$i]);
|
||||
|
||||
|
||||
@@ -35,6 +35,8 @@ abstract class QRDataAbstract implements QRDataInterface{
|
||||
|
||||
/**
|
||||
* mode length bits for the version breakpoints 1-9, 10-26 and 27-40
|
||||
*
|
||||
* ISO/IEC 18004:2000 Table 3 - Number of bits in Character Count Indicator
|
||||
*/
|
||||
protected array $lengthBits = [0, 0, 0];
|
||||
|
||||
@@ -166,7 +168,7 @@ abstract class QRDataAbstract implements QRDataInterface{
|
||||
/**
|
||||
* creates a BitBuffer and writes the string data to it
|
||||
*
|
||||
* @throws \chillerlan\QRCode\QRCodeException
|
||||
* @throws \chillerlan\QRCode\QRCodeException on data overflow
|
||||
*/
|
||||
protected function writeBitBuffer(string $data):void{
|
||||
$this->bitBuffer = new BitBuffer;
|
||||
@@ -186,7 +188,7 @@ abstract class QRDataAbstract implements QRDataInterface{
|
||||
throw new QRCodeDataException(sprintf('code length overflow. (%d > %d bit)', $this->bitBuffer->getLength(), $MAX_BITS));
|
||||
}
|
||||
|
||||
// end code.
|
||||
// add terminator (ISO/IEC 18004:2000 Table 2)
|
||||
if($this->bitBuffer->getLength() + 4 <= $MAX_BITS){
|
||||
$this->bitBuffer->put(0, 4);
|
||||
}
|
||||
@@ -217,7 +219,9 @@ abstract class QRDataAbstract implements QRDataInterface{
|
||||
/**
|
||||
* ECC masking
|
||||
*
|
||||
* @link http://www.thonky.com/qr-code-tutorial/error-correction-coding
|
||||
* ISO/IEC 18004:2000 Section 8.5 ff
|
||||
*
|
||||
* @see http://www.thonky.com/qr-code-tutorial/error-correction-coding
|
||||
*/
|
||||
protected function maskECC():array{
|
||||
[$l1, $l2, $b1, $b2] = $this::RSBLOCKS[$this->version][QRCode::ECC_MODES[$this->options->eccLevel]];
|
||||
@@ -282,7 +286,7 @@ abstract class QRDataAbstract implements QRDataInterface{
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* helper method for the polynomial operations
|
||||
*/
|
||||
protected function poly(int $key, int $count):array{
|
||||
$rsPoly = new Polynomial;
|
||||
|
||||
@@ -13,16 +13,22 @@
|
||||
namespace chillerlan\QRCode\Data;
|
||||
|
||||
/**
|
||||
*
|
||||
* Specifies the methods reqired for the data modules (Number, Alphanum, Byte and Kanji)
|
||||
* and holds version information in several constants
|
||||
*/
|
||||
interface QRDataInterface{
|
||||
|
||||
/**
|
||||
* @var int[]
|
||||
*/
|
||||
const CHAR_MAP_NUMBER = [
|
||||
'0' => 0, '1' => 1, '2' => 2, '3' => 3, '4' => 4, '5' => 5, '6' => 6, '7' => 7, '8' => 8, '9' => 9,
|
||||
];
|
||||
|
||||
/**
|
||||
* ISO/IEC 18004:2000 Table 5
|
||||
*
|
||||
* @var int[]
|
||||
*/
|
||||
const CHAR_MAP_ALPHANUM = [
|
||||
'0' => 0, '1' => 1, '2' => 2, '3' => 3, '4' => 4, '5' => 5, '6' => 6, '7' => 7,
|
||||
@@ -34,7 +40,11 @@ interface QRDataInterface{
|
||||
];
|
||||
|
||||
/**
|
||||
* @link http://www.qrcode.com/en/about/version.html
|
||||
* ISO/IEC 18004:2000 Tables 7-11 - Number of symbol characters and input data capacity for versions 1 to 40
|
||||
*
|
||||
* @see http://www.qrcode.com/en/about/version.html
|
||||
*
|
||||
* @var int [][][]
|
||||
*/
|
||||
const MAX_LENGTH =[
|
||||
// v => [NUMERIC => [L, M, Q, H ], ALPHANUM => [L, M, Q, H], BINARY => [L, M, Q, H ], KANJI => [L, M, Q, H ]] // modules
|
||||
@@ -80,6 +90,11 @@ interface QRDataInterface{
|
||||
40 => [[7089, 5596, 3993, 3057], [4296, 3391, 2420, 1852], [2953, 2331, 1663, 1273], [1817, 1435, 1024, 784]], // 177
|
||||
];
|
||||
|
||||
/**
|
||||
* ISO/IEC 18004:2000 Tables 7-11 - Number of symbol characters and input data capacity for versions 1 to 40
|
||||
*
|
||||
* @var int [][]
|
||||
*/
|
||||
const MAX_BITS = [
|
||||
// version => [L, M, Q, H ]
|
||||
1 => [ 152, 128, 104, 72],
|
||||
@@ -125,7 +140,9 @@ interface QRDataInterface{
|
||||
];
|
||||
|
||||
/**
|
||||
* @link http://www.thonky.com/qr-code-tutorial/error-correction-table
|
||||
* @see http://www.thonky.com/qr-code-tutorial/error-correction-table
|
||||
*
|
||||
* @var int [][][]
|
||||
*/
|
||||
const RSBLOCKS = [
|
||||
1 => [[ 1, 0, 26, 19], [ 1, 0, 26, 16], [ 1, 0, 26, 13], [ 1, 0, 26, 9]],
|
||||
|
||||
+69
-10
@@ -18,28 +18,44 @@ use Closure;
|
||||
use function array_fill, array_key_exists, array_push, array_unshift, count, floor, in_array, max, min, range;
|
||||
|
||||
/**
|
||||
* @link http://www.thonky.com/qr-code-tutorial/format-version-information
|
||||
* Holds a numerical representation of the final QR Code;
|
||||
* maps the ECC coded binary data and applies the mask pattern
|
||||
*
|
||||
* @see http://www.thonky.com/qr-code-tutorial/format-version-information
|
||||
*/
|
||||
final class QRMatrix{
|
||||
|
||||
/** @var int */
|
||||
public const M_NULL = 0x00;
|
||||
/** @var int */
|
||||
public const M_DARKMODULE = 0x02;
|
||||
/** @var int */
|
||||
public const M_DATA = 0x04;
|
||||
/** @var int */
|
||||
public const M_FINDER = 0x06;
|
||||
/** @var int */
|
||||
public const M_SEPARATOR = 0x08;
|
||||
/** @var int */
|
||||
public const M_ALIGNMENT = 0x0a;
|
||||
/** @var int */
|
||||
public const M_TIMING = 0x0c;
|
||||
/** @var int */
|
||||
public const M_FORMAT = 0x0e;
|
||||
/** @var int */
|
||||
public const M_VERSION = 0x10;
|
||||
/** @var int */
|
||||
public const M_QUIETZONE = 0x12;
|
||||
# public const M_LOGO = 0x14; // @todo
|
||||
|
||||
# public const M_LOGO = 0x14; // @todo
|
||||
/** @var int */
|
||||
public const M_TEST = 0xff;
|
||||
|
||||
/**
|
||||
* @link http://www.thonky.com/qr-code-tutorial/alignment-pattern-locations
|
||||
* ISO/IEC 18004:2000 Annex E, Table E.1 - Row/column coordinates of center module of Alignment Patterns
|
||||
*
|
||||
* version -> pattern
|
||||
* version -> pattern
|
||||
*
|
||||
* @var int[][]
|
||||
*/
|
||||
protected const alignmentPattern = [
|
||||
1 => [],
|
||||
@@ -85,9 +101,11 @@ final class QRMatrix{
|
||||
];
|
||||
|
||||
/**
|
||||
* @link http://www.thonky.com/qr-code-tutorial/format-version-tables
|
||||
* ISO/IEC 18004:2000 Annex D, Table D.1 - Version information bit stream for each version
|
||||
*
|
||||
* no version pattern for QR Codes < 7
|
||||
*
|
||||
* @var int[]
|
||||
*/
|
||||
protected const versionPattern = [
|
||||
7 => 0b000111110010010100,
|
||||
@@ -126,7 +144,13 @@ final class QRMatrix{
|
||||
40 => 0b101000110001101001,
|
||||
];
|
||||
|
||||
// ECC level -> mask pattern
|
||||
/**
|
||||
* ISO/IEC 18004:2000 Section 8.9 - Format Information
|
||||
*
|
||||
* ECC level -> mask pattern
|
||||
*
|
||||
* @var int[][]
|
||||
*/
|
||||
protected const formatPattern = [
|
||||
[ // L
|
||||
0b111011111000100,
|
||||
@@ -170,14 +194,31 @@ final class QRMatrix{
|
||||
],
|
||||
];
|
||||
|
||||
/**
|
||||
* the current QR Code version number
|
||||
*/
|
||||
protected int $version;
|
||||
|
||||
/**
|
||||
* the current ECC level
|
||||
*/
|
||||
protected int $eclevel;
|
||||
|
||||
/**
|
||||
* the used mask pattern, set via QRMatrix::mapData()
|
||||
*/
|
||||
protected int $maskPattern = QRCode::MASK_PATTERN_AUTO;
|
||||
|
||||
/**
|
||||
* the size (side length) of the matrix
|
||||
*/
|
||||
protected int $moduleCount;
|
||||
/** @var mixed[] */
|
||||
|
||||
/**
|
||||
* the actual matrix data array
|
||||
*
|
||||
* @var int[][]
|
||||
*/
|
||||
protected array $matrix;
|
||||
|
||||
/**
|
||||
@@ -217,6 +258,8 @@ final class QRMatrix{
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the data matrix
|
||||
*
|
||||
* @return int[][]
|
||||
*/
|
||||
public function matrix():array{
|
||||
@@ -224,21 +267,21 @@ final class QRMatrix{
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Returns the current version number
|
||||
*/
|
||||
public function version():int{
|
||||
return $this->version;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Returns the current ECC level
|
||||
*/
|
||||
public function eccLevel():int{
|
||||
return $this->eclevel;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Returns the current mask pattern
|
||||
*/
|
||||
public function maskPattern():int{
|
||||
return $this->maskPattern;
|
||||
@@ -297,6 +340,8 @@ final class QRMatrix{
|
||||
|
||||
/**
|
||||
* Draws the 7x7 finder patterns in the corners top left/right and bottom left
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 7.3.2
|
||||
*/
|
||||
public function setFinderPattern():QRMatrix{
|
||||
|
||||
@@ -324,6 +369,8 @@ final class QRMatrix{
|
||||
|
||||
/**
|
||||
* Draws the separator lines around the finder patterns
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 7.3.3
|
||||
*/
|
||||
public function setSeparators():QRMatrix{
|
||||
|
||||
@@ -352,6 +399,8 @@ final class QRMatrix{
|
||||
|
||||
/**
|
||||
* Draws the 5x5 alignment patterns
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 7.3.5
|
||||
*/
|
||||
public function setAlignmentPattern():QRMatrix{
|
||||
|
||||
@@ -380,6 +429,8 @@ final class QRMatrix{
|
||||
|
||||
/**
|
||||
* Draws the timing pattern (h/v checkered line between the finder patterns)
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 7.3.4
|
||||
*/
|
||||
public function setTimingPattern():QRMatrix{
|
||||
|
||||
@@ -400,6 +451,8 @@ final class QRMatrix{
|
||||
|
||||
/**
|
||||
* Draws the version information, 2x 3x6 pixel
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 8.10
|
||||
*/
|
||||
public function setVersionNumber(bool $test = null):QRMatrix{
|
||||
$bits = $this::versionPattern[$this->version] ?? false;
|
||||
@@ -422,6 +475,8 @@ final class QRMatrix{
|
||||
|
||||
/**
|
||||
* Draws the format info along the finder patterns
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 8.9
|
||||
*/
|
||||
public function setFormatInfo(int $maskPattern, bool $test = null):QRMatrix{
|
||||
$bits = $this::formatPattern[QRCode::ECC_MODES[$this->eclevel]][$maskPattern] ?? 0;
|
||||
@@ -459,6 +514,8 @@ final class QRMatrix{
|
||||
/**
|
||||
* Draws the "quiet zone" of $size around the matrix
|
||||
*
|
||||
* ISO/IEC 18004:2000 Section 7.3.7
|
||||
*
|
||||
* @throws \chillerlan\QRCode\Data\QRCodeDataException
|
||||
*/
|
||||
public function setQuietZone(int $size = null):QRMatrix{
|
||||
@@ -498,6 +555,8 @@ final class QRMatrix{
|
||||
*
|
||||
* @param int[] $data
|
||||
* @param int $maskPattern
|
||||
*
|
||||
* @return \chillerlan\QRCode\Data\QRMatrix
|
||||
*/
|
||||
public function mapData(array $data, int $maskPattern):QRMatrix{
|
||||
$this->maskPattern = $maskPattern;
|
||||
|
||||
@@ -14,15 +14,25 @@ namespace chillerlan\QRCode\Helpers;
|
||||
|
||||
use function count, floor;
|
||||
|
||||
/**
|
||||
* Holds the raw binary data
|
||||
*/
|
||||
final class BitBuffer{
|
||||
|
||||
/** @var int[] */
|
||||
/**
|
||||
* The buffer content
|
||||
*
|
||||
* @var int[]
|
||||
*/
|
||||
protected array $buffer = [];
|
||||
|
||||
/**
|
||||
* Length of the content (bits)
|
||||
*/
|
||||
protected int $length = 0;
|
||||
|
||||
/**
|
||||
*
|
||||
* clears the buffer
|
||||
*/
|
||||
public function clear():BitBuffer{
|
||||
$this->buffer = [];
|
||||
@@ -32,7 +42,7 @@ final class BitBuffer{
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* appends a sequence of bits
|
||||
*/
|
||||
public function put(int $num, int $length):BitBuffer{
|
||||
|
||||
@@ -44,7 +54,7 @@ final class BitBuffer{
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* appends a single bit
|
||||
*/
|
||||
public function putBit(bool $bit):BitBuffer{
|
||||
$bufIndex = floor($this->length / 8);
|
||||
|
||||
@@ -17,12 +17,14 @@ use chillerlan\QRCode\QRCodeException;
|
||||
use function array_fill, count, sprintf;
|
||||
|
||||
/**
|
||||
* @link http://www.thonky.com/qr-code-tutorial/error-correction-coding
|
||||
* Polynomial long division helpers
|
||||
*
|
||||
* @see http://www.thonky.com/qr-code-tutorial/error-correction-coding
|
||||
*/
|
||||
final class Polynomial{
|
||||
|
||||
/**
|
||||
* @link http://www.thonky.com/qr-code-tutorial/log-antilog-table
|
||||
* @see http://www.thonky.com/qr-code-tutorial/log-antilog-table
|
||||
*/
|
||||
protected const table = [
|
||||
[ 1, 0], [ 2, 0], [ 4, 1], [ 8, 25], [ 16, 2], [ 32, 50], [ 64, 26], [128, 198],
|
||||
@@ -79,7 +81,10 @@ final class Polynomial{
|
||||
}
|
||||
|
||||
/**
|
||||
* @param int[] $num
|
||||
* @param int|null $shift
|
||||
*
|
||||
* @return \chillerlan\QRCode\Helpers\Polynomial
|
||||
*/
|
||||
public function setNum(array $num, int $shift = null):Polynomial{
|
||||
$offset = 0;
|
||||
@@ -99,7 +104,9 @@ final class Polynomial{
|
||||
}
|
||||
|
||||
/**
|
||||
* @param int[] $e
|
||||
*
|
||||
* @return \chillerlan\QRCode\Helpers\Polynomial
|
||||
*/
|
||||
public function multiply(array $e):Polynomial{
|
||||
$n = array_fill(0, count($this->num) + count($e) - 1, 0);
|
||||
@@ -119,7 +126,9 @@ final class Polynomial{
|
||||
}
|
||||
|
||||
/**
|
||||
* @param int[] $e
|
||||
*
|
||||
* @return \chillerlan\QRCode\Helpers\Polynomial
|
||||
*/
|
||||
public function mod(array $e):Polynomial{
|
||||
$n = $this->num;
|
||||
|
||||
+19
-7
@@ -20,12 +20,17 @@ use function array_values, base64_encode, call_user_func, count, imagecoloralloc
|
||||
is_array, ob_end_clean, ob_get_contents, ob_start, range, sprintf;
|
||||
|
||||
/**
|
||||
* Converts the matrix into GD images, raw or base64 output
|
||||
* requires ext-gd
|
||||
* @link http://php.net/manual/book.image.php
|
||||
* Converts the matrix into GD images, raw or base64 output (requires ext-gd)
|
||||
*
|
||||
* @see http://php.net/manual/book.image.php
|
||||
*/
|
||||
class QRImage extends QROutputAbstract{
|
||||
|
||||
/**
|
||||
* GD image types that support transparency
|
||||
*
|
||||
* @var string[]
|
||||
*/
|
||||
protected const TRANSPARENCY_TYPES = [
|
||||
QRCode::OUTPUT_IMAGE_PNG,
|
||||
QRCode::OUTPUT_IMAGE_GIF,
|
||||
@@ -34,6 +39,8 @@ class QRImage extends QROutputAbstract{
|
||||
protected string $defaultMode = QRCode::OUTPUT_IMAGE_PNG;
|
||||
|
||||
/**
|
||||
* The GD image resource
|
||||
*
|
||||
* @see imagecreatetruecolor()
|
||||
* @var resource
|
||||
*/
|
||||
@@ -70,8 +77,8 @@ class QRImage extends QROutputAbstract{
|
||||
|
||||
// avoid: Indirect modification of overloaded property $imageTransparencyBG has no effect
|
||||
// https://stackoverflow.com/a/10455217
|
||||
$tbg = $this->options->imageTransparencyBG;
|
||||
$background = imagecolorallocate($this->image, ...$tbg);
|
||||
$tbg = $this->options->imageTransparencyBG;
|
||||
$background = imagecolorallocate($this->image, ...$tbg);
|
||||
|
||||
if((bool)$this->options->imageTransparent && in_array($this->options->outputType, $this::TRANSPARENCY_TYPES, true)){
|
||||
imagecolortransparent($this->image, $background);
|
||||
@@ -99,7 +106,7 @@ class QRImage extends QROutputAbstract{
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Creates a single QR pixel with the given settings
|
||||
*/
|
||||
protected function setPixel(int $x, int $y, array $rgb):void{
|
||||
imagefilledrectangle(
|
||||
@@ -113,7 +120,7 @@ class QRImage extends QROutputAbstract{
|
||||
}
|
||||
|
||||
/**
|
||||
* @param string|null $file
|
||||
* Creates the final image by calling the desired GD output function
|
||||
*
|
||||
* @throws \chillerlan\QRCode\Output\QRCodeOutputException
|
||||
*/
|
||||
@@ -139,6 +146,8 @@ class QRImage extends QROutputAbstract{
|
||||
}
|
||||
|
||||
/**
|
||||
* PNG output
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
protected function png():void{
|
||||
@@ -153,6 +162,7 @@ class QRImage extends QROutputAbstract{
|
||||
|
||||
/**
|
||||
* Jiff - like... JitHub!
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
protected function gif():void{
|
||||
@@ -160,6 +170,8 @@ class QRImage extends QROutputAbstract{
|
||||
}
|
||||
|
||||
/**
|
||||
* JPG output
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
protected function jpg():void{
|
||||
|
||||
@@ -8,6 +8,8 @@
|
||||
* @author smiley <smiley@chillerlan.net>
|
||||
* @copyright 2018 smiley
|
||||
* @license MIT
|
||||
*
|
||||
* @noinspection PhpComposerExtensionStubsInspection
|
||||
*/
|
||||
|
||||
namespace chillerlan\QRCode\Output;
|
||||
@@ -17,10 +19,10 @@ use Imagick, ImagickDraw, ImagickPixel;
|
||||
use function is_string;
|
||||
|
||||
/**
|
||||
* ImageMagick output module
|
||||
* requires ext-imagick
|
||||
* @link http://php.net/manual/book.imagick.php
|
||||
* @link http://phpimagick.com
|
||||
* ImageMagick output module (requires ext-imagick)
|
||||
*
|
||||
* @see http://php.net/manual/book.imagick.php
|
||||
* @see http://phpimagick.com
|
||||
*/
|
||||
class QRImagick extends QROutputAbstract{
|
||||
|
||||
@@ -67,7 +69,7 @@ class QRImagick extends QROutputAbstract{
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* Creates the QR image via ImagickDraw
|
||||
*/
|
||||
protected function drawImage(Imagick $imagick):string{
|
||||
$draw = new ImagickDraw;
|
||||
|
||||
+15
-6
@@ -26,7 +26,8 @@ class QRMarkup extends QROutputAbstract{
|
||||
/**
|
||||
* @see \sprintf()
|
||||
*/
|
||||
protected string $svgHeader = '<svg xmlns="http://www.w3.org/2000/svg" version="1.1" class="qr-svg %1$s" style="width: 100%%; height: auto;" viewBox="0 0 %2$d %2$d">';
|
||||
protected string $svgHeader = '<svg xmlns="http://www.w3.org/2000/svg" class="qr-svg %1$s" '.
|
||||
'style="width: 100%%; height: auto;" viewBox="0 0 %2$d %2$d">';
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
@@ -50,7 +51,7 @@ class QRMarkup extends QROutputAbstract{
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* HTML output
|
||||
*/
|
||||
protected function html():string{
|
||||
$html = '<div class="'.$this->options->cssClass.'">'.$this->options->eol;
|
||||
@@ -68,14 +69,18 @@ class QRMarkup extends QROutputAbstract{
|
||||
$html .= '</div>'.$this->options->eol;
|
||||
|
||||
if($this->options->cachefile){
|
||||
return '<!DOCTYPE html><head><meta charset="UTF-8"></head><body>'.$this->options->eol.$html.'</body>';
|
||||
return '<!DOCTYPE html>'.
|
||||
'<head><meta charset="UTF-8"><title>QR Code</title></head>'.
|
||||
'<body>'.$this->options->eol.$html.'</body>';
|
||||
}
|
||||
|
||||
return $html;
|
||||
}
|
||||
|
||||
/**
|
||||
* @link https://github.com/codemasher/php-qrcode/pull/5
|
||||
* SVG output
|
||||
*
|
||||
* @see https://github.com/codemasher/php-qrcode/pull/5
|
||||
*/
|
||||
protected function svg():string{
|
||||
$matrix = $this->matrix->matrix();
|
||||
@@ -123,7 +128,10 @@ class QRMarkup extends QROutputAbstract{
|
||||
}
|
||||
|
||||
if(!empty($path)){
|
||||
$svg .= sprintf('<path class="qr-%s %s" stroke="transparent" fill="%s" fill-opacity="%s" d="%s" />', $M_TYPE, $this->options->cssClass, $value, $this->options->svgOpacity, $path);
|
||||
$svg .= sprintf(
|
||||
'<path class="qr-%s %s" stroke="transparent" fill="%s" fill-opacity="%s" d="%s" />',
|
||||
$M_TYPE, $this->options->cssClass, $value, $this->options->svgOpacity, $path
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -133,7 +141,8 @@ class QRMarkup extends QROutputAbstract{
|
||||
|
||||
// if saving to file, append the correct headers
|
||||
if($this->options->cachefile){
|
||||
return '<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">'.$this->options->eol.$svg;
|
||||
return '<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">'.
|
||||
$this->options->eol.$svg;
|
||||
}
|
||||
|
||||
return $svg;
|
||||
|
||||
@@ -45,7 +45,7 @@ class QRString extends QROutputAbstract{
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* string output
|
||||
*/
|
||||
protected function text():string{
|
||||
$str = [];
|
||||
@@ -64,7 +64,7 @@ class QRString extends QROutputAbstract{
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* JSON output
|
||||
*/
|
||||
protected function json():string{
|
||||
return json_encode($this->matrix->matrix());
|
||||
|
||||
+83
-30
@@ -25,45 +25,37 @@ use function call_user_func_array, class_exists, in_array, mb_internal_encoding,
|
||||
/**
|
||||
* Turns a text string into a Model 2 QR Code
|
||||
*
|
||||
* @link https://github.com/kazuhikoarase/qrcode-generator/tree/master/php
|
||||
* @link http://www.qrcode.com/en/codes/model12.html
|
||||
* @link http://www.thonky.com/qr-code-tutorial/
|
||||
* @see https://github.com/kazuhikoarase/qrcode-generator/tree/master/php
|
||||
* @see http://www.qrcode.com/en/codes/model12.html
|
||||
* @see https://www.swisseduc.ch/informatik/theoretische_informatik/qr_codes/docs/qr_standard.pdf
|
||||
* @see https://en.wikipedia.org/wiki/QR_code
|
||||
* @see http://www.thonky.com/qr-code-tutorial/
|
||||
*/
|
||||
class QRCode{
|
||||
|
||||
/**
|
||||
* API constants
|
||||
*/
|
||||
public const OUTPUT_MARKUP_HTML = 'html';
|
||||
public const OUTPUT_MARKUP_SVG = 'svg';
|
||||
public const OUTPUT_IMAGE_PNG = 'png';
|
||||
public const OUTPUT_IMAGE_JPG = 'jpg';
|
||||
public const OUTPUT_IMAGE_GIF = 'gif';
|
||||
public const OUTPUT_STRING_JSON = 'json';
|
||||
public const OUTPUT_STRING_TEXT = 'text';
|
||||
public const OUTPUT_IMAGICK = 'imagick';
|
||||
public const OUTPUT_CUSTOM = 'custom';
|
||||
|
||||
/** @var int */
|
||||
public const VERSION_AUTO = -1;
|
||||
/** @var int */
|
||||
public const MASK_PATTERN_AUTO = -1;
|
||||
|
||||
public const ECC_L = 0b01; // 7%.
|
||||
public const ECC_M = 0b00; // 15%.
|
||||
public const ECC_Q = 0b11; // 25%.
|
||||
public const ECC_H = 0b10; // 30%.
|
||||
// ISO/IEC 18004:2000 Table 2
|
||||
|
||||
/** @var int */
|
||||
public const DATA_NUMBER = 0b0001;
|
||||
/** @var int */
|
||||
public const DATA_ALPHANUM = 0b0010;
|
||||
/** @var int */
|
||||
public const DATA_BYTE = 0b0100;
|
||||
/** @var int */
|
||||
public const DATA_KANJI = 0b1000;
|
||||
|
||||
public const ECC_MODES = [
|
||||
self::ECC_L => 0,
|
||||
self::ECC_M => 1,
|
||||
self::ECC_Q => 2,
|
||||
self::ECC_H => 3,
|
||||
];
|
||||
|
||||
/**
|
||||
* References to the keys of the following tables:
|
||||
*
|
||||
* @see \chillerlan\QRCode\Data\QRDataInterface::MAX_LENGTH
|
||||
*
|
||||
* @var int[]
|
||||
*/
|
||||
public const DATA_MODES = [
|
||||
self::DATA_NUMBER => 0,
|
||||
self::DATA_ALPHANUM => 1,
|
||||
@@ -71,6 +63,57 @@ class QRCode{
|
||||
self::DATA_KANJI => 3,
|
||||
];
|
||||
|
||||
// ISO/IEC 18004:2000 Tables 12, 25
|
||||
|
||||
/** @var int */
|
||||
public const ECC_L = 0b01; // 7%.
|
||||
/** @var int */
|
||||
public const ECC_M = 0b00; // 15%.
|
||||
/** @var int */
|
||||
public const ECC_Q = 0b11; // 25%.
|
||||
/** @var int */
|
||||
public const ECC_H = 0b10; // 30%.
|
||||
|
||||
/**
|
||||
* References to the keys of the following tables:
|
||||
*
|
||||
* @see \chillerlan\QRCode\Data\QRDataInterface::MAX_BITS
|
||||
* @see \chillerlan\QRCode\Data\QRDataInterface::RSBLOCKS
|
||||
* @see \chillerlan\QRCode\Data\QRMatrix::formatPattern
|
||||
*
|
||||
* @var int[]
|
||||
*/
|
||||
public const ECC_MODES = [
|
||||
self::ECC_L => 0,
|
||||
self::ECC_M => 1,
|
||||
self::ECC_Q => 2,
|
||||
self::ECC_H => 3,
|
||||
];
|
||||
|
||||
/** @var string */
|
||||
public const OUTPUT_MARKUP_HTML = 'html';
|
||||
/** @var string */
|
||||
public const OUTPUT_MARKUP_SVG = 'svg';
|
||||
/** @var string */
|
||||
public const OUTPUT_IMAGE_PNG = 'png';
|
||||
/** @var string */
|
||||
public const OUTPUT_IMAGE_JPG = 'jpg';
|
||||
/** @var string */
|
||||
public const OUTPUT_IMAGE_GIF = 'gif';
|
||||
/** @var string */
|
||||
public const OUTPUT_STRING_JSON = 'json';
|
||||
/** @var string */
|
||||
public const OUTPUT_STRING_TEXT = 'text';
|
||||
/** @var string */
|
||||
public const OUTPUT_IMAGICK = 'imagick';
|
||||
/** @var string */
|
||||
public const OUTPUT_CUSTOM = 'custom';
|
||||
|
||||
/**
|
||||
* Map of built-in output modules => capabilities
|
||||
*
|
||||
* @var string[][]
|
||||
*/
|
||||
public const OUTPUT_MODES = [
|
||||
QRMarkup::class => [
|
||||
self::OUTPUT_MARKUP_SVG,
|
||||
@@ -103,22 +146,31 @@ class QRCode{
|
||||
];
|
||||
|
||||
/**
|
||||
* The settings container
|
||||
*
|
||||
* @var \chillerlan\QRCode\QROptions|\chillerlan\Settings\SettingsContainerInterface
|
||||
*/
|
||||
protected SettingsContainerInterface $options;
|
||||
|
||||
/**
|
||||
* The selected data interface (Number, AlphaNum, Kanji, Byte)
|
||||
*/
|
||||
protected QRDataInterface $dataInterface;
|
||||
|
||||
/**
|
||||
* @see http://php.net/manual/function.mb-internal-encoding.php
|
||||
* The current encoding (before the QRCode instance was invoked)
|
||||
*
|
||||
* @see http://php.net/manual/function.mb-internal-encoding.php mb_internal_encoding()
|
||||
*/
|
||||
protected string $mbCurrentEncoding;
|
||||
|
||||
/**
|
||||
* QRCode constructor.
|
||||
*
|
||||
* Sets the options instance, determines the current mb-encoding and sets it to UTF-8
|
||||
*/
|
||||
public function __construct(SettingsContainerInterface $options = null){
|
||||
// save the current mb encoding (in case it differs from UTF-8)
|
||||
// save the current mb-encoding (in case it differs from UTF-8)
|
||||
$this->mbCurrentEncoding = mb_internal_encoding();
|
||||
// use UTF-8 from here on
|
||||
mb_internal_encoding('UTF-8');
|
||||
@@ -127,10 +179,11 @@ class QRCode{
|
||||
}
|
||||
|
||||
/**
|
||||
* Restores the previous mb-encoding setting, so that we don't mess up the rest of the script
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __destruct(){
|
||||
// restore the previous mb_internal_encoding, so that we don't mess up the rest of the script
|
||||
mb_internal_encoding($this->mbCurrentEncoding);
|
||||
}
|
||||
|
||||
|
||||
@@ -12,4 +12,7 @@
|
||||
|
||||
namespace chillerlan\QRCode;
|
||||
|
||||
/**
|
||||
* An exception container
|
||||
*/
|
||||
class QRCodeException extends \Exception{}
|
||||
|
||||
+30
-36
@@ -15,43 +15,37 @@ namespace chillerlan\QRCode;
|
||||
use chillerlan\Settings\SettingsContainerAbstract;
|
||||
|
||||
/**
|
||||
* @property int $version
|
||||
* @property int $versionMin
|
||||
* @property int $versionMax
|
||||
* @property int $eccLevel
|
||||
* @property int $maskPattern
|
||||
* @property bool $addQuietzone
|
||||
* @property int $quietzoneSize
|
||||
* The QRCode settings container
|
||||
*
|
||||
* @property string $dataMode
|
||||
* @property string $outputType
|
||||
* @property string $outputInterface
|
||||
* @property string $cachefile
|
||||
*
|
||||
* @property string $eol
|
||||
* @property int $scale
|
||||
*
|
||||
* @property string $cssClass
|
||||
* @property float $svgOpacity
|
||||
* @property string $svgDefs
|
||||
* @property int $svgViewBoxSize
|
||||
*
|
||||
* @property string $textDark
|
||||
* @property string $textLight
|
||||
*
|
||||
* @property string $markupDark
|
||||
* @property string $markupLight
|
||||
*
|
||||
* @property bool $imageBase64
|
||||
* @property bool $imageTransparent
|
||||
* @property array $imageTransparencyBG
|
||||
* @property int $pngCompression
|
||||
* @property int $jpegQuality
|
||||
*
|
||||
* @property string $imagickFormat
|
||||
* @property string $imagickBG
|
||||
*
|
||||
* @property array $moduleValues
|
||||
* @property int $version
|
||||
* @property int $versionMin
|
||||
* @property int $versionMax
|
||||
* @property int $eccLevel
|
||||
* @property int $maskPattern
|
||||
* @property bool $addQuietzone
|
||||
* @property int $quietzoneSize
|
||||
* @property string|null $dataMode
|
||||
* @property string $outputType
|
||||
* @property string|null $outputInterface
|
||||
* @property string|null $cachefile
|
||||
* @property string $eol
|
||||
* @property int $scale
|
||||
* @property string $cssClass
|
||||
* @property float $svgOpacity
|
||||
* @property string $svgDefs
|
||||
* @property int $svgViewBoxSize
|
||||
* @property string $textDark
|
||||
* @property string $textLight
|
||||
* @property string $markupDark
|
||||
* @property string $markupLight
|
||||
* @property bool $imageBase64
|
||||
* @property bool $imageTransparent
|
||||
* @property array $imageTransparencyBG
|
||||
* @property int $pngCompression
|
||||
* @property int $jpegQuality
|
||||
* @property string $imagickFormat
|
||||
* @property string|null $imagickBG
|
||||
* @property array|null $moduleValues
|
||||
*/
|
||||
class QROptions extends SettingsContainerAbstract{
|
||||
use QROptionsTrait;
|
||||
|
||||
+25
-17
@@ -14,17 +14,22 @@ namespace chillerlan\QRCode;
|
||||
|
||||
use function array_values, count, is_numeric, max, min, sprintf;
|
||||
|
||||
/**
|
||||
* The QRCode plug-in settings & setter functionality
|
||||
*/
|
||||
trait QROptionsTrait{
|
||||
|
||||
/**
|
||||
* QR Code version number
|
||||
*
|
||||
* [1 ... 40] or QRCode::VERSION_AUTO
|
||||
* [1 ... 40] or QRCode::VERSION_AUTO
|
||||
*/
|
||||
protected int $version = QRCode::VERSION_AUTO;
|
||||
|
||||
/**
|
||||
* Minimum QR version (if $version = QRCode::VERSION_AUTO)
|
||||
* Minimum QR version
|
||||
*
|
||||
* if $version = QRCode::VERSION_AUTO
|
||||
*/
|
||||
protected int $versionMin = 1;
|
||||
|
||||
@@ -36,18 +41,19 @@ trait QROptionsTrait{
|
||||
/**
|
||||
* Error correct level
|
||||
*
|
||||
* QRCode::ECC_X where X is
|
||||
* L => 7%
|
||||
* M => 15%
|
||||
* Q => 25%
|
||||
* H => 30%
|
||||
* QRCode::ECC_X where X is:
|
||||
*
|
||||
* - L => 7%
|
||||
* - M => 15%
|
||||
* - Q => 25%
|
||||
* - H => 30%
|
||||
*/
|
||||
protected int $eccLevel = QRCode::ECC_L;
|
||||
|
||||
/**
|
||||
* Mask Pattern to use
|
||||
*
|
||||
* [0...7] or QRCode::MASK_PATTERN_AUTO
|
||||
* [0...7] or QRCode::MASK_PATTERN_AUTO
|
||||
*/
|
||||
protected int $maskPattern = QRCode::MASK_PATTERN_AUTO;
|
||||
|
||||
@@ -59,12 +65,13 @@ trait QROptionsTrait{
|
||||
/**
|
||||
* Size of the quiet zone
|
||||
*
|
||||
* internally clamped to [0 ... $moduleCount / 2], defaults to 4 modules
|
||||
* internally clamped to [0 ... $moduleCount / 2], defaults to 4 modules
|
||||
*/
|
||||
protected int $quietzoneSize = 4;
|
||||
|
||||
/**
|
||||
* Use this to circumvent the data mode detection and force the usage of the given mode.
|
||||
*
|
||||
* valid modes are: Number, AlphaNum, Kanji, Byte
|
||||
*
|
||||
* @see https://github.com/chillerlan/php-qrcode/issues/39
|
||||
@@ -72,10 +79,12 @@ trait QROptionsTrait{
|
||||
protected ?string $dataMode = null;
|
||||
|
||||
/**
|
||||
* QRCode::OUTPUT_MARKUP_XXXX where XXXX = HTML, SVG
|
||||
* QRCode::OUTPUT_IMAGE_XXX where XXX = PNG, GIF, JPG
|
||||
* QRCode::OUTPUT_STRING_XXXX where XXXX = TEXT, JSON
|
||||
* QRCode::OUTPUT_CUSTOM
|
||||
* The output type
|
||||
*
|
||||
* - QRCode::OUTPUT_MARKUP_XXXX where XXXX = HTML, SVG
|
||||
* - QRCode::OUTPUT_IMAGE_XXX where XXX = PNG, GIF, JPG
|
||||
* - QRCode::OUTPUT_STRING_XXXX where XXXX = TEXT, JSON
|
||||
* - QRCode::OUTPUT_CUSTOM
|
||||
*/
|
||||
protected string $outputType = QRCode::OUTPUT_IMAGE_PNG;
|
||||
|
||||
@@ -95,8 +104,7 @@ trait QROptionsTrait{
|
||||
protected string $eol = PHP_EOL;
|
||||
|
||||
/**
|
||||
* size of a QR code pixel [SVG, IMAGE_*]
|
||||
* HTML -> via CSS
|
||||
* size of a QR code pixel [SVG, IMAGE_*], HTML via CSS
|
||||
*/
|
||||
protected int $scale = 5;
|
||||
|
||||
@@ -190,8 +198,8 @@ trait QROptionsTrait{
|
||||
/**
|
||||
* Module values map
|
||||
*
|
||||
* HTML, IMAGICK: #ABCDEF, cssname, rgb(), rgba()...
|
||||
* IMAGE: [63, 127, 255] // R, G, B
|
||||
* - HTML, IMAGICK: #ABCDEF, cssname, rgb(), rgba()...
|
||||
* - IMAGE: [63, 127, 255] // R, G, B
|
||||
*/
|
||||
protected ?array $moduleValues = null;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user