friendship ended with social-app. php is my new best friend
1<?php 2 3namespace Masterminds\HTML5\Serializer; 4 5/** 6 * Traverser for walking a DOM tree. 7 * 8 * This is a concrete traverser designed to convert a DOM tree into an 9 * HTML5 document. It is not intended to be a generic DOMTreeWalker 10 * implementation. 11 * 12 * @see http://www.w3.org/TR/2012/CR-html5-20121217/syntax.html#serializing-html-fragments 13 */ 14class Traverser 15{ 16 /** 17 * Namespaces that should be treated as "local" to HTML5. 18 */ 19 protected static $local_ns = array( 20 'http://www.w3.org/1999/xhtml' => 'html', 21 'http://www.w3.org/1998/Math/MathML' => 'math', 22 'http://www.w3.org/2000/svg' => 'svg', 23 ); 24 25 protected $dom; 26 27 protected $options; 28 29 protected $encode = false; 30 31 protected $rules; 32 33 protected $out; 34 35 /** 36 * Create a traverser. 37 * 38 * @param \DOMNode|\DOMNodeList $dom The document or node to traverse. 39 * @param resource $out A stream that allows writing. The traverser will output into this 40 * stream. 41 * @param array $options An array of options for the traverser as key/value pairs. These include: 42 * - encode_entities: A bool to specify if full encding should happen for all named 43 * charachter references. Defaults to false which escapes &'<>". 44 * - output_rules: The path to the class handling the output rules. 45 */ 46 public function __construct($dom, $out, RulesInterface $rules, $options = array()) 47 { 48 $this->dom = $dom; 49 $this->out = $out; 50 $this->rules = $rules; 51 $this->options = $options; 52 53 $this->rules->setTraverser($this); 54 } 55 56 /** 57 * Tell the traverser to walk the DOM. 58 * 59 * @return resource $out Returns the output stream. 60 */ 61 public function walk() 62 { 63 if ($this->dom instanceof \DOMDocument) { 64 $this->rules->document($this->dom); 65 } elseif ($this->dom instanceof \DOMDocumentFragment) { 66 // Document fragments are a special case. Only the children need to 67 // be serialized. 68 if ($this->dom->hasChildNodes()) { 69 $this->children($this->dom->childNodes); 70 } 71 } // If NodeList, loop 72 elseif ($this->dom instanceof \DOMNodeList) { 73 // If this is a NodeList of DOMDocuments this will not work. 74 $this->children($this->dom); 75 } // Else assume this is a DOMNode-like datastructure. 76 else { 77 $this->node($this->dom); 78 } 79 80 return $this->out; 81 } 82 83 /** 84 * Process a node in the DOM. 85 * 86 * @param mixed $node A node implementing \DOMNode. 87 */ 88 public function node($node) 89 { 90 // A listing of types is at http://php.net/manual/en/dom.constants.php 91 switch ($node->nodeType) { 92 case XML_ELEMENT_NODE: 93 $this->rules->element($node); 94 break; 95 case XML_TEXT_NODE: 96 $this->rules->text($node); 97 break; 98 case XML_CDATA_SECTION_NODE: 99 $this->rules->cdata($node); 100 break; 101 case XML_PI_NODE: 102 $this->rules->processorInstruction($node); 103 break; 104 case XML_COMMENT_NODE: 105 $this->rules->comment($node); 106 break; 107 // Currently we don't support embedding DTDs. 108 default: 109 //print '<!-- Skipped -->'; 110 break; 111 } 112 } 113 114 /** 115 * Walk through all the nodes on a node list. 116 * 117 * @param \DOMNodeList $nl A list of child elements to walk through. 118 */ 119 public function children($nl) 120 { 121 foreach ($nl as $node) { 122 $this->node($node); 123 } 124 } 125 126 /** 127 * Is an element local? 128 * 129 * @param mixed $ele An element that implement \DOMNode. 130 * 131 * @return bool true if local and false otherwise. 132 */ 133 public function isLocalElement($ele) 134 { 135 $uri = $ele->namespaceURI; 136 if (empty($uri)) { 137 return false; 138 } 139 140 return isset(static::$local_ns[$uri]); 141 } 142}