在我的 ZF2 系统中安装语言切换器的最佳选择是什么?
What's the best option to have language switcher in my ZF2 system?
我为我的一位客户开发了小型 ZF2 学说系统。到目前为止一切都很好,但他们需要 2 种语言的系统。
我可以通过 module/Application/config/module.config.php
将默认语言设置为 english
或 another language
'translator' => array(
'locale' => 'en_US',
'translation_file_patterns' => array(
array(
'type' => 'gettext',
'base_dir' => __DIR__ . '/../language',
'pattern' => '%s.mo',
),
),
),
我也可以用这个方法在module.php
中设置默认值
public function onBootstrap(MvcEvent $e)
{
$application = $e->getApplication();
$serviceManager = $application->getServiceManager();
// Just a call to the translator, nothing special!
$serviceManager->get('translator');
$this->initTranslator($e);
// Etc, more of your bootstrap function.
}
protected function initTranslator(MvcEvent $event)
{
$serviceManager = $event->getApplication()->getServiceManager();
// Zend\Session\Container
$session = New Container('language');
$translator = $serviceManager->get('translator');
$translator
->setLocale($session->language)
->setFallbackLocale('zh_CN')
;
}
这很好,现在我的系统显示默认语言为中文。但是,我想给用户选择的选项。
我该怎么做?
我找到了这个 link 但我无法让它工作。
当我在 Application/IndexController.php
中添加以下函数时,它什么也没做,而是 http://myurl.com/changeLocal
抛出 404 error
。我还需要在 module.config.php
中添加任何内容吗?
public function changeLocaleAction()
{
// New Container will get he Language Session if the SessionManager already knows the language session.
$session = new Container('language');
$language = $request->getPost()->language;
$config = $this->serviceLocator->get('config');
if (isset($config['locale']['available'][$language])) {
$session->language = $language;
$this->serviceLocator->get('translator')->setLocale($session->language);
}
}
您需要一些方法来调用 changeLocaleAction
。连接到此控制器操作的路由确实是最简单的:
'language' => array(
'type' => 'literal',
'options' => array(
'route' => '/language',
'defaults' => array(
'controller' => `Application\Controller\IndexController`,
'action' => 'changeLocaleAction'
)
)
),
您需要在您的方法中捕获语言的 post 值:
$request->getPost('language');
或者在您的控制器中使用参数插件:
$this->params()->fromPost('language');
因此,这建议用户 post 使用一个包含 language
字段的表单,该字段包含首选语言设置,例如 'zh_CN'
或 'en_US'
作为值。
您可以简化客户端,因为您只有两种语言选项。您可以简单地使用一个按钮来切换语言和 posts 另一个值:
所以如果当前语言是 'en_US'
你 post 'zh_CN'
反之亦然。
经过长时间的战斗,我是这样实现的。特别感谢 @Kwido 和 @Wilt 将我引导到正确的方向(我对他们都投了赞成票)。
Application/config/module.config.php
return array(
'controllers' => array(
'invokables' => array(
'Application\Controller\Index' => 'Application\Controller\IndexController'
),
),
'router' => array(
'routes' => array(
'home' => array(
'type' => 'Zend\Mvc\Router\Http\Literal',
'options' => array(
'route' => '/',
'defaults' => array(
'controller' => 'Application\Controller\Index',
'action' => 'index',
),
),
),
'language' => array(
'type' => 'Segment',
'options' => array(
//'route' => '/[:language]',
'route' => '/en',
'constraints' => array(
'language' => 'en',
),
'defaults' => array(
'controller' => 'Application\Controller\Index',
'action' => 'changeLocaleEnglish'
)
)
),
'languageChinese' => array(
'type' => 'Segment',
'options' => array(
//'route' => '/[:language]',
'route' => '/cn',
'constraints' => array(
'language' => 'cn',
),
'defaults' => array(
'controller' => 'Application\Controller\Index',
'action' => 'changeLocaleChinese'
)
)
),
////
// other stuff
//////////// like child routes etc
),
),
'service_manager' => array(
'abstract_factories' => array(
'Zend\Cache\Service\StorageCacheAbstractServiceFactory',
'Zend\Log\LoggerAbstractServiceFactory',
),
'factories' => array(
'translator' => 'Zend\Mvc\Service\TranslatorServiceFactory',
),
),
'translator' => array(
'locale' => 'zh_CN', //default is english which is set in module.php
'translation_file_patterns' => array(
array(
'type' => 'gettext',
'base_dir' => __DIR__ . '/../language',
'pattern' => '%s.mo',
),
),
),
'view_helpers' => array(
'invokables'=> array(
'PaginationHelper' => 'Application\View\Helper\PaginationHelper'
)
),
'view_manager' => array(
//....... view stuff
),
// Placeholder for console routes
'console' => array(
'router' => array(
'routes' => array(
),
),
),
);
Application/module.php
public function onBootstrap(MvcEvent $e)
{
$application = $e->getApplication();
$serviceManager = $application->getServiceManager();
// Just a call to the translator, nothing special!
$serviceManager->get('translator');
$this->initTranslator($e);
}
protected function initTranslator(MvcEvent $event)
{
$serviceManager = $event->getApplication()->getServiceManager();
// use Zend\Session\Container add this to top
$session = New Container('language');
$translator = $serviceManager->get('translator');
if($session['language'] != 'zh_CN'){ //if session doesn't have zh_CN then set it as english
$translator
->setLocale($session->language)
->setFallbackLocale('en_US')
;
}
}
现在 Application/src/Application/Controller/IndexController。php 我添加了两个操作来捕获会话并设置语言:
public function changeLocaleChineseAction()
{
$result = new ViewModel();
$result->setTerminal(true);
$response = $this->getResponse();
// New Container will get he Language Session if the SessionManager already knows the language session.
$session = new Container('language');
$request = $this->getRequest();
$config = $this->serviceLocator->get('config');
$language = $config['translator']['locale']; //default locale from Application/config/module.config.php
if (isset($config['translator']['locale'])) {
$session->language = $language;
$this->serviceLocator->get('translator')->setLocale('zh_CN')
->setFallbackLocale('zh_CN')
;
}
return $this->redirect()->toRoute('home');
}
public function changeLocaleEnglishAction()
{
// New Container will get he Language Session if the SessionManager already knows the language session.
$session = new Container('language');
//just clear the language session
$session->getManager()->getStorage()->clear('language');
$language = 'en_US'; //set new language
$request = $this->getRequest();
$config = $this->serviceLocator->get('config');
$session->language = $language;
$this->serviceLocator->get('translator')->setLocale('en_US')
->setFallbackLocale('en_US')
;
return $this->redirect()->toRoute('home');
}
现在只需在 layout.phtml
中添加 link 即可使用语言切换器:
<a href="<?php echo $this->url('home')."cn";?>"><?php echo $this->translate("Chinese");?></a>
<a href="<?php echo $this->url('home')."en";?>"><?php echo $this->translate("English");?></a>
希望这对以后的其他人有所帮助。
我为我的一位客户开发了小型 ZF2 学说系统。到目前为止一切都很好,但他们需要 2 种语言的系统。
我可以通过 module/Application/config/module.config.php
english
或 another language
'translator' => array(
'locale' => 'en_US',
'translation_file_patterns' => array(
array(
'type' => 'gettext',
'base_dir' => __DIR__ . '/../language',
'pattern' => '%s.mo',
),
),
),
我也可以用这个方法在module.php
public function onBootstrap(MvcEvent $e)
{
$application = $e->getApplication();
$serviceManager = $application->getServiceManager();
// Just a call to the translator, nothing special!
$serviceManager->get('translator');
$this->initTranslator($e);
// Etc, more of your bootstrap function.
}
protected function initTranslator(MvcEvent $event)
{
$serviceManager = $event->getApplication()->getServiceManager();
// Zend\Session\Container
$session = New Container('language');
$translator = $serviceManager->get('translator');
$translator
->setLocale($session->language)
->setFallbackLocale('zh_CN')
;
}
这很好,现在我的系统显示默认语言为中文。但是,我想给用户选择的选项。
我该怎么做?
我找到了这个 link 但我无法让它工作。
当我在 Application/IndexController.php
中添加以下函数时,它什么也没做,而是 http://myurl.com/changeLocal
抛出 404 error
。我还需要在 module.config.php
中添加任何内容吗?
public function changeLocaleAction()
{
// New Container will get he Language Session if the SessionManager already knows the language session.
$session = new Container('language');
$language = $request->getPost()->language;
$config = $this->serviceLocator->get('config');
if (isset($config['locale']['available'][$language])) {
$session->language = $language;
$this->serviceLocator->get('translator')->setLocale($session->language);
}
}
您需要一些方法来调用 changeLocaleAction
。连接到此控制器操作的路由确实是最简单的:
'language' => array(
'type' => 'literal',
'options' => array(
'route' => '/language',
'defaults' => array(
'controller' => `Application\Controller\IndexController`,
'action' => 'changeLocaleAction'
)
)
),
您需要在您的方法中捕获语言的 post 值:
$request->getPost('language');
或者在您的控制器中使用参数插件:
$this->params()->fromPost('language');
因此,这建议用户 post 使用一个包含 language
字段的表单,该字段包含首选语言设置,例如 'zh_CN'
或 'en_US'
作为值。
您可以简化客户端,因为您只有两种语言选项。您可以简单地使用一个按钮来切换语言和 posts 另一个值:
所以如果当前语言是 'en_US'
你 post 'zh_CN'
反之亦然。
经过长时间的战斗,我是这样实现的。特别感谢 @Kwido 和 @Wilt 将我引导到正确的方向(我对他们都投了赞成票)。
Application/config/module.config.php
return array(
'controllers' => array(
'invokables' => array(
'Application\Controller\Index' => 'Application\Controller\IndexController'
),
),
'router' => array(
'routes' => array(
'home' => array(
'type' => 'Zend\Mvc\Router\Http\Literal',
'options' => array(
'route' => '/',
'defaults' => array(
'controller' => 'Application\Controller\Index',
'action' => 'index',
),
),
),
'language' => array(
'type' => 'Segment',
'options' => array(
//'route' => '/[:language]',
'route' => '/en',
'constraints' => array(
'language' => 'en',
),
'defaults' => array(
'controller' => 'Application\Controller\Index',
'action' => 'changeLocaleEnglish'
)
)
),
'languageChinese' => array(
'type' => 'Segment',
'options' => array(
//'route' => '/[:language]',
'route' => '/cn',
'constraints' => array(
'language' => 'cn',
),
'defaults' => array(
'controller' => 'Application\Controller\Index',
'action' => 'changeLocaleChinese'
)
)
),
////
// other stuff
//////////// like child routes etc
),
),
'service_manager' => array(
'abstract_factories' => array(
'Zend\Cache\Service\StorageCacheAbstractServiceFactory',
'Zend\Log\LoggerAbstractServiceFactory',
),
'factories' => array(
'translator' => 'Zend\Mvc\Service\TranslatorServiceFactory',
),
),
'translator' => array(
'locale' => 'zh_CN', //default is english which is set in module.php
'translation_file_patterns' => array(
array(
'type' => 'gettext',
'base_dir' => __DIR__ . '/../language',
'pattern' => '%s.mo',
),
),
),
'view_helpers' => array(
'invokables'=> array(
'PaginationHelper' => 'Application\View\Helper\PaginationHelper'
)
),
'view_manager' => array(
//....... view stuff
),
// Placeholder for console routes
'console' => array(
'router' => array(
'routes' => array(
),
),
),
);
Application/module.php
public function onBootstrap(MvcEvent $e)
{
$application = $e->getApplication();
$serviceManager = $application->getServiceManager();
// Just a call to the translator, nothing special!
$serviceManager->get('translator');
$this->initTranslator($e);
}
protected function initTranslator(MvcEvent $event)
{
$serviceManager = $event->getApplication()->getServiceManager();
// use Zend\Session\Container add this to top
$session = New Container('language');
$translator = $serviceManager->get('translator');
if($session['language'] != 'zh_CN'){ //if session doesn't have zh_CN then set it as english
$translator
->setLocale($session->language)
->setFallbackLocale('en_US')
;
}
}
现在 Application/src/Application/Controller/IndexController。php 我添加了两个操作来捕获会话并设置语言:
public function changeLocaleChineseAction()
{
$result = new ViewModel();
$result->setTerminal(true);
$response = $this->getResponse();
// New Container will get he Language Session if the SessionManager already knows the language session.
$session = new Container('language');
$request = $this->getRequest();
$config = $this->serviceLocator->get('config');
$language = $config['translator']['locale']; //default locale from Application/config/module.config.php
if (isset($config['translator']['locale'])) {
$session->language = $language;
$this->serviceLocator->get('translator')->setLocale('zh_CN')
->setFallbackLocale('zh_CN')
;
}
return $this->redirect()->toRoute('home');
}
public function changeLocaleEnglishAction()
{
// New Container will get he Language Session if the SessionManager already knows the language session.
$session = new Container('language');
//just clear the language session
$session->getManager()->getStorage()->clear('language');
$language = 'en_US'; //set new language
$request = $this->getRequest();
$config = $this->serviceLocator->get('config');
$session->language = $language;
$this->serviceLocator->get('translator')->setLocale('en_US')
->setFallbackLocale('en_US')
;
return $this->redirect()->toRoute('home');
}
现在只需在 layout.phtml
中添加 link 即可使用语言切换器:
<a href="<?php echo $this->url('home')."cn";?>"><?php echo $this->translate("Chinese");?></a>
<a href="<?php echo $this->url('home')."en";?>"><?php echo $this->translate("English");?></a>
希望这对以后的其他人有所帮助。