Fix #8052 - fixing pdf
[pear] / XML / SvgToPdf.php
1 <?php
2
3 /* usage:
4      
5        *install Fpdf as a PEAR package by:
6         pear install http://www.akbkhome.com:81/svn/akpear/Fpdf/Fpdf-1.51.tgz
7      
8        
9         $data=array(
10             
11             'address' => array(
12                 array(
13                     'name' => = "Xxxxxxxx xxxxxxxxxxxx xxxxxxxxxx xxxxxxx Xxxxxxxx xxxxxxxxxxxx xxxxxxxxxx xxxxxxx";
14                 ),
15                 array(
16                     'name' => = "Xxxxxxxx xxxxxxxxxxxx xxxxxxxxxx xxxxxxx Xxxxxxxx xxxxxxxxxxxx xxxxxxxxxx xxxxxxx";
17                 ),
18                 array(
19                     'name' => = "Xxxxxxxx xxxxxxxxxxxx xxxxxxxxxx xxxxxxx Xxxxxxxx xxxxxxxxxxxx xxxxxxxxxx xxxxxxx";
20                 ),
21         );
22         $pdf = XML_SvgToPDF::construct(dirname(__FILE__).'/test.svg',$data);
23         
24         $pdf->output();
25         
26         
27         
28         expects an svg file (probably made by sodipodi)
29         a block is the group, 
30         a) it has a text component with
31             dynamic=address
32             rows=7
33             cols=3
34         b) a non-printable rectangle (which is the bounding box)
35         c) some text {xxxx}{yyyy} which is replaced with 
36             address[0....][xxxx] = 'somevalue;
37             address[0....][yyyy] = 'somevalue;
38         
39         
40         
41         
42 */
43
44
45 // current options for generated file..
46
47 $GLOBALS['_XML_SVGTOPDF']['options'] = array(
48     'debug' => 0,
49     );
50  
51         
52 class XML_SvgToPDF {
53
54     var $language;
55     
56     static function debug($s,$e=0) {
57         if (!$GLOBALS['_XML_SVGTOPDF']['options']['debug']) {
58             return;
59         }
60         echo "<PRE>".print_R($s,true). "</PRE>";
61         if ($e) { 
62             exit; 
63         }
64     }
65     
66     
67     /**
68      * 
69      * Static ! not sure why!?
70      * 
71      */
72     static function construct($svg, $data=array()) 
73     {  
74         if (is_object($data)) {
75             $data = (array) $data;
76         }
77       
78         $t = new XML_SvgToPDF;
79         
80         $t->language =  $data['language'];
81         require_once 'XML/Tree/Morph.php';
82
83         $x = new XML_Tree_Morph( 
84                     $svg,
85                     array(
86                        'debug' => 0,
87                        'filter' => array(
88                            'svg'    => array($t, 'buildObject'),
89                            'image'    => array($t, 'buildObject'),
90                            'text'    => array($t, 'buildObject'),
91                            'tspan'   => array($t, 'buildObject'),
92                            'rect'   => array($t, 'buildObject'),
93                            'g'   =>  array($t, 'buildObject'),
94                            'path'   =>  array($t, 'buildObject'),
95                            'sodipodi:namedview' =>  array($t, 'buildNull'),
96                            'defs' =>  array($t, 'buildNull'),
97                         )
98                     )
99                  );
100         
101         $tree = $x->getTreeFromFile();
102        //echo '<PRE>'; print_R($tree);      exit;
103         $tree = $t->buildobject($tree);
104        //   echo '<PRE>'; print_R($tree);      exit;
105          //echo "<PRE>";
106        // $tree = $t->parseSvg($svg);
107         // echo "<PRE>";print_r($tree);exit;
108         
109         
110         
111         
112         
113         //echo "<PRE>";print_r($tree);exit;
114         $w = empty($tree->width) ? 0 : $tree->width;
115         $h = empty($tree->height) ? 0 : $tree->height;
116         $orientation =  (preg_replace('/[^0-9.]+/','', $w)*1) > (preg_replace('/[^0-9.]+/','', $h)*1) ? 'L' : 'P';
117         //var_dump($orientation);exit;
118         $GLOBALS['_XML_SVGTOPDF']['options']['file'] = $svg;
119
120         if ($data['language'] == 'big5') {
121           //die("trying chinese");
122             
123                
124             require_once 'Fpdf/Unicode.php';
125
126             $pdf=new FPDF_Unicode($orientation ,'mm','A4');
127             $pdf->AddGBFont();
128             $pdf->AddBig5Font();
129             $pdf->AddUniCNShwFont(); 
130             $pdf->open();            
131
132          
133         } else {
134             require_once  'Fpdf/tFPDF.php' ;
135
136             $pdf=new tFPDF($orientation ,'mm','A4');
137             $pdf->open();
138         }
139
140         $pdf->setAutoPageBreak(false);
141         $pdf->AliasNbPages();
142         // convert data to array.
143         if (is_object($data)) {
144             $data = (array) $data;
145         }
146         // assoc. array of key => no of fields per page.
147          $perPage = $tree->calcPerPage();
148         //list($var,$perpage) = $tree->calcPerPage();
149         //if (empty($data) || !@$var || !@count($data[$var])) {
150 //         print_r("<PRE>");
151 //          print_r($data['transactions'][0]);
152 //          $data['transactions'][0]->desc = 'abcdefghijklmnopqrstuvwxyz Z';
153 //           print_r($data['transactions'][0]->desc);
154         // no dynamic blocks:
155          if (!$perPage || empty($data)) {
156             $pdf->addPage();
157             $tree->writePDF($pdf,$data);
158             $t->debug($tree);
159             return $pdf;
160         }
161         
162         // build blocks of data for each page.
163         $haveData = true;
164         $page = 0;
165         
166        //    $originalData = $data;
167         //$alldata = $data[$var];
168
169        //  while (count($alldata))  {
170         //print_r($perPage);exit;
171         
172         
173         
174          
175         while (true == $haveData ) {
176             $page_data = $data;
177             $haveData = false;
178             //print_r($perPage);
179             
180             // replaces the properties that have 'page data'
181             
182             
183             foreach($perPage as $k=>$v) {
184                 if (empty($data[$k])) {
185                     $page_data[$k] = array();
186                     continue;
187                 }
188                 $haveData = true;
189                 $page_data[$k] = self::fetchRows($data,$k,$v);
190                 
191                 
192                 //$page_data[$k] = array_splice ( $data[$k], 0,$v);
193             }
194             
195            
196              
197             if ($page && !$haveData) {
198                 break;
199             }
200             $page++;
201                 
202             $t->debug("<B>PAGE $page<B>");
203             
204             $pdf->addPage();
205
206             $tree->writePDF($pdf,$page_data);
207                 
208       
209             //$tree->writePDF($pdf,$data);
210         }
211        
212         $t->debug($tree);
213         return $pdf;
214     }
215     
216     static function fetchRows(&$original_data, $key, $rows) {
217         $ret = array();
218         while ($rows > -1 && !empty($original_data[$key])) {
219             $addrow = array_shift($original_data[$key]);
220             $rows -= !empty($addrow->userows) ? $addrow->userows : 1;
221             if ($rows < 0) {
222                 array_unshift($original_data[$key],$addrow);
223                 break;
224             }
225             $ret[] = $addrow;
226             
227         }
228         return $ret;
229         
230         
231     }
232     
233     
234     
235     function parseSvg($svgFileName)
236     {
237         libxml_use_internal_errors(true);
238         $d = new DOMDocument();
239         $d->load($svgFileName);
240        // print_r($d);
241         return $this->parseNode($d->documentElement);
242     }
243     
244     function parseXMLNode($n)
245     {
246         // do children first..
247         //print_r(array("PARSENODE:",$n));
248         if (empty($n)) {
249             return array();
250         }
251         $children = array();
252         if ($n->childNodes->length) {
253             foreach($n->childNodes as $cn) {
254                 if ($cn->nodeType != XML_ELEMENT_NODE) {
255                     continue;
256                 }
257                 $child = $this->parseNode($cn);
258                 if (is_array($child) && count($child)) {
259                     $children = array_merge($children, $child);
260                     continue;
261                 } 
262                 if (is_object($child)) {
263                     $children[] = $child;
264                 }
265                 continue;
266                 
267             }
268         }
269         if (!in_array($n->tagName, array('svg','image','text', 'tspan', 'rect', 'g', 'path'))) {
270             return $children;
271             
272         }
273         // fixme.. this is the Dom Version..
274         $ret = $this->buildObject($n,$children);
275         
276         return $ret;
277     }
278       
279     
280     
281     
282     
283     
284     function buildNull($node) {
285         return;
286     }
287     function buildObject($node )
288     {
289         require_once 'XML/SvgToPdf/Base.php';
290         
291         return XML_SvgToPDF_Base::factory($node);
292          
293     }
294     
295     
296
297
298 }