如何在zend框架视图中使用$ this-> _()?

时间:2011-11-15 17:07:36

标签: php model-view-controller zend-framework translation

在我的ZF 1.11应用程序中,我将我的翻译器存储在注册表中,如下所示:

Zend_Registry::set('Zend_Translate', $translator);

因此,在我的视图脚本中,我可以通过这种方式访问​​翻译器:

$this->translate('abc');

是否有任何聪明的方法可以使用此调用:

$this->_('abc');

使用$ this->翻译会使视图混乱,而且很多人习惯于看到_()。

2 个答案:

答案 0 :(得分:6)

虽然我普遍同意函数/方法名称应该有意义的概念,但我也同意翻译的_()是一个广泛使用的标准,因此是可以接受的。

您可以通过向中间层添加包装来实现此目的。例如,以下内容将使该方法可用于从MyProject_Controller_Action派生的所有控制器:

class MyProject_Controller_Action extends Zend_Controller_Action 
{
    protected $translator;

    public function init()
    {
        $this->translator = Zend_Registry::get('Zend_Translate');
    }



   /**
    * Translator wrapper
    * 
    * @param string $string The string to be translated
    * @return string $translated The translated string
    */
    protected function _($string)
    {
        $translated = $this->translator->translate($string);
        return $translated;
    }
}

当然可以使用Zend_View完成同样的工作。

免责声明:通过直接调用注册表来混淆代码并不是最好的做法。实际上它是一个反模式,应该被DI取代。 Zend Framework 2将使我们更容易避免注册表。可以通过构造函数将转换对象实际注入到类中来改进此代码。

答案 1 :(得分:5)

不,不是我所知道的。无论如何,有几个与此相关的隐含问题。首先,您应始终提供函数(以及此类变量)meaningful names。也就是说,__()根本不是一个有意义的名字。事实上,恰恰相反,它具有 no 的含义。其次,最佳做法是使用下划线将 privateprotected函数(以及相应的变量)加上前缀。

最后,通过zend视图帮助程序的工作方式,如果命名为__(),您几乎必须“欺骗”系统以查找视图助手。您必须将其命名为Zend_View_Helper___,但这不起作用。更不用说,这需要为您的文件__.php命名。

我想你可以为你的助手Zend_View_Helper_T命名,在这种情况下你可以使用$this->t($string);翻译内容(我测试了它并且它有效),但你应该再次使用meaningful names


修改

到目前为止,我还没有意识到你想从控制器中调用它,我决定修改我的答案,并对我从选民中收到的评论提出一些反馈。

由于以下原因,很难建议您为Zend_Controller_Action创建一个包装类,在其中创建函数_()

  • 因为不管它是否是“公认的标准”,我 重申所有方法和变量应该有一个 有意义的名字我必须坚持这一点,因为我坚信 遵循显式编码标准(而不是那些“传闻”) 或“最近采用的”不直接对应的做法 已知 - 从而信任 - 范式)。那说,应该是梨,还是 甚至Zend,我决定有一天会采取这种激进的改变 辞去我的性格。注意:可以认为这是可信的 像Drupal这样的公司和他们自称的最佳实践可以 被认为是明确的编码标准,但我不同意。为什么?因为 梨子......好吧......它是梨子。 Zend是“PHP公司”。这个很难(硬 比那更可信。 如果有人不同意这一点 声明请说明为什么或纠正我而不是投票。无论如何,标准 仅仅是一个不需要的建议;因此,他们应该被视为 这样。所以,我想只要您遵循某些标准,那就太好了!这些 毕竟不是规则。

尽管如此,马库斯的解决方案除了功能名称之外还很好(原因如前所述)。我唯一要改变的是Zend_Registry::get()函数中对_()的调用。如果你计划尽可能多地调用该函数,那么这样的事情可能会更好:

class MyProject_Controller_Action extends Zend_Controller_Action 
{
    /**
     * the translator object
     * @var Zend_Translate
     */
    protected $_translator;

    public function init()
    {
        $this->_translator = Zend_Registry::get('Zend_Translate');
    }

    /**
     * note my new method name, you don't have to use it but I still
     * recommend it. the name is just a suggestion, if you prefer something
     * like _translate() or _trnslte() then by all means (although I don't
     * recommend abbreviations unless they're super obvious I guess).
     */
    protected function _trans($string)
    {
        return $this->_translator->translate((string) $string);
    }
}