Форум » GUI » Изменение клавиатуры в HWGui 2.23 b5 » Ответить

Изменение клавиатуры в HWGui 2.23 b5

Мирослав: Вот в чем дело: я бы хотел, чтобы, как только одна из моих программ запустилась, было следующее: - определить, какая клавиатура установлена, - сохранить эти данные в переменной, - установить клавиатуру на СЕРБСКУЮ КИРИЛЛИКУ, - после окончания работы вернуть оригинальную клавиатуру. Я пытался решить эту проблему разными способами, но у меня это не сработало. Поэтому я хотел бы попросить всех помочь мне сделать это. Привет из Сербии!

Ответов - 18

alkresin: Не совсем понятно, что вы имеете ввиду, когда хотите "установить клавиатуру"? Если речь идет о кодовой странице, то это делается Harbour-функцией hb_cdpSelect( codepage ), codepage в вашем случае, наверное, "SRWIN". Есть еще "SR646" и "SR646C" - вам виднее, какую использовать. Эта функция возвращает текущую кодовую страницу - если она ранее в программе не была установлена, то, наверное, будет "EN".

alkresin: Ну и, конечно, при выборе шрифта надо выбирать кириллицу.

Dima: alkresin он имел в виду , считать текущую раскладку клавы установить сербскую раскладку апосля вернуть раскладку что была


alkresin: А что за "текущая раскладка клавы"? Почему нам она не нужна?

Dima: вот что то типа такого ему надо http://clipper.borda.ru/?1-4-0-00000995-000-0-0-1642251621

Мирослав: Во-первых, позвольте мне извиниться перед всеми, если вы меня не так поняли. В школе я изучал русский язык (это было очень давно), поэтому, возможно, я плохо выразился. Попробую внести немного ясности: - Перед запуском моей программы установлена ​​следующая клавиатура: ENG US (или любая другая клавиатура), - При запуске моей программы я бы хотел, чтобы моя программа сменила клавиатуру на СЕРБСКУЮ КИРИЛЛИКУ: СРП - при завершении программы хотелось бы вернуть клавиатуру, которая была до запуска программы: ENG US , (то есть та клавиатура, которая была раньше). Ну, это мое желание, которое я не могу исполнить. Я надеюсь, что вы меня поняли. Привет из Сербии!

Andrey: Вот примерно так можно на МиниГуи... - [pre2]/* * MINIGUI - Harbour Win32 GUI library Demo * * Смена языка */ #define _HMG_OUTLOG #include "hmg.ch" REQUEST HB_CODEPAGE_RU1251, HB_CODEPAGE_RU866 // русский язык REQUEST HB_CODEPAGE_UA1251, HB_CODEPAGE_UA866 // украинский язык ///////////////////////////////////////////////////////////////////////// Function Main Local cLog, tTime := HB_DATETIME(), cTime := HB_TTOC( tTime ) Local cKey, cRu, cKeyIsx cLog := _SetGetLogFile( "_msg.log" ) fErase( cLog ) ? REPL("=",20) + " Start [ " + cTime + " ] " + REPL("=",20) ? MiniGuiVersion() cKey := cKeyIsx := KB_LANG() ? "Клавиатура=", cKey ? "Переключить на русский !" KB_RUS() cKey := KB_LANG() ?? "Клавиатура=", cKey InkeyGui(1000) ? "Переключить на украинский !" KB_UKR() cKey := KB_LANG() ?? "Клавиатура=", cKey InkeyGui(1000) // здесь самому надо сделать переключение на исх.клавиатуру ? "cKeyIsx=", cKeyIsx ? REPL("=",20) + " End [ " + HMG_TimeMS( tTime ) + " ] " + REPL("=",20) ShellExecute( 0, "Open", cLog,,, 1 ) Return Nil /*------------------------------------------------------------------------------ * http://clipper.borda.ru/?1-4-0-00000995-000-0-0-1408978369 */ Function KB_LANG() Local rsl, cRet := "???" rsl := RASKLADKA() IF rsl == "00000409" cRet := "ENG" ELSEIF rsl == "00000419" cRet := "RUS" ELSEIF rsl == "00020422" cRet := "UKR" ELSE cRet := rsl ENDIF return cRet #pragma BEGINDUMP #include "Windows.h" #include "hbapi.h" HB_FUNC(KB_RUS) { LoadKeyboardLayout("00000419", KLF_ACTIVATE) ; } HB_FUNC(KB_ENG) { LoadKeyboardLayout("00000409", KLF_ACTIVATE) ; } HB_FUNC(KB_UKR) { LoadKeyboardLayout("00020422", KLF_ACTIVATE) ; } HB_FUNC(RASKLADKA) { TCHAR m_PreviousLayout[KL_NAMELENGTH] ; GetKeyboardLayoutName(m_PreviousLayout); hb_retc(m_PreviousLayout); } #pragma ENDDUMP [/pre2]

alkresin: С русским у вас все нормально, я просто не сразу понял, о чем идет речь - может, потому, что идея переключать раскладку клавиатуры из программы мне в голову не приходила. В HwGUI не предусмотрено для этого специальной функции. Возможно, вам поможет материал по ссылке от Димы чуть выше. Хотя я попробовал на скорую руку - переключить не получилось.

alkresin: Попробовал еще раз - работает, но в том случае, если вставить функцию переключения раскладки непосредственно там, где есть ввод с клавиатуры - например в диалоге с edit control перед ACTIVATE DIALOG. Пробовал в начале программы: kb_rus() hwg_MsgInfo( kb_lang() ) hwg_writelog( kb_lang() ) Раскладка устанавливается, но сразу сбрасывается обратно, как только запускается диалоговый бокс без ввода (hwg_msginfo()).

alkresin: В HwGUI, оказывается), есть функция для смены раскладки: hwg_activatekeyboardlayout( cCode ), где cCode - код нужной раскладки, для русской - "00000419". Надо будет добавить функцию типа hwg_getkeyboardlayout() на основе предложенной здесь Raskladka(): HB_FUNC( HWG_GETKEYBOARDLAYOUT ) { TCHAR m_PreviousLayout[KL_NAMELENGTH]; GetKeyboardLayoutName( m_PreviousLayout ); hb_retc( m_PreviousLayout ); }

Мирослав: Я перепробовал все предложенные вами варианты, но ни один из них не помог. Некоторое время назад я работал над программой в HMG 3.5, и тогда мне нужно было переключить клавиатуру. Я задал вопрос на их форуме и получил ответ, а именно код, который я использовал в своих программах и он работал корректно. Я поместил тот же код в программу на HWGui 2.22 b4, и она работала нормально. Что ж, когда я поместил тот же код в программу в HWGui 2.23 b5, она не работала должным образом. Я думаю, что в самом коде HWGui 2.23 b5 есть какие-то глюки, которые не позволяют этого сделать. Вот тот код, который корректно работал в HWGui 2.22 b4: #include "Hwgui.ch" #include "Common.CH" #include "Fileio.CH" #include "Directry.CH" #include "Plst.CH" REQUEST HB_CODEPAGE_UTF8EX // Латиница и ЋИРИЛИЦА //------------------------------------------------------------------------------------------------------------------------------------ FUNCTION Main() ... hb_SetCodepage( "UTF8EX" ) // Ћирилица ! PUBLIC ... ... ... PUBLIC cDefKLID := GetKeyboardLayoutName(), nDefHKL := GetKeyboardLayout() PUBLIC cSerbCyrKLID:="00000C1A", lReleaseLayout .... .... INIT WINDOW Form_1 MAIN ; AT 0, 0 SIZE 800, 600 STYLE WS_OVERLAPPED + WS_VISIBLE ; TITLE "ПРОГРАМ ЗА СЛАЊЕ ПЛАТНИХ ЛИСТИЋА ЕЛ. ПОШТОМ (e-mail) И ЦИРКУЛАРНИХ МЕЈЛОВА" ; ICON oIcon ; ON INIT { || lReleaseLayout:=SetAnyKeybd( cSerbCyrKLID ), lOk:=Inicijalizacija(), IIF( !lOk, hwg_EndWindow(), NIL ) } ; ON EXIT { || hwg_MsgYesNo("Завршити са радом програма?", "Крај рада програма" ) } ... ... ACTIVATE WINDOW Form_1 CENTER RETURN NIL //--------------------------------------------------------------------------------- //------------------------------------------------------------------------------- EXIT PROCEDURE VratiTastaturu() SetDefKeybd( lReleaseLayout, cSerbCyrKLID ) RETURN //------------------------------------------------------------------------------- .... .... .... //--------------------------------------------------------------------------------- FUNCTION SetAnyKeybd( cKLID ) LOCAL aLayoutList := GetKeyboardLayoutList(), nHKL, lIsLoadedAnyHKL := .F. IF UPPER( cDefKLID ) == UPPER( cKLID ) //already serbian cyr layout is active RETURN .F. ENDIF FOR EACH nHKL IN aLayoutList IF GetKeyboardLayoutName( nHKL ) == UPPER( cKLID ) // serbian cyr layout is loaded lIsLoadedAnyHKL := .T. ActivateKeyboardLayout( nHKL , 0x00000008) EXIT ENDIF NEXT IF !lIsLoadedAnyHKL LoadKeyboardLayout( cKLID, 0x0000001 ) ENDIF RETURN !lIsLoadedAnyHKL //--------------------------------------------------------------------------------- //--------------------------------------------------------------------------------- FUNCTION SetDefKeybd( lReleaseLayout, cKLID ) ActivateKeyboardLayout( nDefHKL, 0x00000008 ) IF lReleaseLayout UnLoadKeyboardLayout( cKLID ) ENDIF RETURN NIL //-------------------------------------------------------------------------------- #pragma BEGINDUMP #include "hbapi.h" #include "hbapiitm.h" #include "hbvm.h" #include "hbstack.h" #include "item.api" #include <shlobj.h> #include <windows.h> typedef unsigned quant; #define NIL '\0' HB_FUNC ( LOADKEYBOARDLAYOUT ) { // http://msdn.microsoft.com/en-us/library/windows/desktop/dd318693(v=vs.85).aspx TCHAR *cKLID = (TCHAR*) hb_parc (1); UINT Flags = (UINT) hb_parni (2); HKL hkl = LoadKeyboardLayout (cKLID, Flags); hb_retnl ((LONG_PTR) hkl ); } HB_FUNC ( UNLOADKEYBOARDLAYOUT ) { HKL hkl = (HKL) hb_parnl (1); hb_retl ((BOOL) UnloadKeyboardLayout (hkl)); } HB_FUNC ( GETKEYBOARDLAYOUTNAME ) { TCHAR cKLID [ KL_NAMELENGTH + 1 ]; GetKeyboardLayoutName (cKLID); hb_retc (cKLID); } HB_FUNC ( GETKEYBOARDLAYOUTLIST ) { int nCount = GetKeyboardLayoutList (0, NULL); if ( nCount > 0 ) { int i; hb_reta (nCount); HKL List [nCount]; GetKeyboardLayoutList (nCount, List); for (i=0; i < nCount; i++) hb_storvnl ((LONG_PTR) List , -1, i+1); } } HB_FUNC ( GETKEYBOARDLAYOUT ) { DWORD idThread = (DWORD) hb_parni (1); // Zero for the current thread HKL hkl = GetKeyboardLayout (idThread); hb_retnl ((LONG_PTR) hkl ); } HB_FUNC ( ACTIVATEKEYBOARDLAYOUT ) { HKL hkl = (HKL) hb_parnl (1); UINT Flags = (UINT) hb_parni (2); HKL old_hkl = ActivateKeyboardLayout (hkl, Flags); hb_retnl ((LONG_PTR) old_hkl ); } #pragma ENDDUMP приведенный выше код отлично работал в HWGui 2.22 b4, и не работает в HWGui 2.23 b5. Почему?

alkresin: Откомпилировал ваш пример (с Mingw, bcc ругается на C код), только убрал вызов Inicijalizacija(), которой нет в коде, заменил hb_SetCodepage() (нет такой функции) на hb_cdpSelect() и изменил cSerbCyrKLID на "00000419". При запуске раскладка изменяется на русскую, при выходе - опять английская, т.е., вроде, работает. И, кстати, hwg_activatekeyboardlayout() работает.

Мирослав: Код смены клавиатуры мне прислали участники форума HMG 3.5, и я прикрепил его здесь полностью (так, как они его написали). Вот почему в этом коде есть activatekeyboardlayout(). Функция Inicijalizacija() не имеет значения для смены клавиатуры, поэтому ее можно опустить. Если у вас есть время, попробуйте скомпилировать этот код в HWGui 2.23 b5 и посмотрите, будет ли он работать.

alkresin: Вот полностью рабочий пример, вам надо только заменить в ON INIT "00000419" на свой код: #include "hwgui.ch" STATIC cOrigLayout FUNCTION Main LOCAL oMainWindow cOrigLayout := hwg_GetKeyboardLayout() INIT WINDOW oMainWindow MAIN TITLE "Example" AT 200, 0 SIZE 400, 150 MENU OF oMainWindow MENUITEM "&Exit" ACTION hwg_EndWindow() MENUITEM "&Get a value" ACTION DlgGet() ENDMENU ACTIVATE WINDOW oMainWindow RETURN Nil FUNCTION DlgGet LOCAL oModDlg, oFont := HFont():Add( "MS Sans Serif", 0, - 13 ) LOCAL oGet, e1 := "Dialog from prg" INIT DIALOG oModDlg TITLE "Get a value" ; AT 210, 10 SIZE 300, 150 FONT oFont ; ON INIT {||hwg_activatekeyboardlayout( "00000419" )} ; ON EXIT {||hwg_activatekeyboardlayout( cOrigLayout ), .T.} @ 20, 10 SAY "Input something:" SIZE 260, 22 @ 20, 35 GET oGet VAR e1 SIZE 260, 26 @ 20, 90 BUTTON "Ok" ID IDOK SIZE 100, 32 @ 180, 90 BUTTON "Cancel" ID IDCANCEL SIZE 100, 32 ACTIVATE DIALOG oModDlg oFont:Release() RETURN Nil #pragma BEGINDUMP #include "hwingui.h" #include "hbapi.h" HB_FUNC( HWG_GETKEYBOARDLAYOUT ) { TCHAR m_PreviousLayout[KL_NAMELENGTH]; GetKeyboardLayoutName( m_PreviousLayout ); HB_RETSTR( m_PreviousLayout ); } #pragma ENDDUMP Обратите внимание, что смена раскладки работает только если текущее окно содержит edit control, или, может, другой control, в который что-то вводится. Ваш код, как я говорил, у меня тоже работает (HwGUI 2.23 dev build 7), но в нем что-то не так, лень проверять, что именно - после выхода из программы раскладки вообще пропадают из системы. Не думаю, что это может зависеть от версии HwGUI или любого другого GUI, так как эти функции - чистые вызовы windows api, они и из консоли должны работать. Но попозже проверю и на build 5.

alkresin: Попробовал свой пример из предыдущего поста с build 5 и build 6. Интересная картина). Раскладка меняется только когда я устаналиваю фокус в edit control. В моей текущей build 7 фокус на edit control устанавливается сразу (не знаю, почему - вроде, ничего что на это могло повлиять, не делал), поэтому раскладка меняется сразу при открытии диалога. Так или иначе, можно сказать, что работает.

Мирослав: Действительно необычная ситуация. Однако мне нужно, чтобы клавиатура менялась сразу при запуске программы, а не только тогда, когда фокус находится на «edit control». Тогда ничего, подожду появления новой "build xy", в которой такой проблемы не будет. Я благодарю всех, кто мне помог, особенно alkresin. Привет из Сербии!

alkresin: Предлагаю такой трюк для решения проблемы: открыть диалог с edit, установить раскладку и тут же закрыть его. Вот работающий пример: #include "hwgui.ch" STATIC cOrigLayout FUNCTION Main LOCAL oMainWindow cOrigLayout := hwg_GetKeyboardLayout() SetKeyboard( "00000419" ) INIT WINDOW oMainWindow MAIN TITLE hwg_version() AT 200, 0 SIZE 400, 150 ACTIVATE WINDOW oMainWindow SetKeyboard( cOrigLayout ) RETURN Nil STATIC FUNCTION SetKeyboard( cCode ) LOCAL oDlg INIT DIALOG oDlg TITLE "1" AT 210, 10 SIZE 20, 20 @ 0,0 EDITBOX "" SIZE 10, 10 ACTIVATE DIALOG oDlg NOMODAL hwg_activatekeyboardlayout( cCode ) oDlg:Close() RETURN Nil #pragma BEGINDUMP #include "hwingui.h" #include "hbapi.h" HB_FUNC( HWG_GETKEYBOARDLAYOUT ) { TCHAR m_PreviousLayout[KL_NAMELENGTH]; GetKeyboardLayoutName( m_PreviousLayout ); HB_RETSTR( m_PreviousLayout ); } #pragma ENDDUMP

Мирослав: alkresin, ваш трюк полностью сработал! Попробовал, вставил в свою программу и теперь все работает нормально. Спасибо!



полная версия страницы