我一直在尝试在一个对象上定义一个方法,用作Mustache模板的值,但是Mustache模板没有正确调用它。所以我一定做错了。
这是一个例子:
<?php
require './vendor/mustache/mustache/src/Mustache/Autoloader.php';
Mustache_Autoloader::register();
$t = new TplValues();
$t->planet = 'Earth';
$m = new Mustache_Engine();
echo $m->render('Hello, {{# caps}}{{planet}}{{/ caps}}!', $t);
class TplValues {
public function caps($text) {
return strtoupper($text);
}
}
这个输出是:
PHP Warning: Missing argument 1 for TplValues::caps(), called in /home/user/test/vendor/mustache/mustache/src/Mustache/Context.php on line 138 and defined in /home/user/test/test.php on line 14
PHP Notice: Undefined variable: text in /home/user/test/test.php on line 15
Hello, !
我也尝试在构造函数中使用帮助器:
<?php
require './vendor/mustache/mustache/src/Mustache/Autoloader.php';
Mustache_Autoloader::register();
$t = new stdClass();
$t->planet = 'Earth';
$m = new Mustache_Engine(array(
'helpers' => array(
'caps' => function($text) {return strtoupper($text);}
)
));
echo $m->render('Hello, {{# caps}}{{planet}}{{/ caps}}! ({{planet}})', $t);
这不会触发通知,但输出为:
Hello, !
我错过了什么吗?
答案 0 :(得分:4)
是的。你错过了一些东西:)
在Mustache中,函数和属性都被视为值。这些在功能上是等价的:
class SomeView {
public $title = 'foo';
}
class AnotherView {
function title() {
return 'foo';
}
}
为了将某个部分视为“高阶部分”或“lambda部分”,该部分的值必须是可调用的。这意味着,您需要从caps
方法返回可调用的内容。你的第一个例子看起来像这样:
class TplValues {
public function caps() {
return function($text) {
return strtoupper($text);
}
}
}
现在当Mustache调用$t->caps()
时,它将返回一个Closure,它将传递该部分的内容。
但这不是全部:)
根据规范,将未渲染的模板传递给更高阶(lambda)部分,然后渲染返回值。所以你的模板开头为:
Hello, {{# caps }}{{ planet }}{{/ caps }}!
调用caps
匿名函数时,会传递:
{{ planet }}
它转换为大写:
{{ PLANET }}
......这绝对不是你想要的。相反,你应该使用这个Closure:
function($text, $m) {
return strtoupper($m->render($text));
}
...因为现在Mustache将首先渲染$text
以解析您的{{ planet }}
变量,然后您可以将其变为大写并返回。