[ Index ] |
PHP Cross Reference of vtigercrm-6.1.0 |
[Summary view] [Print] [Text view]
1 <?php 2 3 /** 4 * Generates HTML from tokens. 5 * @todo Refactor interface so that configuration/context is determined 6 * upon instantiation, no need for messy generateFromTokens() calls 7 * @todo Make some of the more internal functions protected, and have 8 * unit tests work around that 9 */ 10 class HTMLPurifier_Generator 11 { 12 13 /** 14 * Whether or not generator should produce XML output 15 */ 16 private $_xhtml = true; 17 18 /** 19 * :HACK: Whether or not generator should comment the insides of <script> tags 20 */ 21 private $_scriptFix = false; 22 23 /** 24 * Cache of HTMLDefinition during HTML output to determine whether or 25 * not attributes should be minimized. 26 */ 27 private $_def; 28 29 /** 30 * Cache of %Output.SortAttr 31 */ 32 private $_sortAttr; 33 34 /** 35 * Configuration for the generator 36 */ 37 protected $config; 38 39 /** 40 * @param $config Instance of HTMLPurifier_Config 41 * @param $context Instance of HTMLPurifier_Context 42 */ 43 public function __construct($config, $context) { 44 $this->config = $config; 45 $this->_scriptFix = $config->get('Output', 'CommentScriptContents'); 46 $this->_sortAttr = $config->get('Output', 'SortAttr'); 47 $this->_def = $config->getHTMLDefinition(); 48 $this->_xhtml = $this->_def->doctype->xml; 49 } 50 51 /** 52 * Generates HTML from an array of tokens. 53 * @param $tokens Array of HTMLPurifier_Token 54 * @param $config HTMLPurifier_Config object 55 * @return Generated HTML 56 */ 57 public function generateFromTokens($tokens) { 58 if (!$tokens) return ''; 59 60 // Basic algorithm 61 $html = ''; 62 for ($i = 0, $size = count($tokens); $i < $size; $i++) { 63 if ($this->_scriptFix && $tokens[$i]->name === 'script' 64 && $i + 2 < $size && $tokens[$i+2] instanceof HTMLPurifier_Token_End) { 65 // script special case 66 // the contents of the script block must be ONE token 67 // for this to work. 68 $html .= $this->generateFromToken($tokens[$i++]); 69 $html .= $this->generateScriptFromToken($tokens[$i++]); 70 } 71 $html .= $this->generateFromToken($tokens[$i]); 72 } 73 74 // Tidy cleanup 75 if (extension_loaded('tidy') && $this->config->get('Output', 'TidyFormat')) { 76 $tidy = new Tidy; 77 $tidy->parseString($html, array( 78 'indent'=> true, 79 'output-xhtml' => $this->_xhtml, 80 'show-body-only' => true, 81 'indent-spaces' => 2, 82 'wrap' => 68, 83 ), 'utf8'); 84 $tidy->cleanRepair(); 85 $html = (string) $tidy; // explicit cast necessary 86 } 87 88 // Normalize newlines to system defined value 89 $nl = $this->config->get('Output', 'Newline'); 90 if ($nl === null) $nl = PHP_EOL; 91 if ($nl !== "\n") $html = str_replace("\n", $nl, $html); 92 return $html; 93 } 94 95 /** 96 * Generates HTML from a single token. 97 * @param $token HTMLPurifier_Token object. 98 * @return Generated HTML 99 */ 100 public function generateFromToken($token) { 101 if (!$token instanceof HTMLPurifier_Token) { 102 trigger_error('Cannot generate HTML from non-HTMLPurifier_Token object', E_USER_WARNING); 103 return ''; 104 105 } elseif ($token instanceof HTMLPurifier_Token_Start) { 106 $attr = $this->generateAttributes($token->attr, $token->name); 107 return '<' . $token->name . ($attr ? ' ' : '') . $attr . '>'; 108 109 } elseif ($token instanceof HTMLPurifier_Token_End) { 110 return '</' . $token->name . '>'; 111 112 } elseif ($token instanceof HTMLPurifier_Token_Empty) { 113 $attr = $this->generateAttributes($token->attr, $token->name); 114 return '<' . $token->name . ($attr ? ' ' : '') . $attr . 115 ( $this->_xhtml ? ' /': '' ) // <br /> v. <br> 116 . '>'; 117 118 } elseif ($token instanceof HTMLPurifier_Token_Text) { 119 return $this->escape($token->data, ENT_NOQUOTES); 120 121 } elseif ($token instanceof HTMLPurifier_Token_Comment) { 122 return '<!--' . $token->data . '-->'; 123 } else { 124 return ''; 125 126 } 127 } 128 129 /** 130 * Special case processor for the contents of script tags 131 * @warning This runs into problems if there's already a literal 132 * --> somewhere inside the script contents. 133 */ 134 public function generateScriptFromToken($token) { 135 if (!$token instanceof HTMLPurifier_Token_Text) return $this->generateFromToken($token); 136 // Thanks <http://lachy.id.au/log/2005/05/script-comments> 137 $data = preg_replace('#//\s*$#', '', $token->data); 138 return '<!--//--><![CDATA[//><!--' . "\n" . trim($data) . "\n" . '//--><!]]>'; 139 } 140 141 /** 142 * Generates attribute declarations from attribute array. 143 * @note This does not include the leading or trailing space. 144 * @param $assoc_array_of_attributes Attribute array 145 * @param $element Name of element attributes are for, used to check 146 * attribute minimization. 147 * @return Generate HTML fragment for insertion. 148 */ 149 public function generateAttributes($assoc_array_of_attributes, $element = false) { 150 $html = ''; 151 if ($this->_sortAttr) ksort($assoc_array_of_attributes); 152 foreach ($assoc_array_of_attributes as $key => $value) { 153 if (!$this->_xhtml) { 154 // Remove namespaced attributes 155 if (strpos($key, ':') !== false) continue; 156 // Check if we should minimize the attribute: val="val" -> val 157 if ($element && !empty($this->_def->info[$element]->attr[$key]->minimized)) { 158 $html .= $key . ' '; 159 continue; 160 } 161 } 162 $html .= $key.'="'.$this->escape($value).'" '; 163 } 164 return rtrim($html); 165 } 166 167 /** 168 * Escapes raw text data. 169 * @todo This really ought to be protected, but until we have a facility 170 * for properly generating HTML here w/o using tokens, it stays 171 * public. 172 * @param $string String data to escape for HTML. 173 * @param $quote Quoting style, like htmlspecialchars. ENT_NOQUOTES is 174 * permissible for non-attribute output. 175 * @return String escaped data. 176 */ 177 public function escape($string, $quote = ENT_COMPAT) { 178 return htmlspecialchars($string, $quote, 'UTF-8'); 179 } 180 181 } 182 183 // vim: et sw=4 sts=4
title
Description
Body
title
Description
Body
title
Description
Body
title
Body
Generated: Fri Nov 28 20:08:37 2014 | Cross-referenced by PHPXref 0.7.1 |