3 // common defs that we'll support by default
4 require_once 'HTMLPurifier/ChildDef.php';
5 require_once 'HTMLPurifier/ChildDef/Empty.php';
6 require_once 'HTMLPurifier/ChildDef/Required.php';
7 require_once 'HTMLPurifier/ChildDef/Optional.php';
8 require_once 'HTMLPurifier/ChildDef/Custom.php';
12 class HTMLPurifier_ContentSets
16 * List of content set strings (pipe seperators) indexed by name.
22 * List of content set lookups (element => true) indexed by name.
23 * @note This is in HTMLPurifier_HTMLDefinition->info_content_sets
26 var $lookup = array();
29 * Synchronized list of defined content sets (keys of info)
33 * Synchronized list of defined content values (values of info)
35 var $values = array();
38 * Merges in module's content sets, expands identifiers in the content
39 * sets and populates the keys, values and lookup member variables.
40 * @param $modules List of HTMLPurifier_HTMLModule
42 function HTMLPurifier_ContentSets($modules) {
43 if (!is_array($modules)) $modules = array($modules);
44 // populate content_sets based on module hints
45 // sorry, no way of overloading
46 foreach ($modules as $module_i => $module) {
47 foreach ($module->content_sets
as $key => $value) {
48 if (isset($this->info
[$key])) {
49 // add it into the existing content set
50 $this->info
[$key] = $this->info
[$key] . ' | ' . $value;
52 $this->info
[$key] = $value;
56 // perform content_set expansions
57 $this->keys
= array_keys($this->info
);
58 foreach ($this->info
as $i => $set) {
59 // only performed once, so infinite recursion is not
64 // must be recalculated each time due to
65 // changing substitutions
66 array_values($this->info
),
69 $this->values
= array_values($this->info
);
71 // generate lookup tables
72 foreach ($this->info
as $name => $set) {
73 $this->lookup
[$name] = $this->convertToLookup($set);
78 * Accepts a definition; generates and assigns a ChildDef for it
79 * @param $def HTMLPurifier_ElementDef reference
80 * @param $module Module that defined the ElementDef
82 function generateChildDef(&$def, $module) {
83 if (!empty($def->child
)) return; // already done!
84 $content_model = $def->content_model
;
85 if (is_string($content_model)) {
86 $def->content_model
= str_replace(
87 $this->keys
, $this->values
, $content_model);
89 $def->child
= $this->getChildDef($def, $module);
93 * Instantiates a ChildDef based on content_model and content_model_type
94 * member variables in HTMLPurifier_ElementDef
95 * @note This will also defer to modules for custom HTMLPurifier_ChildDef
96 * subclasses that need content set expansion
97 * @param $def HTMLPurifier_ElementDef to have ChildDef extracted
98 * @return HTMLPurifier_ChildDef corresponding to ElementDef
100 function getChildDef($def, $module) {
101 $value = $def->content_model
;
102 if (is_object($value)) {
104 'Literal object child definitions should be stored in '.
105 'ElementDef->child not ElementDef->content_model',
110 switch ($def->content_model_type
) {
112 return new HTMLPurifier_ChildDef_Required($value);
114 return new HTMLPurifier_ChildDef_Optional($value);
116 return new HTMLPurifier_ChildDef_Empty();
118 return new HTMLPurifier_ChildDef_Custom($value);
120 // defer to its module
122 if ($module->defines_child_def
) { // save a func call
123 $return = $module->getChildDef($def);
125 if ($return !== false) return $return;
128 'Could not determine which ChildDef class to instantiate',
135 * Converts a string list of elements separated by pipes into
137 * @param $string List of elements
138 * @return Lookup array of elements
140 function convertToLookup($string) {
141 $array = explode('|', str_replace(' ', '', $string));
143 foreach ($array as $i => $k) {