PluginProbe
PDF & Print by BestWebSoft – WordPress Posts and Pages PDF Generator Plugin / trunk
PDF & Print by BestWebSoft – WordPress Posts and Pages PDF Generator Plugin vtrunk
trunk 1.5 1.6 1.7 1.7.1 1.7.2 1.7.3 1.7.4 1.7.5 1.7.6 1.7.7 1.7.8 1.7.9 1.8.0 1.8.1 1.8.2 1.8.3 1.8.4 1.8.5 1.8.6 1.8.7 1.8.8 1.8.9 1.9.0 1.9.1 All 71 releases
pdf-print / mpdf / qrcode / qrcode.class.php

qrcode.class.php in PDF & Print by BestWebSoft – WordPress Posts and Pages PDF Generator Plugin trunk, at mpdf/qrcode/qrcode.class.php

673 lines 19.8 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /*
3 * Generateur de QRCode
4 * (QR Code is registered trademark of DENSO WAVE INCORPORATED | http://www.denso-wave.com/qrcode/)
5 * Fortement inspiré de "QRcode image PHP scripts version 0.50g (C)2000-2005,Y.Swetake"
6 *
7 * Distribué sous la licence LGPL.
8 *
9 * @author Laurent MINGUET <webmaster@spipu.net>
10 * @version 0.99
11 */
12
13 if (!defined('__CLASS_QRCODE__'))
14 {
15 define('__CLASS_QRCODE__', '0.99');
16
17 class QRcode
18 {
19 private $version_mx = 40; // numero de version maximal autorisé
20 private $type = 'bin'; // type de donnée
21 private $level = 'L'; // ECC
22 private $value = ''; // valeur a encoder
23 private $length = 0; // taille de la valeur
24 private $version = 0; // version
25 private $size = 0; // dimension de la zone data
26 private $qr_size = 0; // dimension du QRcode
27
28 private $data_bit = array(); // nb de bit de chacune des valeurs
29 private $data_val = array(); // liste des valeurs de bit différents
30 private $data_word = array(); // liste des valeurs tout ramené à 8bit
31 private $data_cur = 0; // position courante
32 private $data_num = 0; // position de la dimension
33 private $data_bits = 0; // nom de bit au total
34 private $max_data_bit = 0; // lilmite de nombre de bit maximal pour les datas
35 private $max_data_word = 0; // lilmite de nombre de mot maximal pour les datas
36 private $max_word = 0; // lilmite de nombre de mot maximal en global
37
38 private $ec = 0;
39 private $matrix = array();
40 private $matrix_remain = 0;
41 private $matrix_x_array = array();
42 private $matrix_y_array = array();
43 private $mask_array = array();
44 private $format_information_x1 = array();
45 private $format_information_y1 = array();
46 private $format_information_x2 = array();
47 private $format_information_y2 = array();
48 private $rs_block_order = array();
49 private $rs_ecc_codewords = 0;
50 private $byte_num = 0;
51
52 private $final = array();
53 private $disable_border = false;
54
55
56 /**
57 * Constructeur
58 *
59 * @param string message a encoder
60 * @param string niveau de correction d'erreur (ECC) : L, M, Q, H
61 * @return null
62 */
63 public function __construct($value, $level='L')
64 {
65 if (!in_array($level, array('L', 'M', 'Q', 'H')))
66 $this->ERROR('ECC non reconnu : L, M, Q, H');
67
68 $this->length = strlen($value);
69 if (!$this->length)
70 $this->ERROR('pas de data...');
71
72 $this->level = $level;
73 $this->value = &$value;
74
75 $this->data_bit = array();
76 $this->data_val = array();
77 $this->data_cur = 0;
78 $this->data_bits= 0;
79
80 $this->encode();
81 $this->loadECC();
82 $this->makeECC();
83 $this->makeMatrix();
84 }
85
86 /**
87 * permet de recuperer la taille du QRcode (le nombre de case de côté)
88 *
89 * @return int size of qrcode
90 */
91 public function getQrSize()
92 {
93 if ($this->disable_border)
94 return $this->qr_size-8;
95 else
96 return $this->qr_size;
97 }
98
99 public function disableBorder()
100 {
101 $this->disable_border = true;
102 }
103
104 /**
105 * permet d'afficher le QRcode dans un pdf via FPDF
106 *
107 * @param FPDF objet fpdf
108 * @param float position X
109 * @param float position Y
110 * @param float taille du qrcode
111 * @param array couleur du background (R,V,B)
112 * @param array couleur des cases et du border (R,V,B)
113 * @return boolean true;
114 */
115 public function displayFPDF(&$fpdf, $x, $y, $w, $background=array(255,255,255), $color=array(0,0,0))
116 {
117 $size = $w;
118 $s = $size/$this->getQrSize();
119
120 $fpdf->SetDrawColor($color[0], $color[1], $color[2]);
121 $fpdf->SetFillColor($background[0], $background[1], $background[2]);
122
123 // rectangle de fond
124 if ($this->disable_border)
125 {
126 $s_min = 4;
127 $s_max = $this->qr_size-4;
128 $fpdf->Rect($x, $y, $size, $size, 'F');
129 }
130 else
131 {
132 $s_min = 0;
133 $s_max = $this->qr_size;
134 $fpdf->Rect($x, $y, $size, $size, 'FD');
135 }
136
137 $fpdf->SetFillColor($color[0], $color[1], $color[2]);
138 for($j=$s_min; $j<$s_max; $j++)
139 for($i=$s_min; $i<$s_max; $i++)
140 if ($this->final[$i + $j*$this->qr_size+1])
141 $fpdf->Rect($x+($i-$s_min)*$s, $y+($j-$s_min)*$s, $s, $s, 'F');
142
143 return true;
144 }
145
146 /**
147 * permet d'afficher le QRcode au format HTML, à utiliser avec un style CSS
148 *
149 * @return boolean true;
150 */
151 public function displayHTML()
152 {
153 if ($this->disable_border)
154 {
155 $s_min = 4;
156 $s_max = $this->qr_size-4;
157 }
158 else
159 {
160 $s_min = 0;
161 $s_max = $this->qr_size;
162 }
163 echo '<table class="qr" cellpadding="0" cellspacing="0">'."\n";
164 for($y=$s_min; $y<$s_max; $y++)
165 {
166 echo '<tr>';
167 for($x=$s_min; $x<$s_max; $x++)
168 {
169 echo '<td class="'.($this->final[$x + $y*$this->qr_size+1] ? 'on' : 'off').'"></td>';
170 }
171 echo '</tr>'."\n";
172 }
173 echo '</table>';
174
175 return true;
176 }
177
178 /*
179 * permet d'obtenir une image PNG
180 *
181 * @param float taille du qrcode
182 * @param array couleur du background (R,V,B)
183 * @param array couleur des cases et du border (R,V,B)
184 * @param string nom du fichier de sortie. si null : sortie directe
185 * @param integer qualité de 0 (aucune compression) a 9
186 * @return boolean true;
187 */
188 public function displayPNG($w=100, $background=array(255,255,255), $color=array(0,0,0), $filename = null, $quality = 0)
189 {
190 if ($this->disable_border)
191 {
192 $s_min = 4;
193 $s_max = $this->qr_size-4;
194 }
195 else
196 {
197 $s_min = 0;
198 $s_max = $this->qr_size;
199 }
200 $size = $w;
201 $s = $size/($s_max-$s_min);
202
203 // rectangle de fond
204 $im = imagecreatetruecolor($size,$size);
205 $c_case = imagecolorallocate($im,$color[0],$color[1],$color[2]);
206 $c_back = imagecolorallocate($im,$background[0],$background[1],$background[2]);
207 imagefilledrectangle($im,0,0,$size,$size,$c_back);
208
209 for($j=$s_min; $j<$s_max; $j++)
210 for($i=$s_min; $i<$s_max; $i++)
211 if ($this->final[$i + $j*$this->qr_size+1])
212 imagefilledrectangle($im,($i-$s_min)*$s,($j-$s_min)*$s,($i-$s_min+1)*$s-1,($j-$s_min+1)*$s-1,$c_case);
213
214 if ($filename)
215 {
216 imagepng($im, $filename, $quality);
217 }
218 else
219 {
220 header("Content-type: image/png");
221 imagepng($im);
222 }
223 imagedestroy($im);
224 return true;
225 }
226
227 private function ERROR($msg)
228 {
229 echo 'ERROR : '.$msg;
230 exit;
231 }
232
233 private function addData($val, $bit, $next = true)
234 {
235 $this->data_val[$this->data_cur] = $val;
236 $this->data_bit[$this->data_cur] = $bit;
237 if ($next)
238 {
239 $this->data_cur++;
240 return $this->data_cur-1;
241 }
242 else
243 {
244 return $this->data_cur;
245 }
246 }
247
248 private function encode()
249 {
250 // conversion des datas
251 if (preg_match('/[^0-9]/',$this->value))
252 {
253 if (preg_match('/[^0-9A-Z \$\*\%\+\-\.\/\:]/',$this->value))
254 {
255 // type : bin
256 $this->type = 'bin';
257 $this->addData(4, 4);
258
259 // taille. il faut garder l'indice, car besoin de correction
260 $this->data_num = $this->addData($this->length, 8); /* #version 1-9 */
261 $data_num_correction=array(0,0,0,0,0,0,0,0,0,0,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8);
262
263 // datas
264 for ($i=0; $i<$this->length; $i++)
265 $this->addData(ord(substr($this->value, $i, 1)), 8);
266 }
267 else
268 {
269 // type : alphanum
270 $this->type = 'alphanum';
271 $this->addData(2, 4);
272
273 // taille. il faut garder l'indice, car besoin de correction
274 $this->data_num = $this->addData($this->length, 9); /* #version 1-9 */
275 $data_num_correction=array(0,0,0,0,0,0,0,0,0,0,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,4,4,4,4,4,4,4,4,4,4,4,4,4,4);
276
277 // datas
278 $an_hash=array(
279 '0'=>0,'1'=>1,'2'=>2,'3'=>3,'4'=>4,'5'=>5,'6'=>6,'7'=>7,'8'=>8,'9'=>9,
280 'A'=>10,'B'=>11,'C'=>12,'D'=>13,'E'=>14,'F'=>15,'G'=>16,'H'=>17,'I'=>18,'J'=>19,'K'=>20,'L'=>21,'M'=>22,
281 'N'=>23,'O'=>24,'P'=>25,'Q'=>26,'R'=>27,'S'=>28,'T'=>29,'U'=>30,'V'=>31,'W'=>32,'X'=>33,'Y'=>34,'Z'=>35,
282 ' '=>36,'$'=>37,'%'=>38,'*'=>39,'+'=>40,'-'=>41,'.'=>42,'/'=>43,':'=>44);
283
284 for ($i=0; $i<$this->length; $i++)
285 {
286 if (($i %2)==0)
287 $this->addData($an_hash[substr($this->value,$i,1)], 6, false);
288 else
289 $this->addData($this->data_val[$this->data_cur]*45+$an_hash[substr($this->value,$i,1)], 11, true);
290 }
291 unset($an_hash);
292
293 if (isset($this->data_bit[$this->data_cur]))
294 $this->data_cur++;
295 }
296 }
297 else
298 {
299 // type : num
300 $this->type = 'num';
301 $this->addData(1, 4);
302
303 //taille. il faut garder l'indice, car besoin de correction
304 $this->data_num = $this->addData($this->length, 10); /* #version 1-9 */
305 $data_num_correction=array(0,0,0,0,0,0,0,0,0,0,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,4,4,4,4,4,4,4,4,4,4,4,4,4,4);
306
307 // datas
308 for ($i=0; $i<$this->length; $i++)
309 {
310 if (($i % 3)==0)
311 $this->addData(substr($this->value,$i,1), 4, false);
312 else if (($i % 3)==1)
313 $this->addData($this->data_val[$this->data_cur]*10+substr($this->value,$i,1), 7, false);
314 else
315 $this->addData($this->data_val[$this->data_cur]*10+substr($this->value,$i,1), 10);
316 }
317
318 if (isset($this->data_bit[$this->data_cur]))
319 $this->data_cur++;
320
321
322 }
323
324 // calcul du nombre de bits
325 $this->data_bits=0;
326 foreach($this->data_bit as $bit)
327 $this->data_bits+= $bit;
328
329 // code ECC
330 $ec_hash = array('L'=>1, 'M'=>0, 'Q'=>3, 'H'=>2);
331 $this->ec = $ec_hash[$this->level];
332
333 // tableau de taille limite de bits
334 $max_bits = array(
335 0,128,224,352,512,688,864,992,1232,1456,1728,2032,2320,2672,2920,3320,3624,4056,4504,5016,5352,
336 5712,6256,6880,7312,8000,8496,9024,9544,10136,10984,11640,12328,13048,13800,14496,15312,15936,16816,17728,18672,
337
338 152,272,440,640,864,1088,1248,1552,1856,2192,2592,2960,3424,3688,4184,4712,5176,5768,6360,6888,
339 7456,8048,8752,9392,10208,10960,11744,12248,13048,13880,14744,15640,16568,17528,18448,19472,20528,21616,22496,23648,
340
341 72,128,208,288,368,480,528,688,800,976,1120,1264,1440,1576,1784,2024,2264,2504,2728,3080,
342 3248,3536,3712,4112,4304,4768,5024,5288,5608,5960,6344,6760,7208,7688,7888,8432,8768,9136,9776,10208,
343
344 104,176,272,384,496,608,704,880,1056,1232,1440,1648,1952,2088,2360,2600,2936,3176,3560,3880,
345 4096,4544,4912,5312,5744,6032,6464,6968,7288,7880,8264,8920,9368,9848,10288,10832,11408,12016,12656,13328
346 );
347
348 // determination automatique de la version necessaire
349 $this->version=1;
350 $i=1+40*$this->ec;
351 $j=$i+39;
352 while ($i<=$j)
353 {
354 if ($max_bits[$i]>=$this->data_bits+$data_num_correction[$this->version])
355 {
356 $this->max_data_bit=$max_bits[$i];
357 break;
358 }
359 $i++;
360 $this->version++;
361 }
362
363 // verification max version
364 if ($this->version>$this->version_mx)
365 $this->ERROR('too large version.');
366
367 // correctif sur le nombre de bits du strlen de la valeur
368 $this->data_bits+=$data_num_correction[$this->version];
369 $this->data_bit[$this->data_num]+=$data_num_correction[$this->version];
370 $this->max_data_word = ($this->max_data_bit/8);
371
372 // nombre de mots maximal
373 $max_words_array=array(0,26,44,70,100,134,172,196,242,292,346,404,466,532,581,655,733,815,901,991,1085,1156,
374 1258,1364,1474,1588,1706,1828,1921,2051,2185,2323,2465,2611,2761,2876,3034,3196,3362,3532,3706);
375 $this->max_word = $max_words_array[$this->version];
376 $this->size = 17 + 4*$this->version;
377
378 // nettoyages divers
379 unset($max_bits);
380 unset($data_num_correction);
381 unset($max_words_array);
382 unset($ec_hash);
383
384 // terminator
385 if ($this->data_bits<=$this->max_data_bit-4)
386 $this->addData(0, 4);
387 elseif ($this->data_bits<$this->max_data_bit)
388 $this->addData(0, $this->max_data_bit-$this->data_bits);
389 elseif ($this->data_bits>$this->max_data_bit)
390 $this->ERROR('Overflow error');
391
392 // construction des mots de 8 bit
393 $this->data_word = array();
394 $this->data_word[0] = 0;
395 $nb_word = 0;
396
397 $remaining_bit=8;
398 for($i=0; $i<$this->data_cur; $i++)
399 {
400 $buffer_val=$this->data_val[$i];
401 $buffer_bit=$this->data_bit[$i];
402
403 $flag = true;
404 while ($flag)
405 {
406 if ($remaining_bit>$buffer_bit)
407 {
408 $this->data_word[$nb_word]=((@$this->data_word[$nb_word]<<$buffer_bit) | $buffer_val);
409 $remaining_bit-=$buffer_bit;
410 $flag=false;
411 }
412 else
413 {
414 $buffer_bit-=$remaining_bit;
415 $this->data_word[$nb_word]=((@$this->data_word[$nb_word] << $remaining_bit) | ($buffer_val >> $buffer_bit));
416 $nb_word++;
417
418 if ($buffer_bit==0)
419 $flag=false;
420 else
421 $buffer_val= ($buffer_val & ((1 << $buffer_bit)-1) );
422
423 if ($nb_word<$this->max_data_word-1)
424 $this->data_word[$nb_word]=0;
425 $remaining_bit=8;
426 }
427 }
428 }
429
430 // completion du dernier mot si incomplet
431 if ($remaining_bit<8)
432 $this->data_word[$nb_word]=$this->data_word[$nb_word] << $remaining_bit;
433 else
434 $nb_word--;
435
436 // remplissage du reste
437 if ($nb_word<$this->max_data_word-1)
438 {
439 $flag=true;
440 while ($nb_word<$this->max_data_word-1)
441 {
442 $nb_word++;
443 if ($flag)
444 $this->data_word[$nb_word]=236;
445 else
446 $this->data_word[$nb_word]=17;
447 $flag=!$flag;
448 }
449 }
450 }
451
452 private function loadECC()
453 {
454 $matrix_remain_bit=array(0,0,7,7,7,7,7,0,0,0,0,0,0,0,3,3,3,3,3,3,3,4,4,4,4,4,4,4,3,3,3,3,3,3,3,0,0,0,0,0,0);
455 $this->matrix_remain = $matrix_remain_bit[$this->version];
456 unset($matrix_remain_bit);
457
458 // lecture du fichier : data file of geometry & mask for version V ,ecc level N
459 $this->byte_num = $this->matrix_remain+ 8*$this->max_word;
460 $filename = dirname(__FILE__)."/data/qrv".$this->version."_".$this->ec.".dat";
461 $fp1 = fopen ($filename, "rb");
462 $this->matrix_x_array = unpack("C*", fread($fp1,$this->byte_num));
463 $this->matrix_y_array = unpack("C*", fread($fp1,$this->byte_num));
464 $this->mask_array = unpack("C*", fread($fp1,$this->byte_num));
465 $this->format_information_x2 = unpack("C*", fread($fp1,15));
466 $this->format_information_y2 = unpack("C*", fread($fp1,15));
467 $this->rs_ecc_codewords = ord(fread($fp1,1));
468 $this->rs_block_order = unpack("C*", fread($fp1,128));
469 fclose($fp1);
470 $this->format_information_x1 = array(0,1,2,3,4,5,7,8,8,8,8,8,8,8,8);
471 $this->format_information_y1 = array(8,8,8,8,8,8,8,8,7,5,4,3,2,1,0);
472
473 }
474
475 private function makeECC()
476 {
477 // lecture du fichier : data file of caluclatin tables for RS encoding
478 $rs_cal_table_array = array();
479 $filename = dirname(__FILE__)."/data/rsc".$this->rs_ecc_codewords.".dat";
480 $fp0 = fopen ($filename, "rb");
481 for($i=0; $i<256; $i++)
482 $rs_cal_table_array[$i]=fread ($fp0,$this->rs_ecc_codewords);
483 fclose ($fp0);
484
485 $max_data_codewords = count($this->data_word);
486
487 // preparation
488 $j=0;
489 $rs_block_number=0;
490 $rs_temp[0]="";
491 for($i=0; $i<$max_data_codewords; $i++)
492 {
493 $rs_temp[$rs_block_number].=chr($this->data_word[$i]);
494 $j++;
495 if ($j>=$this->rs_block_order[$rs_block_number+1]-$this->rs_ecc_codewords)
496 {
497 $j=0;
498 $rs_block_number++;
499 $rs_temp[$rs_block_number]="";
500 }
501 }
502
503 // make
504 $rs_block_order_num=count($this->rs_block_order);
505
506 for($rs_block_number=0; $rs_block_number<$rs_block_order_num; $rs_block_number++)
507 {
508 $rs_codewords=$this->rs_block_order[$rs_block_number+1];
509 $rs_data_codewords=$rs_codewords-$this->rs_ecc_codewords;
510
511 $rstemp=$rs_temp[$rs_block_number].str_repeat(chr(0),$this->rs_ecc_codewords);
512 $padding_data=str_repeat(chr(0),$rs_data_codewords);
513
514 $j=$rs_data_codewords;
515 while($j>0)
516 {
517 $first=ord(substr($rstemp,0,1));
518
519 if ($first)
520 {
521 $left_chr=substr($rstemp,1);
522 $cal=$rs_cal_table_array[$first].$padding_data;
523 $rstemp=$left_chr ^ $cal;
524 }
525 else
526 $rstemp=substr($rstemp,1);
527 $j--;
528 }
529
530 $this->data_word=array_merge($this->data_word,unpack("C*",$rstemp));
531 }
532 }
533
534 private function makeMatrix()
535 {
536 // preparation
537 $this->matrix = array_fill(0, $this->size, array_fill(0, $this->size, 0));
538
539 // mettre les words
540 for($i=0; $i<$this->max_word; $i++)
541 {
542 $word = $this->data_word[$i];
543 for($j=8; $j>0; $j--)
544 {
545 $bit_pos = ($i<<3) + $j;
546 $this->matrix[ $this->matrix_x_array[$bit_pos] ][ $this->matrix_y_array[$bit_pos] ] = ((255*($word & 1)) ^ $this->mask_array[$bit_pos] );
547 $word = $word >> 1;
548 }
549 }
550
551 for($k=$this->matrix_remain; $k>0; $k--)
552 {
553 $bit_pos = $k + ( $this->max_word <<3);
554 $this->matrix[ $this->matrix_x_array[$bit_pos] ][ $this->matrix_y_array[$bit_pos] ] = ( 255 ^ $this->mask_array[$bit_pos] );
555 }
556
557 // mask select
558 $min_demerit_score=0;
559 $hor_master="";
560 $ver_master="";
561 $k=0;
562 while($k<$this->size)
563 {
564 $l=0;
565 while($l<$this->size)
566 {
567 $hor_master=$hor_master.chr($this->matrix[$l][$k]);
568 $ver_master=$ver_master.chr($this->matrix[$k][$l]);
569 $l++;
570 }
571 $k++;
572 }
573
574 $i=0;
575 $all_matrix=$this->size * $this->size;
576
577 while ($i<8)
578 {
579 $demerit_n1=0;
580 $ptn_temp=array();
581 $bit= 1<< $i;
582 $bit_r=(~$bit)&255;
583 $bit_mask=str_repeat(chr($bit),$all_matrix);
584 $hor = $hor_master & $bit_mask;
585 $ver = $ver_master & $bit_mask;
586
587 $ver_shift1=$ver.str_repeat(chr(170),$this->size);
588 $ver_shift2=str_repeat(chr(170),$this->size).$ver;
589 $ver_shift1_0=$ver.str_repeat(chr(0),$this->size);
590 $ver_shift2_0=str_repeat(chr(0),$this->size).$ver;
591 $ver_or=chunk_split(~($ver_shift1 | $ver_shift2),$this->size,chr(170));
592 $ver_and=chunk_split(~($ver_shift1_0 & $ver_shift2_0),$this->size,chr(170));
593
594 $hor=chunk_split(~$hor,$this->size,chr(170));
595 $ver=chunk_split(~$ver,$this->size,chr(170));
596 $hor=$hor.chr(170).$ver;
597
598 $n1_search="/".str_repeat(chr(255),5)."+|".str_repeat(chr($bit_r),5)."+/";
599 $n3_search=chr($bit_r).chr(255).chr($bit_r).chr($bit_r).chr($bit_r).chr(255).chr($bit_r);
600
601 $demerit_n3=substr_count($hor,$n3_search)*40;
602 $demerit_n4=floor(abs(( (100* (substr_count($ver,chr($bit_r))/($this->byte_num)) )-50)/5))*10;
603
604 $n2_search1="/".chr($bit_r).chr($bit_r)."+/";
605 $n2_search2="/".chr(255).chr(255)."+/";
606 $demerit_n2=0;
607 preg_match_all($n2_search1,$ver_and,$ptn_temp);
608 foreach($ptn_temp[0] as $str_temp)
609 {
610 $demerit_n2+=(strlen($str_temp)-1);
611 }
612 $ptn_temp=array();
613 preg_match_all($n2_search2,$ver_or,$ptn_temp);
614 foreach($ptn_temp[0] as $str_temp)
615 {
616 $demerit_n2+=(strlen($str_temp)-1);
617 }
618 $demerit_n2*=3;
619
620 $ptn_temp=array();
621
622 preg_match_all($n1_search,$hor,$ptn_temp);
623 foreach($ptn_temp[0] as $str_temp)
624 {
625 $demerit_n1+=(strlen($str_temp)-2);
626 }
627 $demerit_score=$demerit_n1+$demerit_n2+$demerit_n3+$demerit_n4;
628
629 if ($demerit_score<=$min_demerit_score || $i==0)
630 {
631 $mask_number=$i;
632 $min_demerit_score=$demerit_score;
633 }
634
635 $i++;
636 }
637
638 $mask_content=1 << $mask_number;
639
640 $format_information_value=(($this->ec << 3) | $mask_number);
641 $format_information_array=array("101010000010010","101000100100101",
642 "101111001111100","101101101001011","100010111111001","100000011001110",
643 "100111110010111","100101010100000","111011111000100","111001011110011",
644 "111110110101010","111100010011101","110011000101111","110001100011000",
645 "110110001000001","110100101110110","001011010001001","001001110111110",
646 "001110011100111","001100111010000","000011101100010","000001001010101",
647 "000110100001100","000100000111011","011010101011111","011000001101000",
648 "011111100110001","011101000000110","010010010110100","010000110000011",
649 "010111011011010","010101111101101");
650
651 for($i=0; $i<15; $i++)
652 {
653 $content=substr($format_information_array[$format_information_value],$i,1);
654
655 $this->matrix[$this->format_information_x1[$i]][$this->format_information_y1[$i]]=$content * 255;
656 $this->matrix[$this->format_information_x2[$i+1]][$this->format_information_y2[$i+1]]=$content * 255;
657 }
658
659 $this->final = unpack("C*", file_get_contents(dirname(__FILE__).'/data/modele'.$this->version.'.dat'));
660 $this->qr_size = $this->size+8;
661
662 for($x=0; $x<$this->size; $x++)
663 {
664 for($y=0; $y<$this->size; $y++)
665 {
666 if ($this->matrix[$x][$y] & $mask_content)
667 $this->final[($x+4) + ($y+4)*$this->qr_size+1] = true;
668 }
669 }
670 }
671 }
672 }
673