MDL-67115 htmlpurifier: php74 params order for implode()
[moodle.git] / lib / htmlpurifier / HTMLPurifier / Printer / HTMLDefinition.php
CommitLineData
e80855b0
MG
1<?php\r
2\r
3class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer\r
4{\r
5\r
6 /**\r
7 * @type HTMLPurifier_HTMLDefinition, for easy access\r
8 */\r
9 protected $def;\r
10\r
11 /**\r
12 * @param HTMLPurifier_Config $config\r
13 * @return string\r
14 */\r
15 public function render($config)\r
16 {\r
17 $ret = '';\r
18 $this->config =& $config;\r
19\r
20 $this->def = $config->getHTMLDefinition();\r
21\r
22 $ret .= $this->start('div', array('class' => 'HTMLPurifier_Printer'));\r
23\r
24 $ret .= $this->renderDoctype();\r
25 $ret .= $this->renderEnvironment();\r
26 $ret .= $this->renderContentSets();\r
27 $ret .= $this->renderInfo();\r
28\r
29 $ret .= $this->end('div');\r
30\r
31 return $ret;\r
32 }\r
33\r
34 /**\r
35 * Renders the Doctype table\r
36 * @return string\r
37 */\r
38 protected function renderDoctype()\r
39 {\r
40 $doctype = $this->def->doctype;\r
41 $ret = '';\r
42 $ret .= $this->start('table');\r
43 $ret .= $this->element('caption', 'Doctype');\r
44 $ret .= $this->row('Name', $doctype->name);\r
45 $ret .= $this->row('XML', $doctype->xml ? 'Yes' : 'No');\r
9cdbacf3
EL
46 $ret .= $this->row('Default Modules', implode(', ', $doctype->modules));\r
47 $ret .= $this->row('Default Tidy Modules', implode(', ', $doctype->tidyModules));\r
e80855b0
MG
48 $ret .= $this->end('table');\r
49 return $ret;\r
50 }\r
51\r
52\r
53 /**\r
54 * Renders environment table, which is miscellaneous info\r
55 * @return string\r
56 */\r
57 protected function renderEnvironment()\r
58 {\r
59 $def = $this->def;\r
60\r
61 $ret = '';\r
62\r
63 $ret .= $this->start('table');\r
64 $ret .= $this->element('caption', 'Environment');\r
65\r
66 $ret .= $this->row('Parent of fragment', $def->info_parent);\r
67 $ret .= $this->renderChildren($def->info_parent_def->child);\r
68 $ret .= $this->row('Block wrap name', $def->info_block_wrapper);\r
69\r
70 $ret .= $this->start('tr');\r
71 $ret .= $this->element('th', 'Global attributes');\r
72 $ret .= $this->element('td', $this->listifyAttr($def->info_global_attr), null, 0);\r
73 $ret .= $this->end('tr');\r
74\r
75 $ret .= $this->start('tr');\r
76 $ret .= $this->element('th', 'Tag transforms');\r
77 $list = array();\r
78 foreach ($def->info_tag_transform as $old => $new) {\r
79 $new = $this->getClass($new, 'TagTransform_');\r
80 $list[] = "<$old> with $new";\r
81 }\r
82 $ret .= $this->element('td', $this->listify($list));\r
83 $ret .= $this->end('tr');\r
84\r
85 $ret .= $this->start('tr');\r
86 $ret .= $this->element('th', 'Pre-AttrTransform');\r
87 $ret .= $this->element('td', $this->listifyObjectList($def->info_attr_transform_pre));\r
88 $ret .= $this->end('tr');\r
89\r
90 $ret .= $this->start('tr');\r
91 $ret .= $this->element('th', 'Post-AttrTransform');\r
92 $ret .= $this->element('td', $this->listifyObjectList($def->info_attr_transform_post));\r
93 $ret .= $this->end('tr');\r
94\r
95 $ret .= $this->end('table');\r
96 return $ret;\r
97 }\r
98\r
99 /**\r
100 * Renders the Content Sets table\r
101 * @return string\r
102 */\r
103 protected function renderContentSets()\r
104 {\r
105 $ret = '';\r
106 $ret .= $this->start('table');\r
107 $ret .= $this->element('caption', 'Content Sets');\r
108 foreach ($this->def->info_content_sets as $name => $lookup) {\r
109 $ret .= $this->heavyHeader($name);\r
110 $ret .= $this->start('tr');\r
111 $ret .= $this->element('td', $this->listifyTagLookup($lookup));\r
112 $ret .= $this->end('tr');\r
113 }\r
114 $ret .= $this->end('table');\r
115 return $ret;\r
116 }\r
117\r
118 /**\r
119 * Renders the Elements ($info) table\r
120 * @return string\r
121 */\r
122 protected function renderInfo()\r
123 {\r
124 $ret = '';\r
125 $ret .= $this->start('table');\r
126 $ret .= $this->element('caption', 'Elements ($info)');\r
127 ksort($this->def->info);\r
128 $ret .= $this->heavyHeader('Allowed tags', 2);\r
129 $ret .= $this->start('tr');\r
130 $ret .= $this->element('td', $this->listifyTagLookup($this->def->info), array('colspan' => 2));\r
131 $ret .= $this->end('tr');\r
132 foreach ($this->def->info as $name => $def) {\r
133 $ret .= $this->start('tr');\r
134 $ret .= $this->element('th', "<$name>", array('class' => 'heavy', 'colspan' => 2));\r
135 $ret .= $this->end('tr');\r
136 $ret .= $this->start('tr');\r
137 $ret .= $this->element('th', 'Inline content');\r
138 $ret .= $this->element('td', $def->descendants_are_inline ? 'Yes' : 'No');\r
139 $ret .= $this->end('tr');\r
140 if (!empty($def->excludes)) {\r
141 $ret .= $this->start('tr');\r
142 $ret .= $this->element('th', 'Excludes');\r
143 $ret .= $this->element('td', $this->listifyTagLookup($def->excludes));\r
144 $ret .= $this->end('tr');\r
145 }\r
146 if (!empty($def->attr_transform_pre)) {\r
147 $ret .= $this->start('tr');\r
148 $ret .= $this->element('th', 'Pre-AttrTransform');\r
149 $ret .= $this->element('td', $this->listifyObjectList($def->attr_transform_pre));\r
150 $ret .= $this->end('tr');\r
151 }\r
152 if (!empty($def->attr_transform_post)) {\r
153 $ret .= $this->start('tr');\r
154 $ret .= $this->element('th', 'Post-AttrTransform');\r
155 $ret .= $this->element('td', $this->listifyObjectList($def->attr_transform_post));\r
156 $ret .= $this->end('tr');\r
157 }\r
158 if (!empty($def->auto_close)) {\r
159 $ret .= $this->start('tr');\r
160 $ret .= $this->element('th', 'Auto closed by');\r
161 $ret .= $this->element('td', $this->listifyTagLookup($def->auto_close));\r
162 $ret .= $this->end('tr');\r
163 }\r
164 $ret .= $this->start('tr');\r
165 $ret .= $this->element('th', 'Allowed attributes');\r
166 $ret .= $this->element('td', $this->listifyAttr($def->attr), array(), 0);\r
167 $ret .= $this->end('tr');\r
168\r
169 if (!empty($def->required_attr)) {\r
170 $ret .= $this->row('Required attributes', $this->listify($def->required_attr));\r
171 }\r
172\r
173 $ret .= $this->renderChildren($def->child);\r
174 }\r
175 $ret .= $this->end('table');\r
176 return $ret;\r
177 }\r
178\r
179 /**\r
180 * Renders a row describing the allowed children of an element\r
181 * @param HTMLPurifier_ChildDef $def HTMLPurifier_ChildDef of pertinent element\r
182 * @return string\r
183 */\r
184 protected function renderChildren($def)\r
185 {\r
186 $context = new HTMLPurifier_Context();\r
187 $ret = '';\r
188 $ret .= $this->start('tr');\r
189 $elements = array();\r
190 $attr = array();\r
191 if (isset($def->elements)) {\r
192 if ($def->type == 'strictblockquote') {\r
193 $def->validateChildren(array(), $this->config, $context);\r
194 }\r
195 $elements = $def->elements;\r
196 }\r
197 if ($def->type == 'chameleon') {\r
198 $attr['rowspan'] = 2;\r
199 } elseif ($def->type == 'empty') {\r
200 $elements = array();\r
201 } elseif ($def->type == 'table') {\r
202 $elements = array_flip(\r
203 array(\r
204 'col',\r
205 'caption',\r
206 'colgroup',\r
207 'thead',\r
208 'tfoot',\r
209 'tbody',\r
210 'tr'\r
211 )\r
212 );\r
213 }\r
214 $ret .= $this->element('th', 'Allowed children', $attr);\r
215\r
216 if ($def->type == 'chameleon') {\r
217\r
218 $ret .= $this->element(\r
219 'td',\r
220 '<em>Block</em>: ' .\r
221 $this->escape($this->listifyTagLookup($def->block->elements)),\r
222 null,\r
223 0\r
224 );\r
225 $ret .= $this->end('tr');\r
226 $ret .= $this->start('tr');\r
227 $ret .= $this->element(\r
228 'td',\r
229 '<em>Inline</em>: ' .\r
230 $this->escape($this->listifyTagLookup($def->inline->elements)),\r
231 null,\r
232 0\r
233 );\r
234\r
235 } elseif ($def->type == 'custom') {\r
236\r
237 $ret .= $this->element(\r
238 'td',\r
239 '<em>' . ucfirst($def->type) . '</em>: ' .\r
240 $def->dtd_regex\r
241 );\r
242\r
243 } else {\r
244 $ret .= $this->element(\r
245 'td',\r
246 '<em>' . ucfirst($def->type) . '</em>: ' .\r
247 $this->escape($this->listifyTagLookup($elements)),\r
248 null,\r
249 0\r
250 );\r
251 }\r
252 $ret .= $this->end('tr');\r
253 return $ret;\r
254 }\r
255\r
256 /**\r
257 * Listifies a tag lookup table.\r
258 * @param array $array Tag lookup array in form of array('tagname' => true)\r
259 * @return string\r
260 */\r
261 protected function listifyTagLookup($array)\r
262 {\r
263 ksort($array);\r
264 $list = array();\r
265 foreach ($array as $name => $discard) {\r
266 if ($name !== '#PCDATA' && !isset($this->def->info[$name])) {\r
267 continue;\r
268 }\r
269 $list[] = $name;\r
270 }\r
271 return $this->listify($list);\r
272 }\r
273\r
274 /**\r
275 * Listifies a list of objects by retrieving class names and internal state\r
276 * @param array $array List of objects\r
277 * @return string\r
278 * @todo Also add information about internal state\r
279 */\r
280 protected function listifyObjectList($array)\r
281 {\r
282 ksort($array);\r
283 $list = array();\r
284 foreach ($array as $obj) {\r
285 $list[] = $this->getClass($obj, 'AttrTransform_');\r
286 }\r
287 return $this->listify($list);\r
288 }\r
289\r
290 /**\r
291 * Listifies a hash of attributes to AttrDef classes\r
292 * @param array $array Array hash in form of array('attrname' => HTMLPurifier_AttrDef)\r
293 * @return string\r
294 */\r
295 protected function listifyAttr($array)\r
296 {\r
297 ksort($array);\r
298 $list = array();\r
299 foreach ($array as $name => $obj) {\r
300 if ($obj === false) {\r
301 continue;\r
302 }\r
303 $list[] = "$name&nbsp;=&nbsp;<i>" . $this->getClass($obj, 'AttrDef_') . '</i>';\r
304 }\r
305 return $this->listify($list);\r
306 }\r
307\r
308 /**\r
309 * Creates a heavy header row\r
310 * @param string $text\r
311 * @param int $num\r
312 * @return string\r
313 */\r
314 protected function heavyHeader($text, $num = 1)\r
315 {\r
316 $ret = '';\r
317 $ret .= $this->start('tr');\r
318 $ret .= $this->element('th', $text, array('colspan' => $num, 'class' => 'heavy'));\r
319 $ret .= $this->end('tr');\r
320 return $ret;\r
321 }\r
322}\r
323\r
324// vim: et sw=4 sts=4\r