![]() |
|
||||||||||
|
|||||||
|
|
« Предыдущая тема | Следующая тема » |
| Опции темы | Опции просмотра |
|
![]() |
![]() |
|
|||||
|
Регистрация: May 2011
Сообщений: 76
|
Есть клиентское приложение, в нём необходимо реализовать мультиязычность (т.е. при выборе юзером определенного языка, во всех необходимых местах заменять тексты на дефалтном языке, на тексты на необходимом.
На данный момент существует такая система: 1. Есть ХML в котором содержатся тексты на необходимом языке. Например текстфилду который в кнопке выхода ("exit_btn_text") соответствует текст "Exit" ну и т.д. 2. Есть класс который парсит этот ХML и меняет текст в необходимом элементе интерфейса. 3. В управляющем классе замена языков происходит при загрузке приложения и при выборе юзером необходимого языка в опциях. Вопрос следующего характера - как всю эту *****систему сделать более правильной, эргономичной и вообще как нормальные люди реализовывают такие вещи? |
|
|||||
|
Пара ключ-значение.
Например, можно сделать класс View, который содержит методы работы с тем, что может понадобиться вью. Например, getResource, для загрузки динамического контента или getLocaleText, возвращающий текст сразу в нужной локали. Т.е. локаль устанавливается где-то наверху, а элементы отображения делают что-то вроде:
__________________
Тут мужик танцует и поёт про флэш |
|
|||||
|
Регистрация: May 2011
Сообщений: 76
|
То есть ты предлагаешь написать класс который самостоятельно разыменовывает ВСЕ элементы интерфейса, а сама именовка происходит для каждого элемента по его названию?
т.е. код метода getLocaleText() будет какой-то такой? |
|
|||||
|
Реализаций может быть много. Я бы хранил тексты в разных xml файлах, типа en.xml, ru.xml и т.далее, а сам getLocaleText бы возвращал значение из этого xml. Например, interface.close - это тег interface, внутри тег close.
__________________
Тут мужик танцует и поёт про флэш |
|
|||||
|
Я загружаю из базы список текстов. А в флешке запихиваю все это в массив и где нужно вызываю через класс-обертку над массивом.
Что-то вроде: Button.Text = TextDictionary.Text(1); В зависимости от выбранного пользователем языка в массиве в TextDictionary в первом элементе будет лежать или "Выход" для русского или "Exit" для английского языка. Не знаю на сколько это правильно и экономично. Пока работает ![]()
__________________
interplanety |
|
|||||
|
Обращение к элементам по номеру непоказательно. Лучше использовать говорящие индексы, константы или как psycho tiger написал - теги xml.
|
|
|||||
|
Работает не трожь, не?
__________________
http://www.chessmax.ru |
|
|||||
|
блогер
Регистрация: Oct 2005
Адрес: Днепродзержинск - город Брежнева и других логопедов
Сообщений: 1,421
Записей в блоге: 4
|
Да, по тегам из xml или ключам из Object вытягивать строку. Что ещё. Для больших приложений удобнее сделать двухуровневую систему, т.е.
использовать например Почему ещё это всплывает - имеет смысл привязывать строку локализацию не к слову, а к конкретному месту. Т.е. неправильно: слово "играть" имеет ключ play и везде, где встречается слово играть используется getLocaleText("play"). Правильно: для каждого места, где встречается слово "играть", делается отдельный ключ. Потому что на разных языках там могут быть разные слова и даже на одном языке могут быть различия в регистре ("ИГРАТЬ", "играть", "играть!" и "Играть"). Подумать насчет того, что смена языка вызывает перезапуск приложения (или делается только при самом старте). Потому что смена языка в любом месте в любой момент достаточно сложна в реализации и никому на самом деле не нужна. Отдельная веселуха (особенно если есть смена языка в любой момент) - строки типа "Убито бобров 7 из 20, спасено деревьев - 7шт.". Не во всех языках удобно и вообще возможно, чтоб 7, 20 и 7 шли именно в таком порядке (лично мне такое встретилось в тексте просто "2 из 3", по-моему на тайском). Потому хороший вариант - написать функцию типа Которая из строки типа "Убито бобров [1] из [2], спасено деревьев - [1]шт." делала нужную вызовом типа
__________________
Бобры отвечают на вопросы не потому, что знают на них ответы; они отвечают потому, что их спрашивают. |
|
|||||
|
У нас такая штуковина, дабы не травмировать мозг запоминанием ключей, количества и назначения праметров для каждого ключа просто генерируется из таблицы с локализацией:
/** Какой-то текст с {parameter}-ом на ключ some_text */ //<-- это сгенерилось по дефолтному языку локализации - //чтобы не отвлекаться, не смотреть что значит ключ public static function some_text(parameter:String):String { return _values["some_text"].replace(/\{parameter\}/g, parameter);// Утрированно } Т.е. приведённый текст выглядел бы так: Для локализации объектов, а не интерфейса, конечно, так делать не надо и не получится, но для них и тучу ключей поддерживать не надо - просто берёшь ключ у игрового объекта и берешь по нему название этого объекта - такой ключ не захардкожен, его нет в коде. По поводу динамической замены языка - ни разу не приходилось делать (не требовалось), но возможны варианты: 1. Как в fl-компонентах - регистрируем прямо в локализаторе текстовые поля с ключом и при перезагрузке он их обновляет 2. Вручную подписываемся на локализатор во всех окошках и меняем все тексты при событии "изменился язык" 3. Делаем наследника TextField, который уже слушает изенения и сам себя меняет и используем его везде. А если сторонние компоененты используюся? - оборачивать? Проблемы тут 2: 1. Как везде поменять текст с минимальным количеством кода 2. Размеры, вот незадача, тоже у полей будут меняться и ведь нужно реагировать - менять размеры окон и панелей, или дикий запас пространства оставлять Вобщем, перечисленные 3 способа справляются с этими задачами с разным успехом. Последний раз редактировалось iNils; 11.06.2012 в 16:22. |
|
|||||
|
Локализация "на лету" у меня решается следующей схемой:
1. XML 2. Функция в которой регистрируется str_id и текстфилд которому присваевается строка с текущей локалью. Все помещается в хэш-таблицу ключом которой выступает str_id, а значением соответственно текстфилд. 3. При смене локали всем зарегистрированным текстфилдам присваевается соответсвующая новой локали строка. В общем случае такая схема удобна, проста и при необходимости может легко быть дополнена функционалом. Преимуществом является простая схема подписки на событие смены языка, точнее ее полное отсутствие. Один раз присваеваем значение и забываем про это. Я честно говоря, пока использовал такой подход только в одном-двух проектах, но думаю, теперь буду постоянно использовать. |
![]() |
![]() |
Часовой пояс GMT +4, время: 09:37. |
|
|
« Предыдущая тема | Следующая тема » |
|
|