Skip to content

Commit

Permalink
Initial commit
Browse files Browse the repository at this point in the history
  • Loading branch information
edanko committed Feb 13, 2022
1 parent 727cacb commit 24240df
Show file tree
Hide file tree
Showing 7 changed files with 346 additions and 0 deletions.
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
*.err
*.exe
*.obj
19 changes: 19 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
# capslang

This small windowless program allow you swich keyboard layout with CapsLock key. While non-standard keyboard layout will bright Scroll Lock indicator. Usual Caps Lock function available via Shift + CapsLock key combination. I recommend set "To turn off Caps Lock -- SHIFT key" in Windows Advanced Key Settings.

Forked from [here](http://flydom.ru/capslang).

## Complation
You can compile it using Visual Studio or [lccwin32](https://lcc-win32.services.net/)

Project file for lccwin32 included.

## Installation
Copy caps-min.exe to your Startup (%AppData%\Microsoft\Windows\Start Menu\Programs\Startup) folder.

## Run
Just run caps-min.exe and enjoy

## Exit
To close programm press Ctrl + Alt + L
132 changes: 132 additions & 0 deletions caps-min.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,132 @@
/*
CapsLang by Ryurik 2003-11-12, updated 2006-10-24
This small windowless program allow you swich keyboard layout with CapsLock key.
While non-standard keyboard layout will bright Scroll Lock indicator
Installation: copy capslang.exe to your Startup (Start -> Programs) folder.
Run: Just run capslang.exe and enjoy
Exit: To close programm press Ctrl + Alt + L
Note: Does not work with Win9x!
Эта программа позволяет переключать раскладку клавиатуры кнопкой CapsLock.
Для обычного использования CapsLock следует нажать Shift+CapsLock.
Рекомендуется установить в Windows отключение режима CapsLock клавишей Shift
При использовании альтернативной раскладки загорается индикатор ScrollLock.
Для выхода из программы следует нажать Ctrl + Alt + L.
Программа предназначена для работы в операционных системах Windows 2000/XP.
*/

#define _WIN32_WINNT 0x500

#include <windows.h>
#include <tchar.h>

#define WH_KEYBOARD_LL 13
typedef struct tagKBDLLHOOKSTRUCT {
DWORD vkCode;
DWORD scanCode;
DWORD flags;
DWORD time;
DWORD dwExtraInfo;
} KBDLLHOOKSTRUCT, FAR *LPKBDLLHOOKSTRUCT, *PKBDLLHOOKSTRUCT;

#define EXIT 33

HKL caps_default;
HHOOK caps_khook;
HANDLE caps_hEvent;
//UINT caps_key = VK_RCONTROL;
UINT caps_key = VK_CAPITAL;
#define INPUTLANGCHANGE_FORWARD 2

HWND GetCaretWindow()
{
// HWND Active = GetActiveWindow();
HWND Active = GetForegroundWindow();
/*
DWORD ThreadId = GetWindowThreadProcessId(Active, NULL);
GUITHREADINFO ThreadInfo;
ThreadInfo.cbSize = sizeof(GUITHREADINFO);
GetGUIThreadInfo(ThreadId, &ThreadInfo);
return ThreadInfo.hwndFocus;
*/
return Active;
}

LRESULT CALLBACK KbdHook(int nCode,WPARAM wParam,LPARAM lParam) {
if (nCode<0) return CallNextHookEx(caps_khook,nCode,wParam,lParam);
if (nCode==HC_ACTION) {
KBDLLHOOKSTRUCT *ks=(KBDLLHOOKSTRUCT*)lParam;
if (ks->vkCode==caps_key && (GetKeyState(VK_SHIFT)>=0)) {
if (wParam==WM_KEYDOWN) {
HWND hWnd=GetCaretWindow();
if (hWnd) {
PostMessage(hWnd,WM_INPUTLANGCHANGEREQUEST,0,(LPARAM)HKL_NEXT);
// PostMessage(hWnd,WM_INPUTLANGCHANGEREQUEST,(WPARAM)INPUTLANGCHANGE_FORWARD,0);
// PostMessage(hWnd,WM_INPUTLANGCHANGEREQUEST,(WPARAM)INPUTLANGCHANGE_FORWARD,(LPARAM)HKL_NEXT);
return TRUE;
}
}
}
}
skip:
return CallNextHookEx(caps_khook,nCode,wParam,lParam);
}

void failedx(const TCHAR *msg) {
MessageBox(NULL,msg,_T("CapsLang - Error"),MB_OK|MB_ICONERROR);
ExitProcess(1);
}

void failed(const TCHAR *msg) {
DWORD fm;
TCHAR *msg1,*msg2;
const TCHAR *args[2];

fm=FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER|FORMAT_MESSAGE_FROM_SYSTEM|
FORMAT_MESSAGE_IGNORE_INSERTS,NULL,GetLastError(),0,(LPTSTR)&msg1,0,NULL);
if (fm==0)
ExitProcess(1);
args[0]=msg;
args[1]=msg1;
fm=FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER|FORMAT_MESSAGE_FROM_STRING|
FORMAT_MESSAGE_ARGUMENT_ARRAY,_T("%1: %2"),0,0,(LPTSTR)&msg2,0,(va_list*)&args[0]);
if (fm==0)
ExitProcess(1);
MessageBox(NULL,msg2,_T("Capslang Exception"),MB_OK|MB_ICONERROR);
ExitProcess(1);
}

int APIENTRY WinMain(HINSTANCE hInst, HINSTANCE hInstPrev, LPSTR cmd, int show) {
MSG msg;

caps_hEvent=CreateEvent(NULL,TRUE,FALSE,_T("CapsLang"));
if (caps_hEvent==NULL)
failed(_T("CreateEvent()"));
if (GetLastError()==ERROR_ALREADY_EXISTS) {
failedx(_T("CapsLang is already running!"));
goto quit;
}

caps_default = GetKeyboardLayout(0);
if (RegisterHotKey(0,EXIT,MOD_CONTROL|MOD_ALT,'L')==0)
failed(_T("RegisterHotKey()"));

caps_khook=SetWindowsHookEx(WH_KEYBOARD_LL,KbdHook,GetModuleHandle(0),0);
if (caps_khook==0)
failed(_T("SetWindowsHookEx()"));

while (GetMessage(&msg,0,0,0)) {
TranslateMessage(&msg);
if(msg.message==WM_HOTKEY && msg.wParam==EXIT) PostQuitMessage(0);
DispatchMessage(&msg);
}

UnhookWindowsHookEx(caps_khook);
CloseHandle(caps_hEvent);
quit:
ExitProcess(0);
return 0;
}
136 changes: 136 additions & 0 deletions capslang.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,136 @@
/*
CapsLang by Ryurik 2003-11-12, updated 2006-10-24
This small windowless program allow you swich keyboard layout with CapsLock key.
While non-standard keyboard layout will bright Scroll Lock indicator
Installation: copy capslang.exe to your Startup (Start -> Programs) folder.
Run: Just run capslang.exe and enjoy
Exit: To close programm press Ctrl + Alt + L
Note: Does not work with Win9x!
Эта программа позволяет переключать раскладку клавиатуры кнопкой CapsLock.
Для обычного использования CapsLock следует нажать Shift+CapsLock.
Рекомендуется установить в Windows отключение режима CapsLock клавишей Shift
При использовании альтернативной раскладки загорается индикатор ScrollLock.
Для выхода из программы следует нажать Ctrl + Alt + L.
Программа предназначена для работы в операционных системах Windows 2000/XP.
*/

#define _WIN32_WINNT 0x500

#include <windows.h>
#include <tchar.h>

#define WH_KEYBOARD_LL 13
typedef struct tagKBDLLHOOKSTRUCT {
DWORD vkCode;
DWORD scanCode;
DWORD flags;
DWORD time;
DWORD dwExtraInfo;
} KBDLLHOOKSTRUCT, FAR *LPKBDLLHOOKSTRUCT, *PKBDLLHOOKSTRUCT;

#define EXIT 33

HKL caps_default;
HHOOK caps_khook;
HANDLE caps_hEvent;
UINT caps_key = VK_CAPITAL;

HWND GetFocusWindow()
{
return GetForegroundWindow();
}

void ToggleLight() {
keybd_event( VK_SCROLL,0,KEYEVENTF_EXTENDEDKEY | 0,0 );
keybd_event( VK_SCROLL,0,KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP,0 );
}

LRESULT CALLBACK KbdHook(int nCode,WPARAM wParam,LPARAM lParam) {
if (nCode<0) return CallNextHookEx(caps_khook,nCode,wParam,lParam);
if (nCode==HC_ACTION) {
KBDLLHOOKSTRUCT *ks=(KBDLLHOOKSTRUCT*)lParam;
if (ks->vkCode==caps_key && (GetKeyState(VK_SHIFT)>=0)) {
if (wParam==WM_KEYDOWN) {
HWND hWnd=GetFocusWindow();
if (hWnd) {
PostMessage(hWnd,WM_INPUTLANGCHANGEREQUEST,0,(LPARAM)HKL_NEXT);
ToggleLight();
return TRUE;
}
}
}
}
skip:
return CallNextHookEx(caps_khook,nCode,wParam,lParam);
}

void failedx(const TCHAR *msg) {
MessageBox(NULL,msg,_T("Capslang exception"),MB_OK|MB_ICONERROR);
ExitProcess(1);
}

void failed(const TCHAR *msg) {
DWORD fm;
TCHAR *msg1,*msg2;
const TCHAR *args[2];

fm=FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER|FORMAT_MESSAGE_FROM_SYSTEM|
FORMAT_MESSAGE_IGNORE_INSERTS,NULL,GetLastError(),0,(LPTSTR)&msg1,0,NULL);
if (fm==0)
ExitProcess(1);
args[0]=msg;
args[1]=msg1;
fm=FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER|FORMAT_MESSAGE_FROM_STRING|
FORMAT_MESSAGE_ARGUMENT_ARRAY,_T("%1: %2"),0,0,(LPTSTR)&msg2,0,(va_list*)&args[0]);
if (fm==0)
ExitProcess(1);
MessageBox(NULL,msg2,_T("CapsLang - Error"),MB_OK|MB_ICONERROR);
ExitProcess(1);
}

void CALLBACK TimerCaps(HWND hWnd,UINT uMsg,UINT_PTR idEvent,DWORD dwTime) {
if ((GetKeyState(VK_SCROLL)>0) !=
// (GetKeyboardLayout(GetWindowThreadProcessId(GetAncestor(GetFocusWindow(), GA_PARENT),NULL))!=caps_default)) {
// (GetKeyboardLayout(GetCurrentThreadId())!=caps_default)) {
(GetKeyboardLayout(GetWindowThreadProcessId(GetFocusWindow(), NULL))!=caps_default)) {
ToggleLight();
}
}

int APIENTRY WinMain(HINSTANCE hInst, HINSTANCE hInstPrev, LPSTR cmd, int show) {
MSG msg;

caps_hEvent=CreateEvent(NULL,TRUE,FALSE,_T("CapsLang"));
if (caps_hEvent==NULL)
failed(_T("CreateEvent()"));
if (GetLastError()==ERROR_ALREADY_EXISTS) {
failedx(_T("CapsLang is already running!"));
goto quit;
}

if (SetTimer(NULL,0,700,TimerCaps)==0)
failed(_T("SetTimer()"));

caps_default = GetKeyboardLayout(0);
if (RegisterHotKey(0,EXIT,MOD_CONTROL|MOD_ALT,'L')==0)
failed(_T("RegisterHotKey()"));

caps_khook=SetWindowsHookEx(WH_KEYBOARD_LL,KbdHook,GetModuleHandle(0),0);
if (caps_khook==0)
failed(_T("SetWindowsHookEx()"));

while (GetMessage(&msg,0,0,0)) {
TranslateMessage(&msg);
if(msg.message==WM_HOTKEY && msg.wParam==EXIT) PostQuitMessage(0);
DispatchMessage(&msg);
}

UnhookWindowsHookEx(caps_khook);
CloseHandle(caps_hEvent);
quit:
ExitProcess(0);
return 0;
}
30 changes: 30 additions & 0 deletions capslang.prj
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
; Wedit project file. Syntax: Name = value
[capslang]
PrjFiles=1
File1=caps-min.c
ProjectFlags=0
Frame=788 443 1605 1202
StatusBar=0,0,0,0
Name=capslang
CurrentFile=E:\src\github.com\edanko\capslang\caps-min.c
OpenFiles=1
OpenFile1="E:\src\github.com\edanko\capslang\caps-min.c" 42 18 2 -2394 1013
ProjectPath=e:\src\github.com\edanko\capslang
SourcesDir=E:\src\github.com\edanko\capslang
Defines=
IncludeFilesCount=5
IncludeFile0=c:\lcc\include
Libraries=
LinkerArgs=
ProjectTime=388
MakeName=c:\lcc\bin\make.exe
MakeDir=E:\src\github.com\edanko\capslang\lcc
Exe=e:\src\github.com\edanko\capslang\lcc\caps-min.exe
DebuggerArguments=
DbgExeName=e:\src\github.com\edanko\capslang\lcc\caps-min.exe
DbgDir=e:\src\github.com\edanko\capslang\lcc
CompilerFlags=69
Useframework=0
NumberOfBreakpoints=0
ErrorFile=E:\src\github.com\edanko\capslang\lcc\capslang.err
NrOfFileProcessors=0
25 changes: 25 additions & 0 deletions lcc/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
# Wedit Makefile for project capslang
SRCDIR=e:\src\github.com\edanko\capslang
CFLAGS=-I"c:\lcc\include" -O
CC=$(LCCROOT)\bin\lcc.exe
LINKER=$(LCCROOT)\bin\lcclnk.exe
OBJS=\
caps-min.obj

LIBS=
EXE=caps-min.exe

$(EXE): $(OBJS) Makefile
$(LINKER) -s -subsystem windows -o $(SRCDIR)\lcc\caps-min.exe $(OBJS) $(LIBS)

# Build caps-min.c
CAPS-MIN_C=\

caps-min.obj: $(CAPS-MIN_C) $(SRCDIR)\caps-min.c
$(CC) -c $(CFLAGS) $(SRCDIR)\caps-min.c

link:
$(LINKER) -s -subsystem windows -o $(SRCDIR)\lcc\caps-min.exe $(OBJS) $(LIBS)

clean:
del $(OBJS) caps-min.exe
1 change: 1 addition & 0 deletions lcc/capslang.dep
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
[caps-min.c]

0 comments on commit 24240df

Please sign in to comment.