Я просто не могу заставить локализацию работать.Как использовать локализацию в C#
У меня есть библиотека классов. Теперь я хочу создать файлы resx и вернуть некоторые значения на основе культуры потоков.
Как я могу это сделать?
Я просто не могу заставить локализацию работать.Как использовать локализацию в C#
У меня есть библиотека классов. Теперь я хочу создать файлы resx и вернуть некоторые значения на основе культуры потоков.
Как я могу это сделать?
strings.resx
.System.Threading
и System.Globalization
Выполнить этот код:
Console.WriteLine(Properties.strings.Hello);
Должен напечатать «Hello».
Теперь добавьте новый файл ресурсов с именем «strings.fr.resx» (обратите внимание на часть «fr», на которой будут представлены ресурсы на французском языке). Добавьте строковый ресурс с тем же именем, что и в strings.resx, но со значением на французском языке (Name = "Hello", Value = "Salut"). Теперь, если вы запустите следующий код, он должен напечатать Salut:
Thread.CurrentThread.CurrentUICulture = CultureInfo.GetCultureInfo("fr-FR");
Console.WriteLine(Properties.strings.Hello);
Что происходит, что система будет искать ресурс для «FR-FR». Он не найдет никого (так как мы указали «fr» в вашем файле »). Затем он вернется к проверке« fr », которую он находит (и использует).
Следующий код напечатает« Hello » «:
Thread.CurrentThread.CurrentUICulture = CultureInfo.GetCultureInfo("en-US");
Console.WriteLine(Properties.strings.Hello);
это потому, что он не находит какой-либо„“ресурс, а также нет„EN-US ан“ресурса, поэтому он вернется к значению по умолчанию, который является тот, который мы добавили из start
При необходимости вы можете создавать файлы с более конкретными ресурсами (например, strings.fr-FR.resx и strings.fr-CA.resx для французского во Франции и Канаде соответственно). В каждом таком файле вам понадобятся в добавьте ресурсы для тех строк, которые отличаются от ресурсов, на которые он будет возвращаться. Поэтому, если текст во Франции и Канаде одинаковый, вы можете поместить его в strings.fr.resx, в то время как строки, которые отличаются на канадском французском, могут переходить в strings.fr-CA.resx.
Это довольно просто, на самом деле. Создайте новый файл ресурсов, например Strings.resx
. Установить Access Modifier
в Public
. Используйте шаблон apprioriate, поэтому Visual Studio автоматически создаст класс доступа (в этом случае имя будет Strings
). Это ваш язык по умолчанию.
Теперь, когда вы хотите добавить, скажем, немецкую локализацию, добавить локализованный файл resx. В этом случае это будет обычно Strings.de.resx
. Если вы хотите добавить дополнительную локализацию, скажем, в Австрию, вы также создадите Strings.de-AT.resx
.
Теперь перейдите к созданию строки - допустим, строка с именем HelloWorld
. В вашем Strings.resx
добавьте эту строку со значением «Hello, world!». В Strings.de.resx
добавьте «Hallo, Welt!». И в Strings.de-AT.resx
добавьте «Servus, Welt!». Это до сих пор.
Теперь у вас есть сгенерированный класс Strings
, и он имеет свойство с геттером HelloWorld
. Приобретение этого свойства будет загружать «Servus, Welt!» когда ваш язык де-AT, «Hallo, Welt!, когда ваш язык - это любой другой язык (включая de-DE и de-CH) и« Hello, World! », когда ваш язык - это что-то еще. Если строка отсутствует в локализованной версии, диспетчер ресурсов автоматически будет перемещаться по цепочке от наиболее специализированного к инвариантному ресурсу.
Вы можете использовать класс ResourceManager
, чтобы узнать больше о том, как именно вы загружаете вещи. Сгенерированный класс Strings
использует его также.
Отличный ответ F.Mörk. Но если вы хотите обновить перевод или добавить новые языки после того, как приложение будет выпущено, вы застряли, потому что вам всегда приходится перекомпилировать его для генерации ресурсов .dll.
Вот решение для ручной компиляции ресурса dll. Он использует инструменты resgen.exe и al.exe (устанавливается с помощью sdk).
Скажем у вас есть файл ресурсов Strings.fr.resx, вы можете скомпилировать DLL ресурсов с помощью следующей партии:
resgen.exe /compile Strings.fr.resx,WpfRibbonApplication1.Strings.fr.resources
Al.exe /t:lib /embed:WpfRibbonApplication1.Strings.fr.resources /culture:"fr" /out:"WpfRibbonApplication1.resources.dll"
del WpfRibbonApplication1.Strings.fr.resources
pause
Не забудьте сохранить исходное пространство имен в именах файлов (здесь «WpfRibbonApplication1»)
Спасибо за комментарий о сохранении пространства имен (y), который - если пропущен - не будет генерировать никаких ошибок, а просто вернется к резервному ресурсу. –
Кроме того большой ответ @Fredrik MORK на строки, чтобы добавить локализацию в виде сделать следующее:
"Localizable"
к true
Language
свойство формы в языке, который вы хотите (с хорошей раскрывающемся с ними все в)Этот MSDN article on Localizing Windows Forms дает дополнительную информацию об этом.
В дополнении к @Eric Бол-Feysot ответа:
Благодаря спутниковым узлам, локализация может быть создана на основе .dll/EXE-файлах.Таким образом:
Существует малоизвестный инструмент под названием LSACreator (бесплатно для некоммерческого использования или купить вариант), который позволяет создавать локализации на основе .dll/EXE-файлов. Фактически, внутренне (в каталоге языкового проекта) он создает/управляет локализованными версиями файлов resx и компилирует сборку аналогично тому, как описано @ Eric Bole-Feysot.
В моем случае
[assembly: System.Resources.NeutralResourcesLanguage("ru-RU")]
в AssemblyInfo.cs предотвращено вещи работать как обычно.
Исправление и разработка @Fredrik Mörk ответ.
Strings.resx
ресурсов для вашего проекта (или другой файла)Access Modifier
в Public
(в открытой вкладке Strings.resx
файла)Hello
, значение Hello
)Visual Studio автогенерацию s соответствующий класс Strings
, который фактически размещен в Strings.Designer.cs
. Класс находится в том же пространстве имен, что можно было бы ожидать вновь созданный .cs
файл, который будет помещен в
Этот код всегда печатает Hello
, потому что это ресурс по умолчанию, и нет конкретного языка ресурсы не доступны:.
Console.WriteLine(Strings.Hello);
Теперь добавьте новый язык конкретного ресурса:
Strings.fr.resx
(для французского языка)Hello
, значение Salut
)Следующий код печатает Salut
:
Thread.CurrentThread.CurrentUICulture = CultureInfo.GetCultureInfo("fr-FR");
Console.WriteLine(Strings.Hello);
Какой ресурс используется, зависит от Thread.CurrentThread.CurrentUICulture
. Он устанавливается в зависимости от языка интерфейса пользователя Windows или может быть установлен вручную, как в этом примере. Узнать больше об этом here.
Вы можете добавить ресурсы страны, такие как Strings.fr-FR.resx
или Strings.fr-CA.resx
.
Строка для использования определяется в этом порядке приоритета:
Strings.fr-CA.resx
Strings.fr.resx
Strings.resx
Обратите внимание, что ресурсы, специфичные для языка, генерируют satellite assemblies.
Также узнайте, как CurrentCulture
отличается от CurrentUICulture
here.
В ответ можно ссылаться на «закулисную» сантехнику, выполняемую Visual Studio здесь: файл resx.designer.cs, что делает работу intellisense; спутниковые сборки, скомпилированные с библиотекой классов, которые необходимо развернуть с помощью сборной сборки и любых последующих проектов, которые ее используют, и т. д. Ответ прост и прост, но это не помогает объяснить, где ситуация может пойти не так, например, если вы не используете Visual Studio. – Tao
+1 сообщение! Вместо того, чтобы делать файлы вручную, попробуйте редактор ресурсов Zeta (http://www.zeta-resource-editor.com/index.html). Это бесплатно и помогает вам делать эти виды переводов МНОГО быстрее, чем просто в VS. – Killnine
Будет ли .net выбрать язык ОС, а затем автоматически установить для вас информацию о культуре? ... или нам нужно установить CurrentUICulture в код для другого языка? – noelicus