diff --git a/Mustache.php b/Mustache.php index e47e532..3f36d5e 100644 --- a/Mustache.php +++ b/Mustache.php @@ -25,7 +25,8 @@ class Mustache { // Override charset passed to htmlentities() and htmlspecialchars(). Defaults to UTF-8. protected $charset = 'UTF-8'; - const PRAGMA_DOT_NOTATION = 'DOT-NOTATION'; + const PRAGMA_DOT_NOTATION = 'DOT-NOTATION'; + const PRAGMA_IMPLICIT_ITERATOR = 'IMPLICIT-ITERATOR'; protected $tagRegEx; @@ -35,7 +36,8 @@ class Mustache { protected $pragmas = array(); protected $pragmasImplemented = array( - self::PRAGMA_DOT_NOTATION + self::PRAGMA_DOT_NOTATION, + self::PRAGMA_IMPLICIT_ITERATOR ); /** @@ -151,8 +153,23 @@ class Mustache { // regular section case '#': if ($this->varIsIterable($val)) { + if ($this->hasPragma(self::PRAGMA_IMPLICIT_ITERATOR)) { + if ($opt = $this->getPragmaOptions(self::PRAGMA_IMPLICIT_ITERATOR)) { + $iterator = $opt['iterator']; + } else { + $iterator = '.'; + } + } else { + $iterator = false; + } + foreach ($val as $local_context) { - $replace .= $this->_render($content, $this->getContext($context, $local_context)); + if ($iterator) { + $c = array($iterator => $local_context); + $replace .= $this->_render($content, $this->getContext($context, $c)); + } else { + $replace .= $this->_render($content, $this->getContext($context, $local_context)); + } } } else if ($val) { if (is_array($val) || is_object($val)) { @@ -231,11 +248,11 @@ class Mustache { } protected function getPragmaOptions($pragma_name) { - if (!$this->hasPragma()) { + if (!$this->hasPragma($pragma_name)) { throw new MustacheException('Unknown pragma: ' . $pragma_name, MustacheException::UNKNOWN_PRAGMA); } - return $this->pragmas[$pragma_name]; + return (is_array($this->pragmas[$pragma_name])) ? $this->pragmas[$pragma_name] : array(); } /** @@ -426,7 +443,9 @@ class Mustache { * @return string */ protected function getVariable($tag_name, &$context) { - if ($this->hasPragma(self::PRAGMA_DOT_NOTATION)) { + if ($ret = $this->_getVariable($tag_name, $context)) { + return $ret; + } else if ($this->hasPragma(self::PRAGMA_DOT_NOTATION)) { $chunks = explode('.', $tag_name); $first = array_shift($chunks); @@ -438,7 +457,7 @@ class Mustache { } return $ret; } else { - return $this->_getVariable($tag_name, $context); + return $ret; } } diff --git a/examples/implicit_iterator/ImplicitIterator.php b/examples/implicit_iterator/ImplicitIterator.php new file mode 100644 index 0000000..c01fef0 --- /dev/null +++ b/examples/implicit_iterator/ImplicitIterator.php @@ -0,0 +1,5 @@ +getMock('Mustache', array('renderPragma'), array('{{%IMPLICIT-ITERATOR}}')); + $m->expects($this->exactly(1)) + ->method('renderPragma') + ->with(array('{{%IMPLICIT-ITERATOR}}', 'IMPLICIT-ITERATOR', null)); + $m->render(); + } + + public function testImplicitIterator() { + $m1 = new Mustache('{{%IMPLICIT-ITERATOR}}{{#items}}{{.}}{{/items}}', array('items' => array('a', 'b', 'c'))); + $this->assertEquals('abc', $m1->render()); + + $m2 = new Mustache('{{%IMPLICIT-ITERATOR}}{{#items}}{{.}}{{/items}}', array('items' => array(1, 2, 3))); + $this->assertEquals('123', $m2->render()); + } + + public function testDotNotationCollision() { + $m = new Mustache(null, array('items' => array('foo', 'bar', 'baz'))); + + $this->assertEquals('foobarbaz', $m->render('{{%IMPLICIT-ITERATOR}}{{%DOT-NOTATION}}{{#items}}{{.}}{{/items}}')); + $this->assertEquals('foobarbaz', $m->render('{{%DOT-NOTATION}}{{%IMPLICIT-ITERATOR}}{{#items}}{{.}}{{/items}}')); + } + + public function testCustomIterator() { + $m = new Mustache(null, array('items' => array('foo', 'bar', 'baz'))); + + $this->assertEquals('foobarbaz', $m->render('{{%IMPLICIT-ITERATOR iterator=item}}{{#items}}{{item}}{{/items}}')); + $this->assertEquals('foobarbaz', $m->render('{{%IMPLICIT-ITERATOR iterator=items}}{{#items}}{{items}}{{/items}}')); + } + +} \ No newline at end of file