Author |
Topic |
|
Hard.Wired
84 Posts |
Posted - 05/09/2019 : 19:08:48
|
I want to force the desktop to be active, but
acActivateWindow(acGetDesktopWindow(), nil, nil, 0)
doesn't seem to get the job done. However
acActivateWindow(acFindWindowByTitleRegex("Program Manager"), nil, nil, 0)
seems to work.
Is there a difference here or might this be a Windows 10 issue? |
Edited by - Hard.Wired on 05/15/2019 17:29:45 |
|
Rob
USA
2615 Posts |
Posted - 05/09/2019 : 20:11:44
|
acGetDesktopWindow() gets the actual true desktop window, as far as Windows is concerned. But that's not the desktop as you'd think of it.
In StrokesPlus.net I have a sp.DesktopWindowListView() function which returns the visible/interactive desktop window, which uses this code snippet:SystemWindow hProgman = SystemWindow.FindWindow("Progman", "");
IntPtr hDesktopWnd = GetDesktopWindow();
// If the main Program Manager window is found
if (hProgman != null)
{
// Get and load the main List view window containing the icons (found using Spy++).
IntPtr hShellViewWin = SystemWindow.FindWindowEx(hProgman.HWnd, IntPtr.Zero, "SHELLDLL_DefView", null);
if (hShellViewWin != IntPtr.Zero)
hDesktopListView = SystemWindow.FindWindowEx(hShellViewWin, IntPtr.Zero, "SysListView32", null);
else
// When this fails (happens in Windows-7 when picture rotation is turned ON), then look for the WorkerW windows list to get the
// correct desktop list handle.
// As there can be multiple WorkerW windows, so iterate through all to get the correct one
do
{
hWorkerW = SystemWindow.FindWindowEx(hDesktopWnd, hWorkerW, "WorkerW", null);
hShellViewWin = SystemWindow.FindWindowEx(hWorkerW, IntPtr.Zero, "SHELLDLL_DefView", null);
} while (hShellViewWin == IntPtr.Zero && hWorkerW != IntPtr.Zero);
// Get the ListView control
hDesktopListView = SystemWindow.FindWindowEx(hShellViewWin, IntPtr.Zero, "SysListView32", null);
} |
|
|
Hard.Wired
84 Posts |
Posted - 05/10/2019 : 06:15:34
|
Ah, I think see better now. I can't drill down the tree without using FindWindowEx... and even though acFindWindowByTitleRegex("Program Manager") seems to work, it really isn't correct, especially if the desktop icons are hidden (or at least it seems that way).
And GetDesktopWindow() is the highest handle in the tree that the other desktop processes start from (parent?).
So I'll have to do an alien.core dll call to access FindWindowEx. Hmm.
I will eventually get to StrokesPlus.net, but right now I need a few things to work in my StrokesPlus.com lua daily driver before I start converting everything.
I also need to figure out a way to get Window Z-order into a table. I've found some old code examples, but nothing that works well with Window 10 (or 8 for that matter).
|
|
|
Hard.Wired
84 Posts |
Posted - 05/10/2019 : 16:00:02
|
Hmm... is sp_all_windows supposed to be in Z-Order after acGetAllWindows(1)? |
|
|
Rob
USA
2615 Posts |
Posted - 05/10/2019 : 16:15:35
|
It just calls EnumWindows and after filtering out the things like visible etc, to qualify the main windows, it just added each handle (as they are received by EnumWindowsProc, sent by Windows) via vector::push_back(). Then the ac function using this snippet to load the sp_all_windows table...so take from that what you will! for (int i=0; i<GetAllWindowsList.size(); i++) {
lua_pushinteger(L, (int)GetAllWindowsList[i]);
lua_rawseti (L, -2, i);
} See here for some other info about a question regarding the z-order: https://stackoverflow.com/questions/295996/is-the-order-in-which-handles-are-returned-by-enumwindows-meaningful.
Basically, it's either in correct z-order, or completely reversed...but I think it's top down, which is the reason I used push_back so the lua push would spit them out in the correct order when it loops. however, the entirety of the ordering process is dictated by what Windows pushes into the EnumWindowsProc, so I don't alter the z-order in any way other than my loops. |
|
|
Hard.Wired
84 Posts |
Posted - 05/13/2019 : 13:20:05
|
After some testing, Z-Order seems consistent as long as I use
for i, hwnd in pairs(sp_all_windows) do
...
end and not ipairs or something like
for i = #sp_all_windows, 1, -1 do
...
end which is a bummer. To get them in a reverse order it looks like I have to do something like
local index_all_windows = {}
local iw = 1
for i, hwnd in pairs(sp_all_windows) do
index_all_windows[iw] = hwnd
iw = iw + 1
end
And then traverse through index_all_windows any way I want. Is there a better way to get the reverse order? |
|
|
Rob
USA
2615 Posts |
Posted - 05/13/2019 : 14:06:57
|
I was never a Lua master, anything I could google, you probably could too :-/ |
|
|
Hard.Wired
84 Posts |
Posted - 05/13/2019 : 15:42:39
|
Yeah, thanks. I'll keep poking at it. |
|
|
Hard.Wired
84 Posts |
Posted - 05/15/2019 : 17:28:05
|
After reading through the Lua docs (https://www.lua.org/manual/5.3/) and finding this info on Stack Exchange (https://stackoverflow.com/questions/15706270/sort-a-table-in-lua), I found out that Lua tables and for/pairs() can be tricky. For anyone interested, I'll repost the code here...
function spairs(t, order)
-- collect the keys
local keys = {}
for k in pairs(t) do keys[#keys+1] = k end
-- if order function given, sort by it by passing the table and keys a, b,
-- otherwise just sort the keys
if order then
table.sort(keys, function(a,b) return order(t, a, b) end)
else
table.sort(keys)
end
-- return the iterator function
local i = 0
return function()
i = i + 1
if keys[i] then
return keys[i], t[keys[i]]
end
end
end Example of use:
HighScore = { Robin = 8, Jon = 10, Max = 11 }
-- basic usage, just sort by the keys
for k,v in spairs(HighScore) do
print(k,v)
end
--> Jon 10
--> Max 11
--> Robin 8
-- this uses an custom sorting function ordering by score descending
for k,v in spairs(HighScore, function(t,a,b) return t[b] < t[a] end) do
print(k,v)
end
--> Max 11
--> Jon 10
--> Robin 8 Also, learned about "iterators". |
|
|
|
Topic |
|
|
|