2010-02-16 17 views
7

Recientemente estuve profundizando en la localización con .NET. Esencialmente, aprendí cómo personalizar un formulario (usando las propiedades de Idioma y Localizable) y luego cambiar la cultura en consecuencia.Localización .NET; Fallback cuando utilizo ResourceManager

Sin embargo, descubrí que al migrar mis cadenas codificadas en inglés a los archivos de recursos generados automáticamente, y el uso de .GetString ("Clave") - bueno, digamos que no era feliz: P.

Decidí hacer un conjunto separado de archivos resx dedicados exclusivamente a las traducciones de cadenas codificadas. Siguieron la convención/requisito de [nombre]. [Código de cultura] .resx. Hice de estos para cada idioma relevante; p.ej. appstrings.de.resx (para alemán) y appstrings.resx (como línea base invariable).

Para utilizar estos nuevos recursos, he creado una instancia de ResourceManager y Recursos Conjunto

Dim resManager As New ResourceManager("LanguageTest.appstrings", Assembly.GetExecutingAssembly) 
Dim resSet As ResourceSet = resManager.GetResourceSet(My.Application.UICulture, True, True) 

se estableció la cultura de la interfaz de usuario actual (por ejemplo, al alemán) usando

My.Application.ChangeUICulture("de") 

Problema original

A menos que t él resSet.GetString ("Clave") se define explícitamente en el appstrings.de.resx, devolverá una cadena en blanco. ¿Hay alguna forma de que pueda recurrir a appstrings.resx (donde "Key" existe), que asumí que sería la línea base predeterminada?

actualización

Rhapsody hizo una sugerencia a continuación, mientras que la propia punta real no funciona, lo hizo en-hecho a provocar un punto interesante, usando resManager.GetString ("llave"), frente a RESSET .GetString ("Clave"). Esto parece funcionar sin defectos hasta el momento. Es decir, los valores presentes en el archivo de idioma especializado se devuelven, mientras que los valores "faltantes" se retrotraen a la cultura predeterminada cuando se accede mediante una sola tecla.

número posterior

La única cuestión que queda sería si el impacto en el rendimiento de la utilización de ResourceManger en contraposición a un ResourceSet caché será perjudicial que?

Respuesta

2

Trate

Public Function GetString(ByVal Name As String) As String 
    Return My.Resources.Strings.ResourceManager.GetString(Name) 
End Function 

Dónde Strings es el nombre de los archivos resx en su proyecto. Esto devolverá automáticamente el valor de referencia cuando no esté disponible para la cultura actual.

Es un ejemplo fácil, es posible que desee hacerlo más infalible.

+1

Lamentablemente, los recursos de "appstrings" no estaban presentes en el espacio de nombres My.Resources. Sin embargo, su solución de código plantea un punto interesante (ver pregunta actualizada) :). –

0

Una vez creado una aplicación web que tenía en-Estados Unidos como el idioma de reserva, pero tienen otras más específicas como .de basado en la configuración en el navegador de los usuarios web

Básicamente para que funcione fijo el xml en la web.config

<globalization uiCulture="auto" culture="auto" requestEncoding="utf-8" responseEncoding="utf-8"/> 

A partir de ahí he utilizado el ResourceManager estática interna del archivo .cs que se proporciona con su idioma predeterminado, por ejemplo,

Resources.<ResourceFileName>.ItemSearchNoResultsErrorText 

y en los archivos .aspx:

<%$ Resources:<ResourceFileName>, TimeSelect %> 

Como lo entiendo entonces es significativa en el archivo .cs que contiene las vidas de clase ResourceManager, es que detrás del archivo de idioma o la .de lenguaje alternativo? Como se compila como un conjunto de satélites separado, depende de dónde se compila la clase .cs y del ensamblaje de satélites del que forma parte.

Como regla Siempre he tenido la clase ResourceManager como un código detrás en el idioma en-US, porque esa es la que quiero usar como el idioma de reserva si los más específicos no se encuentran

Uso esta configuración nunca obtuve un valor en blanco, siempre utilizo el lenguaje alternativo, aunque cambio los ensamblajes satelitales en tiempo de ejecución.

+0

He leído, sin embargo, que usar el espacio de nombres de recursos es costoso (en términos de rendimiento general). He leído que es mejor crear un conjunto de recursos por separado para almacenar en caché las cadenas, mejorando así el rendimiento. Rhapsody está en el camino correcto con su respuesta. Es solo un detalle final que debe ser resuelto (ver el comentario de esa respuesta). –

4

Usted puede tratar de declarar una cultura por defecto para la aplicación de la siguiente manera

[assembly: NeutralResourcesLanguageAttribute("en-US", UltimateResourceFallbackLocation.Satellite)] 

Este código declara que su cultura por defecto es en-US. En su ejemplo, si la cultura actual es "de-DE" busca recursos en "de-DE", luego busca la cultura "de" padre y así sucesivamente y Ultimamente va al archivo de recursos de cultura definida (en-US) . see MSDN para estrategias de respaldo por resourceManage. El código anterior va normalmente en assenblyInfo.cs. El segundo parámetro le dice al administrador de recursos dónde se encuentran los recursos ubicados en el ensamblaje principal o satélite.

Desafortunadamente, en esta solución debe utilizar un nombre de cultura, no el nombre del archivo de recursos. sin embargo, puede extender RM para usar un recurso específico por nombre de archivo, pero es mucho más sencillo seleccionar una cultura predeterminada y cambiar el nombre de su archivo de recursos a esa cultura y tiene la solución lista para usar.