2010-02-16 4 views
7

Récemment, je me suis intéressé à la localisation avec .NET. Essentiellement, j'ai appris comment personnaliser un formulaire (en utilisant la propriété Language et Localizable) et ensuite changer la culture en conséquence.Localisation .NET; Langue de repli lors de l'utilisation de ResourceManager

Cependant, j'ai trouvé que lors de la migration de mes chaînes anglaises codées en dur dans les fichiers de ressources générés automatiquement, et d'utiliser .GetString ("Key") - bien, disons simplement qu'il n'était pas heureux: P.

J'ai décidé de créer un ensemble séparé de fichiers resx dédiés uniquement aux traductions de chaînes codées en dur. Ils ont suivi la convention/exigence de [nom]. [Code-culture] .resx. J'ai fait de ceux-ci pour chaque langue pertinente; par exemple. appstrings.de.resx (pour l'allemand) et appstrings.resx (comme ligne de base invariante).

Pour utiliser ces nouvelles ressources, je créé une instance de ResourceManager et des ressources Set

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

La culture d'interface utilisateur actuelle a été fixé (par exemple, allemand) en utilisant

My.Application.ChangeUICulture("de") 

Version originale

À moins que t Le resSet.GetString ("Key") est explicitement défini dans le appstrings.de.resx, il retournera une chaîne vide. Y at-il de toute façon que je peux le faire tomber à appstrings.resx (où "clé" existe), que je supposais être la ligne de base par défaut?

Mise à jour

Rhapsody fait une suggestion ci-dessous, tandis que la pointe réelle elle-même ne fonctionne pas, il ne fait en étincelle un point intéressant, en utilisant resManager.GetString (« Key ») par opposition à resSet .GetString ("Clé"). Cela semble fonctionner sans faille jusqu'à présent. C'est-à-dire que les valeurs présentes dans le fichier de langue spécialisé sont renvoyées, tandis que les valeurs «manquantes» reviennent à la culture par défaut lorsqu'elles sont accédées par une seule clé.

émission ultérieure

La seule question qui reste est de savoir si l'impact sur les performances de l'utilisation ResourceManger par opposition à un cache ResourceSet sera que préjudiciable?

Répondre

2

Essayez

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

Strings est le nom des resx dans votre projet. Cela renvoie automatiquement la valeur de référence lorsqu'elle n'est pas disponible pour la culture en cours.

C'est un exemple facile, vous pourriez vouloir le rendre plus infaillible.

+1

Malheureusement, les ressources 'appstrings' n'étaient pas présentes dans l'espace de noms My.Resources. Cependant, votre solution de code soulève un point intéressant (voir la question mise à jour) :). –

0

Une fois, je créé une application web qui avait en États-Unis comme la langue de repli mais ont d'autres plus spécifiques comme .de en fonction des paramètres dans les utilisateurs navigateur Web

Fondamentalement, pour le faire fonctionner, je mis le xml dans le web.config

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

De là, j'ai utilisé le ResourceManager statique interne à partir du fichier .cs qui est fourni avec votre langue par défaut, par exemple

Resources.<ResourceFileName>.ItemSearchNoResultsErrorText 

et dans les fichiers .aspx:

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

Si je comprends bien, alors il est important où votre fichier .cs qui contient la vie de la classe ResourceManager, est derrière le fichier de langue .de ou langue de secours? Comme il est compilé en tant qu'ensemble satellite séparé, il dépend de l'endroit où la classe .cs est compilée et de l'assemblage satellite dont elle fait partie.

En règle générale, j'ai toujours eu la classe ResourceManager comme un code derrière la langue en États-Unis parce que c'est celui que je veux utiliser comme langue de secours si les plus spécifiques ne sont pas trouvés

aide Dans cette configuration, je n'ai jamais une valeur vide, elle utilise toujours le langage de repli, même si j'échange les assemblys satellites lors de l'exécution.

+0

J'ai lu cependant que l'utilisation de l'espace de noms Resources est coûteuse (en termes de performances de l'overhead). J'ai lu qu'il est préférable de créer un ensemble de ressources distinct pour mettre en cache les chaînes, améliorant ainsi les performances. Rhapsody est sur la bonne voie avec sa réponse. C'est juste un détail final qui doit être résolu (voir le commentaire de cette réponse). –

4

Vous pouvez déclarer une valeur par défaut de la culture pour l'application comme ci-dessous

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

Ce code déclare que votre culture par défaut est en-US. Dans votre exemple, si la culture actuelle est "de-DE", elle recherche la ressource dans "DE-DE", puis recherche la culture "de" parente et ainsi de suite et Ultimatly passe au fichier de ressources de culture définie (en-US). . see MSDN pour les stratégies de secours par resourceManage. Le code ci-dessus va normalement dans le assenblyInfo.cs. Le second paramètre indique au gestionnaire de ressources où se trouvent les ressources situées dans l'assemblage principal ou par satellite. Malheureusement, dans cette solution, vous devez utiliser un nom de culture, pas le nom du fichier de ressources. Cependant, vous pouvez étendre RM pour utiliser une ressource spécifique par nom de fichier, mais il est plus simple de choisir une culture par défaut et de renommer votre fichier de ressources à cette culture et vous avez la solution hors de la boîte.

Questions connexes