Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Delphi программирование > Общие вопросы Delphi
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 18.03.2012, 01:56   #1
Zer0
Форумчанин
 
Аватар для Zer0
 
Регистрация: 13.12.2007
Сообщений: 788
По умолчанию Принудительный вывод Exception на одном языке

Всем добрый вечер. Возникла проблема - получать сообщения Exception всегда на одном и том же языке, вне зависимости от региональных настроек системы (например использовать английский)
В интернете под NET было найдено такое решение http://stackoverflow.com/questions/1...users-language
Но в Delphi нет ChangeUICulture
Пробовал изменять локаль потока - продолжают выводиться на системном языке
Что еще можно попробовать? (нужно чтобы метод не требовал привилегий администратора)
благодарность - сюда (не забываем писать от кого)
Zer0 вне форума Ответить с цитированием
Старый 18.03.2012, 15:24   #2
GunSmoker
Старожил
 
Регистрация: 13.08.2009
Сообщений: 2,581
По умолчанию

А в приложении вообще-то есть строки на другом языке? По умолчанию в ваших программах есть только английский. Все прочие языки надо самому подключать.
Опытный программист на C++ легко решает любые не существующие в Паскале проблемы.
GunSmoker вне форума Ответить с цитированием
Старый 18.03.2012, 19:15   #3
Zer0
Форумчанин
 
Аватар для Zer0
 
Регистрация: 13.12.2007
Сообщений: 788
По умолчанию

Есть, но не вижу связи между текстами в программе и генерируемыми стандартными исключениями. Пример:

Хотя никаких намеков на иврит в программе нет
Цель - избежать именно таких моментов
благодарность - сюда (не забываем писать от кого)
Zer0 вне форума Ответить с цитированием
Старый 18.03.2012, 19:23   #4
GunSmoker
Старожил
 
Регистрация: 13.08.2009
Сообщений: 2,581
По умолчанию

Так ведь этот текст приходит не от вашей программы, а от ОС.

Большинство исключений генерируются с тем сообщением об ошибке, что указывает ваша программа. Поэтому вы их контролируете. Можете менять. Язык подменять.

Но некоторые сообщения приходят от других компонентов системы, не от вас.
Опытный программист на C++ легко решает любые не существующие в Паскале проблемы.
GunSmoker вне форума Ответить с цитированием
Старый 18.03.2012, 20:35   #5
Zer0
Форумчанин
 
Аватар для Zer0
 
Регистрация: 13.12.2007
Сообщений: 788
По умолчанию

По ссылке есть решение под .NET, насколько я понял - принудительное указание языка (системные исключения тоже начинают генерироваться на этом языке)
Логично предположить, что должно быть нечто аналогичное и для Delphi
благодарность - сюда (не забываем писать от кого)
Zer0 вне форума Ответить с цитированием
Старый 19.03.2012, 02:37   #6
GunSmoker
Старожил
 
Регистрация: 13.08.2009
Сообщений: 2,581
По умолчанию

.NET - это управляемое окружение, оно изолируется от нижележащей ОС слоем виртуальной машины. Там конечно всё будет под вашим контролем.

Собственно, в системе в большинстве случаев не будет установлен произвольный нужный вам язык (вы получите сообщение на другом, ближайшем доступном, языке).

Но если язык всё же установлен и код, который получает системные сообщения, находится под вашим контролем, то да, вы можете это сделать. Системные сообщения получаются по коду с использованием функции FormatMessage. По умолчанию Delphi передаёт туда 0 (и это поведение изменить нельзя), но вы можете передавать туда любое значение. Например:

Код:
function SysErrorMessageLang(ErrorCode: Cardinal; LangID: LANGID): String;
var
  Buffer: PChar;
  Len: Integer;
begin
  Len := FormatMessage(
    FORMAT_MESSAGE_FROM_SYSTEM or
    FORMAT_MESSAGE_IGNORE_INSERTS or
    FORMAT_MESSAGE_ARGUMENT_ARRAY or
    FORMAT_MESSAGE_ALLOCATE_BUFFER, nil, ErrorCode, LangID, @Buffer, 0, nil);
  try
    while (Len > 0) and (CharInSet(Buffer[Len - 1], [#0..#32, '.'])) do
      Dec(Len);
    SetString(Result, Buffer, Len);
  finally
    LocalFree(HLOCAL(Buffer));
  end;
end;

var
  Ru, En: String;
begin
  Ru := SysErrorMessageLang(ERROR_FILE_NOT_FOUND, MAKELANGID(LANG_RUSSIAN, SUBLANG_DEFAULT));
  En := SysErrorMessageLang(ERROR_FILE_NOT_FOUND, MAKELANGID(LANG_ENGLISH, SUBLANG_DEFAULT));
end;
Альтернативно, можно сменить язык UI, но эта возможность доступна только с XP и выше:

Код:
var
  LID: LangID;
begin
  Ru := SysErrorMessageLang(ERROR_FILE_NOT_FOUND);
  LID := MAKELANGID(LANG_ENGLISH, SUBLANG_DEFAULT);
  Win32Check(SetThreadUILanguage(LID) = LID);
  En := SysErrorMessageLang(ERROR_FILE_NOT_FOUND);
end;
Опытный программист на C++ легко решает любые не существующие в Паскале проблемы.
GunSmoker вне форума Ответить с цитированием
Старый 19.03.2012, 02:40   #7
GunSmoker
Старожил
 
Регистрация: 13.08.2009
Сообщений: 2,581
По умолчанию

P.S. Менять локаль потока - плохая идея. Об этом написано в описании самой функции SetThreadLocale и об этом же говорит разработчик Windows.
Опытный программист на C++ легко решает любые не существующие в Паскале проблемы.
GunSmoker вне форума Ответить с цитированием
Старый 19.03.2012, 08:39   #8
Zer0
Форумчанин
 
Аватар для Zer0
 
Регистрация: 13.12.2007
Сообщений: 788
По умолчанию

Большое спасибо, довольно познавательно.
Но есть небольшой минус (даже например для исключения в примере) использование первого метода не даст пути к файлу, а получать все возможные языки системы чтобы найти подходящий для замены - на мой взгляд извращение.
Метода SetThreadUILanguage у себя не нашел к сожалению, наверное это именно то что мне нужно. В каком модуле находится ее описание?
благодарность - сюда (не забываем писать от кого)
Zer0 вне форума Ответить с цитированием
Старый 19.03.2012, 08:45   #9
GunSmoker
Старожил
 
Регистрация: 13.08.2009
Сообщений: 2,581
По умолчанию

Понятия не имею, я его сам написал.

Поищите по .pas файлам в \Source. Если нет - то в JEDI Windows API Library. Если и там нет - то:
Код:
var
  SetThreadUILanguage: function(LID: LangID): LangID; stdcall; // kernel32.dll
С динамической загрузкой, разумеется.
Опытный программист на C++ легко решает любые не существующие в Паскале проблемы.
GunSmoker вне форума Ответить с цитированием
Старый 19.03.2012, 13:34   #10
Zer0
Форумчанин
 
Аватар для Zer0
 
Регистрация: 13.12.2007
Сообщений: 788
По умолчанию

А какие методы определения кода ошибки есть (кроме GetLastError, потому что не подходит)? Просто ERROR_FILE_NOT_FOUND не единственно возможный вариант
И возможно ли таким образом получить английский вариант ошибок класса TOleException?
благодарность - сюда (не забываем писать от кого)

Последний раз редактировалось Zer0; 19.03.2012 в 13:47.
Zer0 вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Вывод на одном и том же месте JinYa Assembler - Ассемблер (FASM, MASM, WASM, NASM, GoASM, Gas, RosAsm, HLA) и не рекомендуем TASM 3 23.09.2011 22:54
вывод текста на русском языке _elena Visual C++ 6 01.04.2011 11:26
Ввод-вывод на Языке С тотошкин Помощь студентам 1 16.01.2010 23:47
Как осуществить ввод данных в одном цикле, их обработку в другом, и вывод результатов в третьем? ReM Паскаль, Turbo Pascal, PascalABC.NET 5 11.11.2008 18:21
Как сделать все данные на одном языке? Python Microsoft Office Excel 2 29.01.2007 12:37