*** empty log message ***
[Packages/TYPO3.CMS.git] / t3lib / class.t3lib_syntaxhl.php
1 <?php
2 /***************************************************************
3 * Copyright notice
4 *
5 * (c) 1999-2003 Kasper Skaarhoj (kasper@typo3.com)
6 * All rights reserved
7 *
8 * This script is part of the TYPO3 project. The TYPO3 project is
9 * free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
13 *
14 * The GNU General Public License can be found at
15 * http://www.gnu.org/copyleft/gpl.html.
16 * A copy is found in the textfile GPL.txt and important notices to the license
17 * from the author is found in LICENSE.txt distributed with these scripts.
18 *
19 *
20 * This script is distributed in the hope that it will be useful,
21 * but WITHOUT ANY WARRANTY; without even the implied warranty of
22 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 * GNU General Public License for more details.
24 *
25 * This copyright notice MUST APPEAR in all copies of the script!
26 ***************************************************************/
27 /**
28 * Contains a class for various syntax highlighting.
29 *
30 * $Id$
31 *
32 * @author Kasper Skaarhoj <kasper@typo3.com>
33 */
34 /**
35 * [CLASS/FUNCTION INDEX of SCRIPT]
36 *
37 *
38 *
39 * 76: class t3lib_syntaxhl
40 * 109: function highLight_DS($str)
41 * 133: function getAllTags($str)
42 * 164: function splitXMLbyTags($tagList,$str)
43 * 192: function markUpRecursively($struct,$parent='',$app='')
44 *
45 * TOTAL FUNCTIONS: 4
46 * (This index is automatically created/updated by the extension "extdeveval")
47 *
48 */
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66 require_once(PATH_t3lib.'class.t3lib_parsehtml.php');
67
68
69 /**
70 * Syntax Highlighting class.
71 *
72 * @author Kasper Skaarhoj <kasper@typo3.com>
73 * @package TYPO3
74 * @subpackage t3lib
75 */
76 class t3lib_syntaxhl {
77
78 // Internal, dynamic:
79 var $htmlParse; // Parse object.
80
81 // External, static:
82 var $DS_wrapTags = array(
83 'T3DataStructure' => array('<span style="font-weight: bold;">','</span>'),
84 'type' => array('<span style="font-weight: bold; color: #000080;">','</span>'),
85 'section' => array('<span style="font-weight: bold; color: #000080;">','</span>'),
86 'el' => array('<span style="font-weight: bold; color: #800000;">','</span>'),
87 'meta' => array('<span style="font-weight: bold; color: #800080;">','</span>'),
88 '_unknown' => array('<span style="font-style: italic; color: #666666;">','</span>'),
89
90 '_applicationTag' => array('<span style="font-weight: bold; color: #FF6600;">','</span>'),
91 '_applicationContents' => array('<span style="font-style: italic; color: #C29336;">','</span>'),
92
93 'sheets' => array('<span style="font-weight: bold; color: #008000;">','</span>'),
94 'parent:sheets' => array('<span style="color: #008000;">','</span>'),
95
96 'ROOT' => array('<span style="font-weight: bold; color: #008080;">','</span>'),
97 'parent:el' => array('<span style="font-weight: bold; color: #008080;">','</span>'),
98
99 'langDisable' => array('<span style="color: #000080;">','</span>'),
100 'langChildren' => array('<span style="color: #000080;">','</span>'),
101 );
102
103 var $FF_wrapTags = array(
104 'T3FlexForms' => array('<span style="font-weight: bold;">','</span>'),
105 'meta' => array('<span style="font-weight: bold; color: #800080;">','</span>'),
106 'data' => array('<span style="font-weight: bold; color: #800080;">','</span>'),
107 '_unknown' => array('<span style="font-style: italic; color: #666666;">','</span>'),
108
109
110 'sDEF' => array('<span style="font-weight: bold; color: #008000;">','</span>'),
111 'level:sheet' => array('<span style="font-weight: bold; color: #008000;">','</span>'),
112
113 'lDEF' => array('<span style="font-weight: bold; color: #000080;">','</span>'),
114 'level:language' => array('<span style="font-weight: bold; color: #000080;">','</span>'),
115
116 'level:fieldname' => array('<span style="font-weight: bold; color: #666666;">','</span>'),
117
118 'vDEF' => array('<span style="font-weight: bold; color: #800000;">','</span>'),
119 'level:value' => array('<span style="font-weight: bold; color: #800000;">','</span>'),
120
121 'currentSheetId' => array('<span style="color: #000080;">','</span>'),
122 'currentLangId' => array('<span style="color: #000080;">','</span>'),
123 );
124
125
126
127
128
129
130
131
132 /*************************************
133 *
134 * Markup of Data Structure, <T3DataStructure>
135 *
136 *************************************/
137
138 /**
139 * Makes syntax highlighting of a Data Structure, <T3DataStructure>
140 *
141 * @param string Data Structure XML, must be valid since it's parsed.
142 * @return string HTML code with highlighted content. Must be wrapped in <PRE> tags
143 */
144 function highLight_DS($str) {
145
146 // Parse DS to verify that it is valid:
147 $DS = t3lib_div::xml2array($str);
148 if (is_array($DS)) {
149 $completeTagList = array_unique($this->getAllTags($str)); // Complete list of tags in DS
150
151 // Highlighting source:
152 $this->htmlParse = t3lib_div::makeInstance('t3lib_parsehtml'); // Init parser object
153 $struct = $this->splitXMLbyTags(implode(',',$completeTagList),$str); // Split the XML by the found tags, recursively into LARGE array.
154 $markUp = $this->highLight_DS_markUpRecursively($struct); // Perform color-markup on the parsed content. Markup preserves the LINE formatting of the XML.
155
156 // Return content:
157 return $markUp;
158 } else $error = 'ERROR: The input content failed XML parsing: '.$DS;
159 return $error;
160 }
161
162 /**
163 * Making syntax highlighting of the parsed Data Structure XML.
164 * Called recursively.
165 *
166 * @param array The structure, see splitXMLbyTags()
167 * @param string Parent tag.
168 * @param string "Application" - used to denote if we are 'inside' a section
169 * @return string HTML
170 */
171 function highLight_DS_markUpRecursively($struct,$parent='',$app='') {
172 $output='';
173 foreach($struct as $k => $v) {
174 if ($k%2) {
175 $nextApp = $app;
176 $wrap = array('','');
177
178 switch($app) {
179 case 'TCEforms':
180 case 'tx_templavoila':
181 $wrap = $this->DS_wrapTags['_applicationContents'];
182 break;
183 case 'el':
184 default:
185 if ($parent=='el') {
186 $wrap = $this->DS_wrapTags['parent:el'];
187 $nextApp = 'el';
188 } elseif ($parent=='sheets') {
189 $wrap = $this->DS_wrapTags['parent:sheets'];
190 } else {
191 $wrap = $this->DS_wrapTags[$v['tagName']];
192 $nextApp = '';
193 }
194
195 // If no wrap defined, us "unknown" definition
196 if (!is_array($wrap)) {
197 $wrap = $this->DS_wrapTags['_unknown'];
198 }
199
200 // Check for application sections in the XML:
201 if ($app=='el' || $parent=='ROOT') {
202 switch($v['tagName']) {
203 case 'TCEforms':
204 case 'tx_templavoila':
205 $nextApp = $v['tagName'];
206 $wrap = $this->DS_wrapTags['_applicationTag'];
207 break;
208 }
209 }
210 break;
211 }
212
213 $output.=$wrap[0].htmlspecialchars($v['tag']).$wrap[1];
214 $output.=$this->highLight_DS_markUpRecursively($v['sub'],$v['tagName'],$nextApp);
215 $output.=$wrap[0].htmlspecialchars('</'.$v['tagName'].'>').$wrap[1];
216 } else {
217 $output.=htmlspecialchars($v);
218 }
219 }
220
221 return $output;
222 }
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244 /*************************************
245 *
246 * Markup of Data Structure, <T3FlexForms>
247 *
248 *************************************/
249
250 /**
251 * Makes syntax highlighting of a FlexForm Data, <T3FlexForms>
252 *
253 * @param string Data Structure XML, must be valid since it's parsed.
254 * @return string HTML code with highlighted content. Must be wrapped in <PRE> tags
255 */
256 function highLight_FF($str) {
257
258 // Parse DS to verify that it is valid:
259 $DS = t3lib_div::xml2array($str);
260 if (is_array($DS)) {
261 $completeTagList = array_unique($this->getAllTags($str)); // Complete list of tags in DS
262
263 // Highlighting source:
264 $this->htmlParse = t3lib_div::makeInstance('t3lib_parsehtml'); // Init parser object
265 $struct = $this->splitXMLbyTags(implode(',',$completeTagList),$str); // Split the XML by the found tags, recursively into LARGE array.
266 $markUp = $this->highLight_FF_markUpRecursively($struct); // Perform color-markup on the parsed content. Markup preserves the LINE formatting of the XML.
267
268 // Return content:
269 return $markUp;
270 } else $error = 'ERROR: The input content failed XML parsing: '.$DS;
271 return $error;
272 }
273
274 /**
275 * Making syntax highlighting of the parsed FlexForm XML.
276 * Called recursively.
277 *
278 * @param array The structure, see splitXMLbyTags()
279 * @param string Parent tag.
280 * @param string "Application" - used to denote if we are 'inside' a section
281 * @return string HTML
282 */
283 function highLight_FF_markUpRecursively($struct,$parent='',$app='') {
284 $output='';
285
286 // Setting levels:
287 if ($parent=='data') {
288 $app='sheet';
289 } elseif($app=='sheet') {
290 $app='language';
291 } elseif($app=='language') {
292 $app='fieldname';
293 } elseif($app=='fieldname') {
294 $app='value';
295 }
296
297 // Traverse structure:
298 foreach($struct as $k => $v) {
299 if ($k%2) {
300 $wrap = array('','');
301
302 // Default wrap:
303 $wrap = $this->FF_wrapTags[$v['tagName']];
304
305 // If no wrap defined, us "unknown" definition
306 if (!is_array($wrap)) {
307 switch($app) {
308 case 'sheet':
309 case 'language':
310 case 'fieldname':
311 case 'value':
312 $wrap = $this->FF_wrapTags['level:'.$app];
313 break;
314 default:
315 $wrap = $this->FF_wrapTags['_unknown'];
316 break;
317 }
318 }
319
320 $output.=$wrap[0].htmlspecialchars($v['tag']).$wrap[1];
321 $output.=$this->highLight_FF_markUpRecursively($v['sub'],$v['tagName'],$app);
322 $output.=$wrap[0].htmlspecialchars('</'.$v['tagName'].'>').$wrap[1];
323 } else {
324 $output.=htmlspecialchars($v);
325 }
326 }
327
328 return $output;
329 }
330
331
332
333
334
335
336
337
338
339
340
341
342 /*************************************
343 *
344 * Various
345 *
346 *************************************/
347
348 /**
349 * Returning all tag names found in XML/HTML input string
350 *
351 * @param string HTML/XML input
352 * @return array Array with all found tags (starttags only)
353 */
354 function getAllTags($str) {
355
356 // Init:
357 $tags = array();
358 $token = md5(microtime());
359
360 // Markup all tag names with token.
361 $markUpStr = ereg_replace('<([[:alnum:]_]+)[^>]*>',$token.'\1'.$token,$str);
362
363 // Splitting by token:
364 $parts = explode($token,$markUpStr);
365
366 // Traversing parts:
367 foreach($parts as $k => $v) {
368 if ($k%2) {
369 $tags[]=$v;
370 }
371 }
372
373 // Returning tags:
374 return $tags;
375 }
376
377 /**
378 * Splitting the input source by the tags listing in $tagList.
379 * Called recursively.
380 *
381 * @param string Commalist of tags to split source by (into blocks, ALL being block-tags!)
382 * @param string Input string.
383 * @return array Array with the content arranged hierarchically.
384 */
385 function splitXMLbyTags($tagList,$str) {
386 $struct = $this->htmlParse->splitIntoBlock($tagList,$str);
387
388 // Traverse level:
389 foreach($struct as $k => $v) {
390 if ($k%2) {
391 $tag = $this->htmlParse->getFirstTag($v);
392 $tagName = $this->htmlParse->getFirstTagName($tag,TRUE);
393 $struct[$k] = array(
394 'tag' => $tag,
395 'tagName' => $tagName,
396 'sub' => $this->splitXMLbyTags($tagList,$this->htmlParse->removeFirstAndLastTag($struct[$k]))
397 );
398 }
399 }
400
401 return $struct;
402 }
403 }
404
405
406 if (defined('TYPO3_MODE') && $TYPO3_CONF_VARS[TYPO3_MODE]['XCLASS']['t3lib/class.t3lib_syntaxhl.php']) {
407 include_once($TYPO3_CONF_VARS[TYPO3_MODE]['XCLASS']['t3lib/class.t3lib_syntaxhl.php']);
408 }
409 ?>