webmaster@0: xmlDocument = new DOMDocument(); webmaster@6: $this->xmlDocument->validateOnParse = $shouldValidate; webmaster@9: $this->xmlDocument->preserveWhiteSpace = false; webmaster@17: $contents = file_get_contents($fileName, FILE_USE_INCLUDE_PATH); webmaster@17: $this->xmlDocument->loadXML($contents); webmaster@15: $this->xmlDocument->preserveWhiteSpace = false; webmaster@0: $this->xmlXPath = new DOMXPath($this->xmlDocument); webmaster@8: $this->xmlXPath->registerNamespace('_t', Template::NS); webmaster@0: } webmaster@0: webmaster@3: function apply($selector, $obj, DOMElement $root = null) { webmaster@6: if(!($root instanceof DOMElement)) webmaster@3: $root = $this->xmlDocument->documentElement; webmaster@3: $rootSelector = $this->parseSelector($selector, $root); webmaster@6: if(is_array($obj)) webmaster@6: $this->applyClone($rootSelector, $obj, $root); webmaster@3: else { webmaster@0: foreach($rootSelector->nodes as $node) { webmaster@3: $content = $this->parseReplacement($obj); webmaster@15: if(isset($rootSelector->attribute)) webmaster@0: $node->setAttribute($rootSelector->attribute, $obj); webmaster@15: else webmaster@15: $this->setNodeContent($node, $content); webmaster@0: } webmaster@0: } webmaster@0: } webmaster@6: webmaster@6: function applyClone($rootSelector, $obj, $root) { webmaster@6: foreach($obj as $array) { webmaster@6: $nodeName = key($array); webmaster@6: foreach($rootSelector->nodes as $node) { webmaster@6: $tmp = $this->getClonedNode($node, $nodeName); webmaster@6: $futureNode = $tmp->clone; webmaster@6: $futureNode = $node->insertBefore($futureNode, $tmp->orig); webmaster@6: foreach($array as $sel => $test) { webmaster@6: $locSelector = $this->parseSelector($sel, $node); webmaster@7: if(isset($locSelector->attribute)) webmaster@6: $futureNode->setAttribute($locSelector->attribute, $test); webmaster@6: else { webmaster@6: $content = $this->parseReplacement($test); webmaster@6: $node->insertBefore($content, $tmp->orig); webmaster@15: $this->setNodeContent($futureNode, $content); webmaster@6: } webmaster@6: } webmaster@6: } webmaster@6: } webmaster@6: } webmaster@0: webmaster@0: function getClonedNode($node, $childNodeName) { webmaster@3: $candidates = $this->parseSelector($childNodeName, $node)->nodes; webmaster@1: foreach($candidates as $candidate) { webmaster@3: if($candidate->getAttributeNS(Template::NS, 'toClone') == 'true') { webmaster@0: $tmp = array(); webmaster@1: $tmp['orig'] = $candidate; webmaster@1: $cnode = $candidate->cloneNode(true); webmaster@6: $cnode->removeAttributeNS(Template::NS, 'toClone'); webmaster@0: $tmp['clone'] = $cnode; webmaster@0: return (object)$tmp; webmaster@0: } webmaster@0: } webmaster@0: } webmaster@0: webmaster@3: function parseSelector($selector, DOMElement $root) { webmaster@0: $obj = array(); webmaster@0: $pos = strpos($selector, '@'); webmaster@0: if($pos !== false) { webmaster@0: $obj['attribute'] = substr($selector,$pos +1); webmaster@0: $selector = substr($selector, 0, $pos); webmaster@0: } webmaster@0: if($selector[0] == '#') { webmaster@8: $obj['xpath'] = "//*[@_t:id='" . substr($selector, 1) . "']"; webmaster@0: $obj['nodes'] = $this->xmlXPath->query($obj['xpath'], $root); webmaster@0: } webmaster@0: else { webmaster@0: $obj['nodeName'] = $selector; webmaster@0: $obj['nodes'] = $root->getElementsByTagName($selector); webmaster@0: } webmaster@0: return (object)$obj; webmaster@0: } webmaster@0: webmaster@0: function parseReplacement($obj) { webmaster@0: $retVal = NULL; webmaster@0: if(is_string($obj)) webmaster@0: $retVal = $this->xmlDocument->createTextNode($obj); webmaster@0: else if($obj instanceof DOMDocument) webmaster@16: $retVal = $this->xmlDocument->importNode($obj->documentElement); webmaster@16: else if($obj instanceof DOMDocumentFragment) webmaster@16: $retVal = $obj; webmaster@0: else if($obj instanceof DOMNode) webmaster@3: $retVal = $obj->clone(true); webmaster@11: else if($obj instanceof Template) { webmaster@11: $node = $obj->xmlDocument->documentElement; webmaster@11: $retVal = $this->xmlDocument->importNode($node, true); webmaster@11: } webmaster@0: return $retVal; webmaster@0: } webmaster@0: webmaster@0: function setParams($array) { webmaster@0: foreach($array as $selector => $obj) { webmaster@0: $this->apply($selector, $obj); webmaster@0: } webmaster@0: } webmaster@0: webmaster@0: function replaceNode(DOMNode $node, DOMNode $content) { webmaster@0: $parent = $node->parentNode; webmaster@0: $parent->replaceChild($content, $node); webmaster@0: } webmaster@0: webmaster@0: function setNodeContent(DOMElement $node, DOMNode $content) { webmaster@0: // Suppress existing childs webmaster@0: foreach($node->childNodes as $child) { webmaster@0: $node->removeChild($child); webmaster@0: } webmaster@0: // Add the new child webmaster@0: $node->appendChild($content); webmaster@0: } webmaster@0: webmaster@0: function clean() { webmaster@0: // Suppression des noeuds à cloner webmaster@8: $nodes = $this->xmlXPath->query("//*[@_t:toClone]|//_t:*"); webmaster@0: foreach($nodes as $node) { webmaster@0: if($node->parentNode) { webmaster@15: $parent = $node->parentNode; webmaster@15: if(!$node->hasAttributeNS(Template::NS, 'toClone')) { webmaster@15: while($node->hasChildNodes()) webmaster@15: $parent->insertBefore($node->firstChild, $node); webmaster@15: } webmaster@15: $parent->removeChild($node); webmaster@0: } webmaster@0: } webmaster@19: webmaster@19: // Suppression éventuelle des attributs de l'espace de nom Template::NS webmaster@19: if($this->stripAttributesInTemplateNS) { webmaster@19: $nodes = $this->xmlXPath->query("//*[@_t:*]"); webmaster@19: foreach($nodes as $node) { webmaster@19: foreach($node->attributes as $attr) { webmaster@19: if($attr->namespaceURI == Template::NS) webmaster@19: $node->removeAttributeNode($attr); webmaster@19: } webmaster@19: } webmaster@19: } webmaster@19: } webmaster@19: webmaster@19: function shouldStripAttributesInTemplateNS($boolean) { webmaster@19: $this->stripAttributesInTemplateNS = $boolean; webmaster@0: } webmaster@0: webmaster@0: function __toString() { webmaster@0: $this->clean(); webmaster@9: $this->xmlDocument->formatOutput = true; webmaster@15: $this->xmlDocument->normalizeDocument(); webmaster@0: return $this->xmlDocument->saveXML(); webmaster@0: } webmaster@16: webmaster@16: function getDocumentFragment() { webmaster@16: return $this->xmlDocument->createDocumentFragment(); webmaster@16: } webmaster@6: }