当您设置文本域时,它(显然)会擦除之前的文本域。
当您使用嵌套包含,其中可能存在具有不同文本域的 textdomain() 调用时,这会成为问题。从包含返回后,您的文本域将发生更改,并且父脚本的其余部分将无法翻译剩余的句子。
我编写了这两个小函数来避免这种情况。您应该将整个代码放入一个文件中,您需要在每个需要 gettext 功能的脚本中包含该文件。然后,仅在设置文本域的每个脚本/函数的开头和结尾使用 set_textdomain() 和 restore_textdomain()。
对 set_textdomain() 的调用必须对应对 restore_textdomain() 的调用,并且对嵌套调用的次数没有限制。
这里进行了一项优化:当新的文本域与当前文本域相同时,不会进行任何更改,并且 restore_textdomain() 会意识到这一点,因此您可以安全地调用它。
<?php
$_td_stack = array(); // 文本域堆栈
/**
* 在记录当前文本域后设置新的文本域,
* 因此它可以在以后使用 restore_textdomain() 恢复。
*
* 可以嵌套对这两个函数的调用。
* @param string 要设置的新文本域
*/
function set_textdomain($td)
{
global $_td_stack;
$old_td = textdomain(NULL);
if ($old_td)
{
if (!strcmp($old_td, $td))
{
array_push($_td_stack, false);
}
else
{
array_push($_td_stack, $old_td);
}
}
textdomain($td);
}
/**
* 恢复上次调用 set_textdomain() 之前激活的文本域。
*/
function restore_textdomain()
{
global $_td_stack;
$old_td = array_pop($_td_stack);
if ($old_td)
{
textdomain($old_td);
}
}
?>