Download (cursors included)
Several times I came across the file "KlavaState_Cursor.pb" and I modified it a little.
One person gave me a link to this file and asked if it could be compiled for Linux. I said no, because it uses WinAPI. But I googled GTK3 functions and found gdk_cursor_new_from_pixbuf_(). But the presence of this function can only solve half of the problem; I also need to catch the layout switching event.
Code: Select all
EnableExplicit
#EnCode = $4090409
#RuCode = $4190419 ; set your native language... задайте свой родной язык
; https://www.autoitscript.com/autoit3/docs/appendix/OSLangCodes.htm
; $40c040c
; $4070407
#EnStr$ = "En"
#RuStr$ = "Ru" ; it will be written on the tray icon ... это будет написано на иконке в трее
; "Fr"
; "De"
#Window = 0
#SysTrayIcon = 0
#mClose = 0
#Timer = 0
#Menu = 0
#Font0 = 0
#Lang0 = 0
#Lang1 = 1
Global hRuCur, hEnCur, hDefault, hFont, hRuCurCopy, hEnCurCopy
; Structure Lang
; Array aLang.i(0)
; EndStructure
; Global aLang.Lang
Define CountLang
CountLang = GetKeyboardLayoutList_(0, 0)
If CountLang < 2
; MessageRequester("Error", "Используется один язык, нет смысла в этой программе", #MB_OK | #MB_ICONERROR)
MessageRequester("Error", "One language is used, there is no point in this program", #MB_OK | #MB_ICONERROR)
End
EndIf
; Debug "Number of languages: " + CountLang
; Debug "Число языков: " + CountLang
; ReDim aLang\aLang(CountLang - 1)
;
; GetKeyboardLayoutList_(CountLang, @aLang\aLang())
; ShowMemoryViewer(@aLang\aLang(), SizeOf(i) * 2)
; For i = 0 To ArraySize(aLang\aLang())
; Debug aLang\aLang(i) >> 16
; Debug aLang\aLang(i) & $FFF
; Next
hEnCur = LoadCursorFromFile_(@"En.cur")
hRuCur = LoadCursorFromFile_(@"Ru.cur")
hDefault = LoadCursorFromFile_(@"C:\Windows\Cursors\beam_m.cur")
If Not (hRuCur And hEnCur And hDefault)
; MessageRequester("Error", "Не удалось загрузить курсор", #MB_OK | #MB_ICONERROR)
MessageRequester("Error", "Failed to load cursor!", #MB_OK | #MB_ICONERROR)
End
EndIf
Procedure GetLayoutWindowActive()
Protected Layout
Static LayoutTemp
Layout = GetKeyboardLayout_(GetWindowThreadProcessId_(GetForegroundWindow_(), 0))
If LayoutTemp <> Layout
LayoutTemp = Layout
If Layout = #RuCode
ChangeSysTrayIcon(#SysTrayIcon, ImageID(#Lang0))
hRuCurCopy = CopyIcon_(hRuCur)
; функция уничтожает курсор после его переопределения, поэтому мы не можем применить его дважды без копирования.
SetSystemCursor_(hRuCurCopy, #OCR_IBEAM)
ElseIf Layout = #EnCode
ChangeSysTrayIcon(#SysTrayIcon, ImageID(#Lang1))
hEnCurCopy = CopyIcon_(hEnCur)
SetSystemCursor_(hEnCurCopy, #OCR_IBEAM)
Else
SetSystemCursor_(hDefault, #OCR_IBEAM)
EndIf
; Debug GetLastError_() ; 1402 = ERROR_INVALID_CURSOR_HANDLE
; https://learn.microsoft.com/ru-ru/windows/win32/Debug/system-error-codes--1300-1699-
; Debug Hex(Layout)
EndIf
EndProcedure
hFont = LoadFont(#Font0, "Tahoma", 9, #PB_Font_Bold | #PB_Font_HighQuality)
Procedure CreateIcon(id, Text$, ColorFR, ColorBG)
If CreateImage(id, 16 , 16, 24, ColorBG) And StartDrawing(ImageOutput(id))
; Box(0, 0, 16, 16, ColorBG)
DrawingMode(#PB_2DDrawing_Transparent)
DrawingFont(hFont)
DrawText(0, 0, Text$, ColorFR)
StopDrawing()
EndIf
EndProcedure
; Рисуем иконки. В идеале получить буквы языков
CreateIcon(#Lang0, #RuStr$, $006600, $00FF00)
CreateIcon(#Lang1, #EnStr$, $000055, $0000FF)
;-┌───GUI───┐
If OpenWindow(#Window, 0, 0, 100, 20, "", #PB_Window_Invisible)
AddSysTrayIcon(#SysTrayIcon, WindowID(#Window), ImageID(#Lang0))
; SysTrayIconToolTip(#SysTrayIcon, "Русский")
; SysTrayIconToolTip(#SysTrayIcon, "Russian")
If CreatePopupMenu(#Menu)
; MenuItem(#mClose, "Закрыть")
MenuItem(#mClose, "Close")
EndIf
SetTimer_(WindowID(#Window), #Timer, 200, @GetLayoutWindowActive())
;-┌───Loop───┐
Repeat
Select WaitWindowEvent()
Case #PB_Event_SysTray
If EventType() = #PB_EventType_RightClick
DisplayPopupMenu(#Menu, WindowID(#Window) )
EndIf
Case #PB_Event_Menu
If EventMenu() = #mClose
Break
EndIf
EndSelect
ForEver
;-└───Loop───┘
EndIf
KillTimer_(WindowID(#Window), #Timer)
CloseWindow(#Window)
SetSystemCursor_(hDefault, #OCR_IBEAM) ; возвращаем старый курсор, хотя это не возвращает ваш курсор.
DestroyCursor_(hEnCurCopy)
DestroyCursor_(hRuCurCopy)
DestroyCursor_(hRuCur)
DestroyCursor_(hEnCur)
; DestroyCursor_(hDefault)
End