WinMove a gui moves it briefly but goes back where it was

Get help with using AutoHotkey (v1.1 and older) and its commands and hotkeys
User avatar
theimmersion
Posts: 181
Joined: 09 Jul 2016, 08:34
Location: Serbia

WinMove a gui moves it briefly but goes back where it was

11 Feb 2018, 09:54

Im trying to keep a gui on screen by using WinMove once it is outside screen but it does not work.
I click on the gui, move it outside screen, when i release it, it moves as it should within the screen but only for a brief moment, then it goes back to its original location.

This is the code:

Code: Select all

~LButton Up::
	NewPosition() ; the only place it gets used.
Return

NewPosition()
	global newPosX ; Making it global so i can use it to save to .ini in OnExit sub.
	global newPosY ; Making it global so i can use it to save to .ini in OnExit sub.
	global Width     ; Get the window width.
	global Height    ; Get the window height
	WinGetPos, newPosX, newPosY, , , ahk_id %hwnd1% ; Get the gui 1 hwnd.
	KeepOnScreen := 1 ; Option that toggles but is set here for debugging to true.
	if (KeepOnScreen=1)
	{
		if (newPosX<0)
			newPosX:=0
		else if (newPosX>(A_ScreenWidth-Width))
			newPosX:=A_ScreenWidth-Width
		if (newPosY<0)
			newPosY:=0
		else if (newPosY>(A_ScreenHeight-Height))
			newPosY:=A_ScreenHeight-Height
		WinMove, ahk_id %hwnd1%, , %newPosX%, %newPosY% ; Move it within screen.
	}
	return 1 ; call confirmed
In case it matters, i made a few gdi+ guis and used SetParent dll call. Could not get +Parent to work. o.O
Also, Gui 2 is child of Gui 1 but buttons (gui 3-6) are child of gui 2.
I am not moving the gui from anywhere inside the script, only here happens such an event. Any ideas why it does that?
I also use the above function to save the location with IniWrite when i close the script and use IniRead on startup to set it back where it was last time.
Id post the full script but its 1500+ lines and its hard to pull out what i guess relevant code that might make an issue?
But i dont think it should tho unless its some inherent issue or way how gdi works? Thats the only thing out of the ordinary in my script.
User avatar
boiler
Posts: 17215
Joined: 21 Dec 2014, 02:44

Re: WinMove a gui moves it briefly but goes back where it was

11 Feb 2018, 20:27

WinGetPos does not get the hwnd of the gui like your comments says. That parameter is used to specify the title of the window you want to move. If your script is working, it must be because you're defining hwnd1 as a global variable and assigning it's value somewhere else.
User avatar
theimmersion
Posts: 181
Joined: 09 Jul 2016, 08:34
Location: Serbia

Re: WinMove a gui moves it briefly but goes back where it was

12 Feb 2018, 07:30

Yes, i use hwnd1 as a global as this "when i release it, it moves as it should within the screen but only for a brief moment" would not work at all.
But the issue is not if its working, it does, the odd thing is that it reverts back.
If i was to copy/paste:

Code: Select all

WinMove, ahk_id %hwnd1%, , %newPosX%, %newPosY% ; Move it within screen.
multiple times, it would remain where it supposed to while the lines get executed, after all of them are executed, it goes back outside the screen.

This should show You what i mean.
GIF.gif
GIF.gif (232.73 KiB) Viewed 1131 times
As You can see, it moves within the screen briefly when i release the left click while the bar is outside the screen, that is the WinMove at work, but than moves back outside again.

Im trying to figure out where my mistake is (usually always is) but so far i could not find anything so i was wondering if people had issues like these as well and what could cause that or if its because of gdi+ lib. Maybe that could help me troubleshoot the issue.

EDIT
Also, if i do this:

Code: Select all

F5::
	testPosX:=A_ScreenWidth-Width
	WinMove, ahk_id %hwnd1%, , %testPosX%, %PosY%
Return
it works. It moves it on the right edge of screen and it stays there. Is that a positive indicator that its a mistake on my part?
User avatar
boiler
Posts: 17215
Joined: 21 Dec 2014, 02:44

Re: WinMove a gui moves it briefly but goes back where it was

12 Feb 2018, 08:55

I don't know what the issue might be just based on your descriptions of what's going on with the rest of your code. I suggest commenting out parts of your code and see when it starts working to isolate the problem. Or, working the other way, you might start by commenting out most of it, then adding pieces until it stops working.
User avatar
theimmersion
Posts: 181
Joined: 09 Jul 2016, 08:34
Location: Serbia

Re: WinMove a gui moves it briefly but goes back where it was

12 Feb 2018, 09:09

Found the problem. Thank god because commenting out code would take a lot of time. xD
The issue is:

Code: Select all

PostMessage, 0xA1, 2
If i use a timer for MouseGetPos / WinMove it works. Of course you can see the timers lag while moving the gui.
Now, why is PostMessage, 0xA1, 2 resetting the gui?. I tried even adding a sleep in the NewLocation() function but it still gets overriden.
How does PostMessage, 0xA1, 2 work and any way i can force disable it when NewLocation() gets called?
EDIT
I really want to use PostMessage, 0xA1, 2 because it moves the gui fluidly and not stuttery like a timer. Its a complex script so theres no way i can make a timer be fast enough to do the job. :(
User avatar
boiler
Posts: 17215
Joined: 21 Dec 2014, 02:44

Re: WinMove a gui moves it briefly but goes back where it was

12 Feb 2018, 09:32

Not sure what you mean. PostMessage isn't just magically moving the gui. You must be executing that line of code. I can't really comment since I don't know how/when you are calling it. Not that I want to look through all your code either. At this point, it sounds like you have isolated the issue and it's a matter of figuring out what works best for your code.
User avatar
theimmersion
Posts: 181
Joined: 09 Jul 2016, 08:34
Location: Serbia

Re: WinMove a gui moves it briefly but goes back where it was

12 Feb 2018, 10:06

Sorry for so many incomplete code snippets that might have explained it much better. For the sake of this topic to not be incomplete.
I think this should be essentially the complete event how the gui gets moved. There is no other code in my script that would/should interfere with this.

I use WM_LBUTTONDOWN as i saw in some of the AHK help examples. Since im using a GDI+ gui that does not come nor should have a bar, i needed to use the following to enable gui movement.

Now that i know what the exact issue is, i created a new script to try and solve the issue, if someone knows already a proper way of dealing with this, i would appreciate it very much. Thanks for taking the time to try and help! :)

Here is a working script that shows the issue:

Code: Select all

#NoEnv
; #Warn
SendMode Input
SetWorkingDir %A_ScriptDir%

#Include, %A_ScriptDir%\Gdip_All.ahk

If !pToken := Gdip_Startup() 
{ 
   MsgBox, 48, gdiplus error!, Gdiplus failed to start. Please ensure you have gdiplus on your system 
   ExitApp 
}
OnExit, Exit

OnMessage(0x201, "WM_LBUTTONDOWN")

Width := 500
Height := 100

Gui, -Caption +E0x80000 +LastFound +OwnDialogs +AlwaysOnTop
Gui, Show, NA
global hwnd1 := WinExist()

hbm := CreateDIBSection(Width, Height)
hdc := CreateCompatibleDC()
obm := SelectObject(hdc, hbm)
G := Gdip_GraphicsFromHDC(hdc)
Gdip_SetSmoothingMode(G, 4)
Gdip_GraphicsClear(G)

pBrush := Gdip_BrushCreateSolid(0xffff0000)
Gdip_FillRectangle(G, pBrush, 0, 0, Width, Height)
Gdip_DeleteBrush(pBrush)

UpdateLayeredWindow(hwnd1, hdc, 0, 0, Width, Height)

SelectObject(hdc, obm)
DeleteObject(hbm)
DeleteDC(hdc)
Gdip_DeleteGraphics(G)
return

WM_LBUTTONDOWN(wParam,lParam)
{
	PostMessage, 0xA1, 2
}

; I should replace ~LButton Up:: with OnMessage(0x202, "WM_LBUTTONUP"). This was just easier for testing.
~LButton Up::
	NewLocation()
Return

NewLocation()
{
	global newPosX
	global newPosY
	global Width
	global Height
	;sleep 1000 ; Wanted to see if i could wait for the gui to settle outside the screen then attempt to move it inside screen zone. Did not help, moved in than out again.
	WinGetPos, newPosX, newPosY, , , ahk_id %hwnd1%
	KeepOnScreen := 1
	if (KeepOnScreen=1)
	{
		if (newPosX<0)
			newPosX:=0
		else if (newPosX>(A_ScreenWidth-Width))
			newPosX:=A_ScreenWidth-Width
		if (newPosY<0)
			newPosY:=0
		else if (newPosY>(A_ScreenHeight-Height))
			newPosY:=A_ScreenHeight-Height
		WinMove, ahk_id %hwnd1%, , %newPosX%, %newPosY%
	}
	return 1
}

Esc::
GuiClose:
Exit:
	Gdip_Shutdown(pToken)
	ExitApp
Return
It should work just by copy/pasting the script. (and having the GDI_All.ahk lib of course). :)

Return to “Ask for Help (v1)”

Who is online

Users browsing this forum: Chunjee, GEOVAN, Leonardo_Portela and 181 guests