2011-12-05 3 views
0

Я пытаюсь реализовать интернационализацию в JSF 2. Я пробовал много решений, но я не могу изменить его. Вот мой код для faces-config.xml файла:Как изменить локаль представления на p: commandLinks?

<application> 
    <locale-config> 
     <default-locale>es</default-locale> 
     <supported-locale>en_GB</supported-locale> 
     <supported-locale>fr</supported-locale> 
    </locale-config> 
    <resource-bundle> 
     <base-name>malagaAcoge.configuracion.Messages</base-name> 
     <var>msg</var> 
    </resource-bundle> 
</application> 

Я использую 3 свойства, которые находятся в моем исходном пакете.

Это мое мнение:

<f:view locale="#{idiomaBean.locale}"> 
    <div id="contenedor"> 
     <div id="cabecera" 
      style="background: url('../images/logo/fondoCabecera.png') no-repeat"> 
     </div> 
     <div id="cuerpo"> 
      <div id="center"> 
       <h:form prependId="false" id="form_login"> 
        <h:selectOneMenu value="#{idiomaBean.locale}" 
         onchange="submit()" 
         valueChangeListener="#{idiomaBean.changeLanguage}"> 
         <f:selectItems value="#{idiomaBean.countriesInMap}" /> 
        </h:selectOneMenu> 

        <h:panelGrid columns="3"> 
         <p:commandLink title="SP" action="#{idiomaBean.changeLanguage}"> 
          <p:graphicImage value="../images/paises/sp.png"></p:graphicImage> 
         </p:commandLink> 
         <p:commandLink title="EN" action="#{idiomaBean.changeLanguage}"> 
          <p:graphicImage value="../images/paises/en.png"> 
          </p:graphicImage> 
         </p:commandLink> 
         <p:commandLink title="FR" action="#{idiomaBean.changeLanguage}"> 
          <p:graphicImage value="../images/paises/fr.png"> 
          </p:graphicImage> 
          <f:setPropertyActionListener target="#{idiomaBean.locale}" 
           value="fr"></f:setPropertyActionListener> 
         </p:commandLink> 
        </h:panelGrid> 

Это IdiomaBean я использую, чтобы выполнить изменение:

private static final long serialVersionUID = 1L; 
private static String locale = FacesContext.getCurrentInstance() 
     .getViewRoot().getLocale().getLanguage(); 
private static Map<String, Object> countries; 
static { 
    countries = new LinkedHashMap<String, Object>(); 
    countries.put("Español", new Locale("es")); // label, value 
    countries.put("English", Locale.ENGLISH); 
    countries.put("Français", Locale.FRENCH); 
} 

public Map<String, Object> getCountriesInMap() { 
    return countries; 
} 

public String getLocale() { 
    return locale; 
} 

@SuppressWarnings("static-access") 
public void setLocale(String locale) { 
    this.locale = locale; 
    FacesContext.getCurrentInstance().getViewRoot().setLocale(new Locale(locale)); 
} 

public void changeLanguage(ValueChangeEvent e) { 
    String newLocaleValue = e.getNewValue().toString(); 

    // loop country map to compare the locale code 
    for (Map.Entry<String, Object> entry : countries.entrySet()) { 

     if (entry.getValue().toString().equals(newLocaleValue)) { 

      FacesContext.getCurrentInstance().getViewRoot() 
        .setLocale((Locale) entry.getValue()); 

     } 
    } 

Я использую PrimeFaces 3.0 на сервере Tomcat.

ответ

4

В описании проблемы не указано. Этот выпадающий список выглядит так, как он будет работать (хотя прослушиватель изменения стоимости совершенно лишний), но эти ссылки действительно не будут работать вообще. Я предполагаю, что вы действительно спрашиваете, как правильно реализовать ссылки.

Во-первых, избавитесь от метода прослушивателя изменения значения как в раскрывающемся списке, так и в ссылках изображения. Вас не интересует старое значение, вас интересует только новое значение, так что вам это совсем не нужно. Поскольку вы используете PrimeFaces 3.0, который, в свою очередь, требует Servlet 3.0, который, в свою очередь, поставляется вместе с EL 2.2, вы должны просто передать аргументы метода в EL. Вам нужно только изменить аргумент Locale на String, чтобы он также мог использоваться для передачи в качестве аргумента метода ссылки.

Кроме того, вы не должны полностью выбирать выбранный пользователем язык static. Он будет распространяться среди всех пользователей в одном приложении. Поэтому, если один пользователь меняет локаль, то каждый другой посетитель увидит последний выбранный пользователем язык! Вместо этого сделайте это нестатистическим свойством бинарного сеанса.

Таким образом, это должно сделать

<f:view locale="#{idiomaBean.locale}"> 
    <h:form> 
     <h:selectOneMenu value="#{idiomaBean.language}" onchange="submit()"> 
      <f:selectItems value="#{idiomaBean.availableLanguages}" /> 
     </h:selectOneMenu> 

     <h:panelGrid columns="3"> 
      <p:commandLink title="SP" action="#{idiomaBean.setLanguage('sp')}" update="@all"> 
       <p:graphicImage value="../images/paises/sp.png" /> 
      </p:commandLink> 
      <p:commandLink title="EN" action="#{idiomaBean.setLanguage('en')}" update="@all"> 
       <p:graphicImage value="../images/paises/en.png" /> 
      </p:commandLink> 
      <p:commandLink title="FR" action="#{idiomaBean.setLanguage('fr')}" update="@all"> 
       <p:graphicImage value="../images/paises/fr.png" /> 
      </p:commandLink> 
     </h:panelGrid> 
    </h:form> 
</f:view> 

с

@ManagedBean 
@SessionScoped 
public class IdiomaBean implements Serializable { 

    private Locale locale = FacesContext.getCurrentInstance().getViewRoot().getLocale(); 

    private static Map<String, String> availableLanguages; 

    static { 
     availableLanguages = new LinkedHashMap<String, String>(); 
     availableLanguages.put("Español", "es"); 
     availableLanguages.put("English", "en"); 
     availableLanguages.put("Français", "fr"); 
    } 

    public Map<String, String> getAvailableLanguages() { 
     return availableLanguages; 
    } 

    public Locale getLocale() { 
     return locale; 
    } 

    public String getLanguage() { 
     return locale.getLanguage(); 
    } 

    public void setLanguage(String language) { 
     locale = new Locale(language); 
     FacesContext.getCurrentInstance().getViewRoot().setLocale(locale); 
    } 

} 
+0

Спасибо за ваш быстрый annswer. Я сделал именно то, что вы мне сказали, но все равно не работал. Когда я отлаживаю, я вижу, что валентность языка изменилась, но никаких изменений языка не происходит. Я пробовал много решений, но ничего не работает. – amal

+0

Что именно не работает? Выпадающий список или ссылки, или и то, и другое? Аннотации '@ ManagedBean' и' @ SessionScoped' являются как из пакета 'javax.faces.bean', так? – BalusC

+0

Ничего не работает. Ну, я не использую аннотации для поддержки bean-компонентов, я объявляю их в файле-config-файла faces. Я также пробовал аннотации. Все еще не работает. Бэк-код правильно вызывается, а переменная задана, но не изменяется язык. Я действительно смущен, потому что я пробовал много учебников. Файлы сообщений должны быть в определенном пакете или что-то еще? – amal

Смежные вопросы