Last active
March 13, 2021 09:28
-
-
Save preetpalS/d2482d6ec91eb8147e6cff43ab197ed5 to your computer and use it in GitHub Desktop.
AutoHotKey script replacement in D for multi-monitor window maximization (Windows only)
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Compilation tested with ldc2 and dmd. D BetterC compatible. | |
// I compile with: ldc2 -O3 -release -mcpu=native -m64 -betterC -static main.d | |
// import core.stdc.stdio : printf; | |
// import std.stdio; | |
import core.sys.windows.windows; | |
import core.sys.windows.winuser; | |
pragma(lib, "user32.lib"); | |
__gshared bool altPressed = false; | |
__gshared bool controlPressed = false; | |
__gshared bool shiftPressed = false; | |
__gshared bool winkeyPressed = false; | |
// No predefined constant for this | |
immutable DWORD VIRTUAL_KEY_CODE_QUESTION_MARK = 0xbf; | |
version (D_BetterC) { | |
extern (Windows) int WinMain(HINSTANCE _hInstance, HINSTANCE _hPrevInstance, LPSTR _lpCmdLine, int _nCmdShow) | |
{ | |
return mainloop(); | |
} | |
} else { | |
int main() { return mainloop(); } | |
} | |
int mainloop() | |
{ | |
// Ensures only one instance of application can run at one time | |
HANDLE globalMutexHandle = CreateMutex(NULL, true, "multi-monitor-window-maximization"); | |
if (globalMutexHandle == NULL) { | |
return -1; | |
} | |
DWORD lastErrorAfterMutexCreationAttempt = GetLastError(); | |
if (lastErrorAfterMutexCreationAttempt == ERROR_ALREADY_EXISTS) { | |
return -2; | |
} if (lastErrorAfterMutexCreationAttempt == ERROR_INVALID_HANDLE) { | |
return -3; | |
} | |
scope(exit) { | |
ReleaseMutex(globalMutexHandle); | |
CloseHandle(globalMutexHandle); | |
} | |
HHOOK hook = SetWindowsHookEx(WH_KEYBOARD_LL, cast(HOOKPROC) &hookProc, null, 0u); | |
if(hook is null) | |
{ | |
// printf("Exited with code : %u", GetLastError()); | |
return -4; | |
} | |
scope(exit) UnhookWindowsHookEx(hook); | |
MSG msg; | |
while(GetMessage(&msg, null, 0u, 0u)) | |
{ | |
TranslateMessage(&msg); | |
DispatchMessage(&msg); | |
} | |
return 0; | |
} | |
bool detectAndActivateShortcut(DWORD vkCode) { | |
if (winkeyPressed && shiftPressed) { | |
switch (vkCode) { | |
case VK_UP: | |
if (controlPressed) { | |
ultraMaximizeCurrentWindow(); | |
} else { | |
superMaximizeCurrentWindow(); | |
} | |
return true; | |
case VK_LEFT: | |
superLeftMaximizeCurrentWindow(); | |
return true; | |
case VK_RIGHT: | |
superRightMaximizeCurrentWindow(); | |
return true; | |
case VIRTUAL_KEY_CODE_QUESTION_MARK: | |
clearState(); | |
return true; | |
default: | |
break; | |
} | |
} | |
return false; | |
} | |
extern(Windows) LRESULT hookProc(in int nCode, in WPARAM wParam, in LPARAM lParam) | |
{ | |
if(nCode < 0) | |
return CallNextHookEx(null, nCode, wParam, lParam); | |
bool activated = false; | |
auto hookStruct = cast(KBDLLHOOKSTRUCT *) lParam; | |
if(wParam == WM_KEYDOWN || wParam == WM_SYSKEYDOWN) | |
{ | |
// printf("Pressed : %x", hookStruct.vkCode); | |
switch (hookStruct.vkCode) { | |
case VK_LSHIFT: // 0xA1 Left Shift Key | |
goto case; | |
case VK_RSHIFT: // 0xA2 Rigth Shift Key | |
shiftPressed = true; | |
// printf("Shift pressed"); | |
break; | |
case VK_LCONTROL: // 0xA3 Left Control Key | |
goto case; | |
case VK_RCONTROL: // 0xA4 Left Control Key | |
controlPressed = true; | |
break; | |
case VK_LMENU: // 0xA5 Left Alt Key | |
goto case; | |
case VK_RMENU: // 0xA6 Right Alt Key | |
altPressed = true; | |
break; | |
case VK_LWIN: // 0x5B Windows key | |
goto case; | |
case VK_RWIN: // 0x5C Windows key | |
winkeyPressed = true; | |
break; | |
case VK_SHIFT: // 0x10 Shift Key | |
shiftPressed = true; | |
// printf("Shift pressed"); | |
break; | |
case VK_CONTROL: // 0x11 Control Key | |
controlPressed = true; | |
break; | |
case VK_MENU: // 0x12 Alt Key | |
altPressed = true; | |
break; | |
default: | |
activated = detectAndActivateShortcut(hookStruct.vkCode); | |
break; | |
} | |
} | |
else if(wParam == WM_KEYUP || wParam == WM_SYSKEYUP) | |
{ | |
// printf("Released : %x", hookStruct.vkCode); | |
switch (hookStruct.vkCode) { | |
case VK_LSHIFT: // 0xA1 Left Shift Key | |
case VK_RSHIFT: // 0xA2 Rigth Shift Key | |
shiftPressed = false; | |
// printf("Shift released"); | |
break; | |
case VK_LCONTROL: // 0xA3 Left Control Key | |
case VK_RCONTROL: // 0xA4 Left Control Key | |
controlPressed = false; | |
break; | |
case VK_LMENU: // 0xA5 Left Alt Key | |
case VK_RMENU: // 0xA6 Right Alt Key | |
altPressed = false; | |
break; | |
case VK_LWIN: // 0x5B Windows key | |
case VK_RWIN: // 0x5C Windows key | |
winkeyPressed = false; | |
break; | |
case VK_SHIFT: // 0x10 Shift Key | |
shiftPressed = false; | |
// printf("Shift released"); | |
break; | |
case VK_CONTROL: // 0x11 Control Key | |
controlPressed = false; | |
break; | |
case VK_MENU: // 0x12 Alt Key | |
altPressed = false; | |
break; | |
default: | |
break; | |
} | |
} | |
if (activated) { | |
return -1; | |
} else { | |
return CallNextHookEx(null, (activated ? -1 : nCode), wParam, lParam); | |
} | |
} | |
void superMaximizeCurrentWindow() { | |
changeWindowPosition(0, 0, 2560, 2520); | |
} | |
void ultraMaximizeCurrentWindow() { | |
changeWindowPosition(0, 0, 4000, 2520); | |
} | |
void superLeftMaximizeCurrentWindow() { | |
changeWindowPosition(0, 0, 1280, 2520); | |
} | |
void superRightMaximizeCurrentWindow() { | |
changeWindowPosition(1280, 0, 1280, 2520); | |
} | |
void changeWindowPosition(int x, int y, int width, int height) { | |
HWND foreground = GetForegroundWindow(); | |
if (foreground is null) { | |
// printf("No active window to maximize.\n"); | |
return; | |
} | |
int _wasPreviouslyVisibleP = ShowWindow(foreground, SW_RESTORE); | |
int _wasWindowResizedP = SetWindowPos(foreground, HWND_NOTOPMOST, | |
x, y, width, height, | |
SWP_ASYNCWINDOWPOS); | |
// if (wasWindowResizedP == 0) { | |
// printf("Failed to change window size and/or position\n"); | |
// } | |
// // Alternative implementation (needs work, only tested in one configuration (contains hard-coded values)) | |
// HWND foreground = GetForegroundWindow(); | |
// if (foreground is null) { | |
// stderr.writeln("No active window to maximize."); | |
// return; | |
// } | |
// POINT point = POINT(0,0); | |
// HMONITOR mainMonitorHandle = cast(HMONITOR)MonitorFromPoint(point, MONITOR_DEFAULTTOPRIMARY); | |
// if (mainMonitorHandle == null) { | |
// writeln("Failed to get main monitor handle"); | |
// return; | |
// } | |
// MONITORINFO mainMonitorInfo; | |
// int monitorInfoRetrievalSuccessP = GetMonitorInfo(mainMonitorHandle, &mainMonitorInfo); | |
// if (monitorInfoRetrievalSuccessP == 0) { | |
// writeln("Failed to retrieve monitor info."); | |
// return; | |
// } | |
// RECT rcMonitor = mainMonitorInfo.rcMonitor; | |
// int _wasPreviouslyVisibleP = ShowWindow(foreground, SW_RESTORE); | |
// int wasWindowResizedP = SetWindowPos(foreground, HWND_NOTOPMOST, | |
// ((rcMonitor.right - rcMonitor.left) / 2), rcMonitor.top, | |
// ((rcMonitor.right - rcMonitor.left) / 2), 2520, | |
// SWP_ASYNCWINDOWPOS); | |
// if (wasWindowResizedP == 0) { | |
// writeln("Failed to change window size and/or position"); | |
// } | |
} | |
void clearState() { | |
shiftPressed = false; | |
controlPressed = false; | |
altPressed = false; | |
winkeyPressed = false; | |
// printf("Cleared state.\n"); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment