如何在JSF 2.0中更改语言环境? [英] How to change locale in JSF 2.0?

查看:71
本文介绍了如何在JSF 2.0中更改语言环境?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在我的应用中,用户应该能够切换语言环境(用于在页面上呈现文本的语言).大量的教程都使用FacesContext.getCurrentInstance().getViewRoot().setLocale().例如: http://www.mkyong.com/jsf2/jsf-2 -internationalization-example/.但是,这在JSF 2.0中根本不起作用(它在1.2中确实有效).语言永不切换.没有错误或任何东西.相同的代码在JSF 1.2中运行良好.

In my app, user should be able to switch the locale (the language used to render text on pages). Tons of tutorials are using FacesContext.getCurrentInstance().getViewRoot().setLocale(). For example: http://www.mkyong.com/jsf2/jsf-2-internationalization-example/. But, that simply doesn't work in JSF 2.0 (it did work in 1.2). The language never switches. No errors or anything. The same code worked fine in JSF 1.2.

什么是正确和确定的方法?我已经拼凑出一种解决方案,但是不确定这是否正确.这很好.用户单击英语或法语后,语言将切换.这是一些代码片段,可以给您一些想法.

What is the correct and definitive approach? I have cobbled together a solution, but not sure if this is the correct one. This works fine. The language switches after user clicks on English or French. Here is code snippet to give you some idea.

@ManagedBean(name = "switcher")
@SessionScoped
public class LanguageSwitcher {
    Locale locale = FacesContext.getCurrentInstance().getViewRoot().getLocale();
    public String switchLocale(String lang) {
        locale = new Locale(lang);

        return FacesContext.getCurrentInstance().getViewRoot().getViewId() +
            "?faces-redirect=true";
    }
    //getLocale() etc. omitted for brevity
}

XHTML:

<f:view locale="#{switcher.locale}">
    <h:outputText value="#{msg.greeting}" />
    <h:commandLink value="English" action="#{switcher.switchLocale('en')}" />
    <h:commandLink value="French" action="#{switcher.switchLocale('fr')}" />
</f:view>

仅为给您更多信息,这是配置文件.

Just to give you more info, here is the config file.

<application>
    <locale-config>
        <supported-locale>en</supported-locale>
        <supported-locale>fr</supported-locale>
    </locale-config>
    <resource-bundle>
        <base-name>com.resources.Messages</base-name>
        <var>msg</var>
    </resource-bundle>
</application>

这再次起作用.但是,我没有通过以任何方式调用任何API来更改JSF本身的语言环境.这给了我一些令人毛骨悚然的感觉.这是更改用户语言环境的正确方法吗?

Once again, this works. But, I haven't changed the locale of JSF itself by calling any API in any way. This gives me somewhat of a creepy feeling. Is this the correct way to change user's locale?

推荐答案

好的,冒着回答我自己问题的风险,我想总结一下我发现的所有不同方法.

OK, at the risk of answering my own question, I will like to summarize all the different approaches that I have found.

基本方法是我已经在做的事情.也就是说,在会话范围内有一个受管Bean,它可以返回用户的语言环境.需要使用<f:view locale="...">在每个XHTML中使用此语言环境.我从BalusC的帖子中学到了这种技术,所以谢谢.

The basic approach is what I am already doing. That is, have a managed bean in session scope that returns the Locale of the user. This locale needs to be used in every XHTML using <f:view locale="...">. I learned this technique from a post by BalusC, so thanks are due there.

现在,需要关注的是f:view元素的使用.这需要在每页中重复,如果错误地忽略了,则可能是缺陷的来源.我找到了解决此问题的几种方法.

Now, the concern is the use of the f:view element. This needs to be repeated in every page, a potential source of defect if omitted by mistake. I have found a couple of ways of solving this problem.

方法1:创建Facelet模板,然后在其中添加f:view元素.各个模板用户页面不必担心添加此元素.

Approach #1: Create a Facelet template and add the f:view element there. Individual template user pages don't have to worry about adding this element.

方法2使用阶段侦听器. @meriton已在此处发布了解决方案.谢谢你.

Approach #2 uses a phase listener. @meriton has posted the solution here. Thank you for that.

方法#3使用自定义视图处理程序,该处理程序扩展了MultiViewHandler并从calculateLocale()方法返回用户的语言环境. 《 Begining JSF 2 APIs and JBoss Seam》(作者:Kent Ka Iok Tong)一书对此进行了描述.这是本书的一个稍作改动的例子:

Approach #3 uses a custom view handler that extends MultiViewHandler and returns user's locale from the calculateLocale() method. This is described in the book Beginning JSF 2 APIs and JBoss Seam By: Kent Ka Iok Tong. Here is a slightly altered example from the book:

public class MyViewHandler extends MultiViewHandler {
    public Locale calculateLocale(FacesContext context) {
        HttpSession session = (HttpSession) context.getExternalContext()
            .getSession(false);
        if (session != null) {
            //Return the locale saved by the managed bean earlier
            Locale locale = (Locale) session.getAttribute("locale");
            if (locale != null) {
                return locale;
            }
        }
       return super.calculateLocale(context);
    }
}

然后将其注册在face config中.

Then register it in faces config.

<application>
    <view-handler>com.package.MyViewHandler</view-handler>
<!-- Other stuff ... -->
</application>

这比相位侦听器更为优雅.不幸的是,MultiViewHandler是来自com.sun.faces.application.view包的内部非API类.这就招致了前进的风险.

This is somewhat more elegant than the phase listener. Unfortunately, MultiViewHandler is an internal non-API class from the com.sun.faces.application.view package. That incurs some risk going forward.

使用方法2或方法3,无需在页面中使用f:view元素.

With either approach #2 or #3, there is no need for the f:view element in the pages.

这篇关于如何在JSF 2.0中更改语言环境?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆