Number.php 1.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182
  1. <?php
  2. /**
  3. * Class Number
  4. *
  5. * @filesource Number.php
  6. * @created 26.11.2015
  7. * @package QRCode
  8. * @author Smiley <smiley@chillerlan.net>
  9. * @copyright 2015 Smiley
  10. * @license MIT
  11. */
  12. namespace chillerlan\QRCode\Data;
  13. use chillerlan\QRCode\QRCode;
  14. use function ord, sprintf, substr;
  15. /**
  16. * Numeric mode: decimal digits 0 through 9
  17. */
  18. class Number extends QRDataAbstract{
  19. /**
  20. * @inheritdoc
  21. */
  22. protected $datamode = QRCode::DATA_NUMBER;
  23. /**
  24. * @inheritdoc
  25. */
  26. protected $lengthBits = [10, 12, 14];
  27. /**
  28. * @inheritdoc
  29. */
  30. protected function write(string $data):void{
  31. $i = 0;
  32. while($i + 2 < $this->strlen){
  33. $this->bitBuffer->put($this->parseInt(substr($data, $i, 3)), 10);
  34. $i += 3;
  35. }
  36. if($i < $this->strlen){
  37. if($this->strlen - $i === 1){
  38. $this->bitBuffer->put($this->parseInt(substr($data, $i, $i + 1)), 4);
  39. }
  40. elseif($this->strlen - $i === 2){
  41. $this->bitBuffer->put($this->parseInt(substr($data, $i, $i + 2)), 7);
  42. }
  43. }
  44. }
  45. /**
  46. * @param string $string
  47. *
  48. * @return int
  49. * @throws \chillerlan\QRCode\Data\QRCodeDataException
  50. */
  51. protected function parseInt(string $string):int{
  52. $num = 0;
  53. $len = strlen($string);
  54. for($i = 0; $i < $len; $i++){
  55. $c = ord($string[$i]);
  56. if(!in_array($string[$i], $this::NUMBER_CHAR_MAP, true)){
  57. throw new QRCodeDataException(sprintf('illegal char: "%s" [%d]', $string[$i], $c));
  58. }
  59. $c = $c - 48; // ord('0')
  60. $num = $num * 10 + $c;
  61. }
  62. return $num;
  63. }
  64. }