Esempio n. 1
0
 public function endTag($name)
 {
     $lname = $this->normalizeTagName($name);
     // Ignore closing tags for unary elements.
     if (Elements::isA($name, Elements::VOID_TAG)) {
         return;
     }
     if ($this->insertMode <= static::IM_BEFORE_HTML) {
         // 8.2.5.4.2
         if (in_array($name, array('html', 'br', 'head', 'title'))) {
             $this->startTag('html');
             $this->endTag($name);
             $this->insertMode = static::IM_BEFORE_HEAD;
             return;
         }
         // Ignore the tag.
         $this->parseError("Illegal closing tag at global scope.");
         return;
     }
     // Special case handling for SVG.
     if ($this->insertMode == static::IM_IN_SVG) {
         $lname = Elements::normalizeSvgElement($lname);
     }
     // See https://github.com/facebook/hhvm/issues/2962
     if (defined('HHVM_VERSION') && ($cid = $this->current->getAttribute('html5-php-fake-id-attribute'))) {
         $this->current->removeAttribute('html5-php-fake-id-attribute');
     } else {
         $cid = spl_object_hash($this->current);
     }
     // XXX: Not sure whether we need this anymore.
     // if ($name != $lname) {
     // return $this->quirksTreeResolver($lname);
     // }
     // XXX: HTML has no parent. What do we do, though,
     // if this element appears in the wrong place?
     if ($lname == 'html') {
         return;
     }
     // remove the namespaced definded by current node
     if (isset($this->pushes[$cid])) {
         for ($i = 0; $i < $this->pushes[$cid][0]; $i++) {
             array_shift($this->nsStack);
         }
         unset($this->pushes[$cid]);
     }
     if (!$this->autoclose($lname)) {
         $this->parseError('Could not find closing tag for ' . $lname);
     }
     // switch ($this->insertMode) {
     switch ($lname) {
         case "head":
             $this->insertMode = static::IM_AFTER_HEAD;
             break;
         case "body":
             $this->insertMode = static::IM_AFTER_BODY;
             break;
         case "svg":
         case "mathml":
             $this->insertMode = static::IM_IN_BODY;
             break;
     }
 }
Esempio n. 2
0
 protected function attrs($ele)
 {
     // FIXME: Needs support for xml, xmlns, xlink, and namespaced elements.
     if (!$ele->hasAttributes()) {
         return $this;
     }
     // TODO: Currently, this always writes name="value", and does not do
     // value-less attributes.
     $map = $ele->attributes;
     $len = $map->length;
     for ($i = 0; $i < $len; ++$i) {
         $node = $map->item($i);
         $val = $this->enc($node->value, true);
         // XXX: The spec says that we need to ensure that anything in
         // the XML, XMLNS, or XLink NS's should use the canonical
         // prefix. It seems that DOM does this for us already, but there
         // may be exceptions.
         $name = $node->name;
         // Special handling for attributes in SVG and MathML.
         // Using if/elseif instead of switch because it's faster in PHP.
         if ($this->outputMode == static::IM_IN_SVG) {
             $name = Elements::normalizeSvgAttribute($name);
         } elseif ($this->outputMode == static::IM_IN_MATHML) {
             $name = Elements::normalizeMathMlAttribute($name);
         }
         $this->wr(' ')->wr($name);
         if (isset($val) && $val !== '' || $this->nonBooleanAttribute($node)) {
             $this->wr('="')->wr($val)->wr('"');
         }
     }
 }
Esempio n. 3
0
 /**
  * Read text in RCDATA mode.
  */
 protected function rcdata()
 {
     if (is_null($this->untilTag)) {
         return $this->text();
     }
     $sequence = '</' . $this->untilTag;
     $txt = '';
     $tok = $this->scanner->current();
     $caseSensitive = !Elements::isHtml5Element($this->untilTag);
     while ($tok !== false && !($tok == '<' && $this->sequenceMatches($sequence, $caseSensitive))) {
         if ($tok == '&') {
             $txt .= $this->decodeCharacterReference();
             $tok = $this->scanner->current();
         } else {
             $txt .= $tok;
             $tok = $this->scanner->next();
         }
     }
     $len = strlen($sequence);
     $this->scanner->consume($len);
     $len += strlen($this->scanner->whitespace());
     if ($this->scanner->current() !== '>') {
         $this->parseError("Unclosed RCDATA end tag");
     }
     $this->scanner->unconsume($len);
     $this->events->text($txt);
     $this->setTextMode(0);
     return $this->endTag();
 }
Esempio n. 4
0
 public function testNormalizeMathMlAttribute()
 {
     $tests = array('foo' => 'foo', 'definitionurl' => 'definitionURL', 'BAR' => 'bar');
     foreach ($tests as $input => $expected) {
         $this->assertEquals($expected, Elements::normalizeMathMlAttribute($input));
     }
 }