Skip to content

Commit

Permalink
Activation order & much more, CMake build
Browse files Browse the repository at this point in the history
After much deliberation and study, cmdtab has been rebuilt to support true activation order. What's that you say? Doesn't cmdtab--the best macOS-style app/window switcher for Windows--already support that? Well, cmdtab has been overpromising and underdelivering this whole time.

Previously cmdtab relied on the order that Windows gives its top-level windows in when the EnumWindows function is called, and that order is the Z-order. The Z-order and the activation order are in some circumstances different, and not so subtly at that. If you minimize a window it is sent to the bottom of the Z-order, and therefore, in versions of cmdtab prior to v1.5, that window would be displayed last in the cmdtab switcher, even if it was the window that was just in the foreground.

Windows has no documented API for querying the activation order of desktop windows, only the Z-order. This has put me on the path to discover the best way to keep track of the activation order of windows. There are many possible solutions to this, each with merits, quirks, gotchas, both subtle and not. Especially minimizing any involvement with the going-ons of the Windows shell was a goal. Although in hindsight the solution in cmdtab is at once obvious, it was nevertheless arrived at only after considering what felt like every other possible solution. This gives me confidence, and the results speak for themselves.

Coupled with fixes to seemingly inscrutable bugs regarding stuck keys and subtly mismatching behavior between Windows' stock Alt-Tab switcher and cmdtab, along with a near astronomical improvement in memory usage and window capacity (70% memory usage decrease and yet 3200% increase of window capacity!), as well as color theme awareness and rudimentary handling of pesky UWP windows, this is clearly the best version of cmdtab yet.

It has taken close scrutiny of subtleties of the Win32 API to arrive here; the minutia of which knowledge is required to eek out the minimal surface area for a dead simple window switcher is surprisingly vast.

But now the jank is gone. Go forth and enjoy finally knowing wtf is going on with your Windows desktop.

Changes / highlights / improvements / fixes

- this change log will have a lesser detail level than previously; everything is renamed and moved around
- add resource info to cmdtab.exe
- cmdtab.exe has a new (placeholder) icon
- new build system CMake, instructions in README.md
- get rid of cmdtab.h, put includes in cmdtab.c
- remove bit array macros
- experiment with windows.h NO* defines
- specify comctl version with linker directive for prettier message dialog
- reduce struct definitions from 9 to 3: string, app, config
- use simplified typedefs & lowercase null
- separate Win32 "wrappers" from cmdtab implementation
- try out PascalCase
- debug macro and print function -> Debug, Print, Error, Ask
- use less intrusive "alt hack" (mouse input instead of kbd)
- UWP handling (TODO icons)
- slightly expanded IsAltTabWindow filter & default blacklist
- use strsafe.h
- fix crash caused by some apps' product name (#2)
- PostMessage instead of SendMessage for window management functions
- dark mode and accent color awareness
- don't ShowWindow if already foreground
- extensive logging
- move bitmap resizing from draw function to resize function
- put blacklist checking logic in separate function
- complete restructure of window handling: linked_window_t[] -> app[]
- massive memory usage reduction
- impl persistent window activation order
- measure performance of window handling
- improve error handling of access failure on getting filepath
- improve legibility of hwnd printing
- combine and simplify print functions
- complete restructure & simplification of selection handling
- fix text alignment bug caused by not #including math.h
- fix text alignment bias from right to left
- fix stuck modifier keys
- restructure keyboard hook procedure for maximum performance
- fix alt key / window menu inconsistency compared to Windows Alt-Tab
- impl select first app corner case when on bare desktop
- impl Alt-Q to quit process
- impl some debug hotkeys, Alt-B, Alt-F11, Alt-F12
- improve input passthrough / sink
- rely on switcher being top-most window vs. active window
- refactor WndProc & wWinMain
  • Loading branch information
stianhoiland committed Dec 11, 2024
1 parent f252a3b commit f9ff6e4
Show file tree
Hide file tree
Showing 6 changed files with 438 additions and 470 deletions.
14 changes: 14 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
cmake_minimum_required(VERSION 3.16)
project(cmdtab C)

set(C_STANDARD 99)
set(C_STANDARD_REQUIRED TRUE)
set(BUILD_TYPE "Debug")

add_executable(cmdtab WIN32 "src/cmdtab.c" "res/cmdtab.rc")

#set_property(TARGET ${PROJECT_NAME} PROPERTY
#LINK_FLAGS /MANIFESTUAC:"level='highestAvailable' uiAccess='true'"
#)
#mt.exe -manifest "cmdtab.exe.manifest" -updateresource:"cmdtab.exe;"#1
#mt.exe -manifest "cmdtab.exe.manifest" -outputresource:"cmdtab.exe;"#1
13 changes: 9 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,10 +1,9 @@
# cmdtab[^1]
# cmdtab
The best Mac-style Alt-Tab window/app switcher replacement for Windows, written in the Lord's language.

![screenshot2-cropped2](https://github.com/stianhoiland/cmdtab/assets/2081712/ec5d0d61-005f-4123-b191-8d5b49d1f7db)

## What's the deal?

### What's the deal?
1. On Windows Alt-Tab cycles through different windows from different apps all mixed together, showing small window previews
2. On macOS Cmd-Tab cycles through apps, showing big, clear icons
3. On macOS there is a separate hotkey that cycles through windows of the same app
Expand Down Expand Up @@ -45,4 +44,10 @@ The basics of window switching are easy to understand, but why is **cmdtab** *th

That's a lot of useful stuff, and the code is small! Go read it, and learn some C while you're at it.

[^1]: Keywords (you're welcome): *CmdTab for Windows // macOS window switcher on Windows // Alt-Tab replacement alternative // Mac style Alt-Tab window switching replacement for Windows*
## Buildling from source
1. `git clone https://github.com/stianhoiland/cmdtab.git`
2. `cd cmdtab`
3. `mkdir build`
4. `cmake -G"Visual Studio 17 2022" -B build`
5. *(in developer console)* `devenv build\cmdtab.sln /Build "MinSizeRel|x64"`
6. *(run cmdtab)* `build\MinSizeRel\cmdtab.exe`
143 changes: 0 additions & 143 deletions cmdtab.vcxproj

This file was deleted.

Binary file added res/cmdtab.ico
Binary file not shown.
38 changes: 38 additions & 0 deletions res/cmdtab.rc
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
1 VERSIONINFO
FILEVERSION 1,5,0,0
PRODUCTVERSION 1,5,0,0
FILEFLAGSMASK 0x3FL
#ifdef _DEBUG
FILEFLAGS 0x1L
#else
FILEFLAGS 0x0L
#endif
FILEOS 0x40004L
FILETYPE 0x1L
FILESUBTYPE 0x0L
{
BLOCK "VarFileInfo"
{
VALUE "Translation", 0x409, 1200
}
BLOCK "StringFileInfo"
{
BLOCK "040904B0"
{
VALUE "Comments", "N/A"
VALUE "CompanyName", "Stian Gudmundsen Høiland"
VALUE "FileDescription", "macOS-style Alt-Tab window switcher alternative"
VALUE "FileVersion", "1.5"
VALUE "InternalName", "cmdtab"
VALUE "LegalCopyright", "Copyright (C) 2023 Stian Gudmundsen Høiland"
VALUE "LegalTrademarks", "N/A"
VALUE "OriginalFilename", "cmdtab.exe"
VALUE "PrivateBuild"; "N/A"
VALUE "ProductName", "cmdtab"
VALUE "ProductVersion", "1.5"
VALUE "SpecialBuild", "N/A"
}
}
}

2 ICON "cmdtab.ico"
Loading

0 comments on commit f9ff6e4

Please sign in to comment.