Jump to content
Sign in to follow this  
mpower

Clicking a list in a popup child window without losing focus on main GUI

Recommended Posts

mpower

Hi guys, I have below code (taken from CaptainClucks):

#Include 
#include 
#include 
#include 
Opt("GUIOnEventMode", 1)
Opt("GUIResizeMode", 1)
Global $__KM_Hook
Global $__KM_KB_Hook
Global $__KM_User32
Global $GUIMINWID = 463; Resizing / minimum width
Global $GUIMINHT = 278; Resizing / minimum hight
Global Const $WS_RESIZABLE = 0x00070000
Global $sPartialData, $asKeyWords[5], $iMatch_Count
Global $sCurr_Input = "", $sData = "|", $sChosen = "http://www.someplace.com/somedir/"
Global $iCurrIndex = -1
#region - GUI -
Global $BANEVADER = GUICreate("test", $GUIMINWID, $GUIMINHT, -1, -1, BitOR($WS_RESIZABLE, $WS_CAPTION, $WS_POPUP))
GUISetOnEvent(-3, "Terminate")
GUICtrlSetResizing(-1, 102)
GUICtrlCreateCheckbox("test",20,70,100,20)
Global $Input1 = GUICtrlCreateInput($sChosen, 4, 33, 385, 21)
GUICtrlSetResizing(-1, 512 + 32)
GUISetState(@SW_SHOW)
#region - HISTORY LIST -
Global $hUP = GUICtrlCreateDummy()
GUICtrlSetOnEvent(-1, "UP")
Global $hDOWN = GUICtrlCreateDummy()
GUICtrlSetOnEvent(-1, "DOWN")
Global $hENTER = GUICtrlCreateDummy()
GUICtrlSetOnEvent(-1, "ENTER")
Global $AccelKeys[3][2]=[["{UP}", $hUP], ["{DOWN}", $hDOWN], ["{ENTER}", $hENTER]]
GUISetAccelerators($AccelKeys)
Global $hlist_ui = GUICreate("Child", 385, 20, 3, 52, $WS_POPUP, $WS_EX_MDICHILD, $BANEVADER)
Global $hList = GUICtrlCreateList("", 0, 0, 385, 20, BitOR(0x00100000, 0x00200000))
GUICtrlSetOnEvent(-1, "SetListItem")
GUICtrlSetResizing($hList, 1)
Sleep(3000)
#endregion - HISTORY LIST -
#endregion - GUI -
Keywords()
_SetHooks(True)
Global $masterMask = CreateMasterMask();
AddToMask($masterMask,$hlist_ui,$hList);add button to mask
FitMask($masterMask,$hlist_ui);apply the mask to the window

Sleep(99999999999999)
Func CreateMasterMask()
return DllCall("gdi32.dll", "long", "CreateRectRgn", "long", 0, "long", 0, "long", 0, "long", 0)
EndFunc
Func FitMask($aMask,$hWnd)
DllCall("user32.dll", "long", "SetWindowRgn", "hwnd", $hWnd, "long", $aMask[0], "int", 1)
endfunc
Func AddToMask(ByRef $MM, $hWnd, $ID)
Local $pp = ControlGetPos($hWnd,'',$ID)
Local $Mask1 = DllCall("gdi32.dll", "long", "CreateRectRgn", "long", $pp[0], "long", $pp[1], "long", $pp[0] + $pp[2], "long",$pp[1] + $pp[3])
DllCall("gdi32.dll", "long", "CombineRgn", "long", $MM[0], "long", $Mask1[0], "long", $MM[0],"int",2)
EndFunc
Func _KeyProcess($NCode, $WParam, $LParam)
Local $aResult
If $NCode < 0 Then
$aResult = DllCall($__KM_User32, "lresult", "CallNextHookEx", "handle", $__KM_Hook, "int", $NCode, "wparam", $WParam, "lparam", $LParam)
If @error Then Return SetError(@error, @extended, -1)
Return $aResult[0]
EndIf
AdlibRegister("Monitor",100)
$aResult = DllCall($__KM_User32, "lresult", "CallNextHookEx", "handle", $__KM_Hook, "int", $NCode, "wparam", $WParam, "lparam", $LParam)
If @error Then Return SetError(@error, @extended, -1)
Return $aResult[0]
EndFunc ;==>_KeyProcess
Func SetListItem($Selected = 0)
If Not IsDeclared("Selected") Then
$sChosen = GUICtrlRead($hList)
Else
$sChosen = $Selected
EndIf
If $sChosen <> "" Then GUICtrlSetData($Input1, $sChosen)
GUISetState(@SW_HIDE, $hlist_ui)
EndFunc
Func UP()
$iCurrIndex -= 1
If $iCurrIndex < 0 Then $iCurrIndex = 0
_GUICtrlListBox_SetCurSel($hList, $iCurrIndex)
EndFunc
Func DOWN()
Local $iTotal = _GUICtrlListBox_GetCount($hList)
$iCurrIndex += 1
If $iCurrIndex > $iTotal - 1 Then $iCurrIndex = $iTotal - 1
_GUICtrlListBox_SetCurSel($hList, $iCurrIndex)
EndFunc
Func ENTER()
If $iCurrIndex <> -1 Then
Local $sText = _GUICtrlListBox_GetText($hList, $iCurrIndex)
SetListItem($sText)
$iCurrIndex = -1
_GUICtrlListBox_SetCurSel($hList, $iCurrIndex)
GUISetState(@SW_HIDE, $hlist_ui)
EndIf
EndFunc
Func Monitor()
If (GUICtrlRead($Input1) <> "") And (GUICtrlRead($Input1) <> $sChosen) And Not(BitAND(WinGetState($hlist_ui), 2)) And ($sData <> "|") Then
GUISetState(@SW_SHOWNOACTIVATE, $hlist_ui)
GUICtrlSetState($Input1, $GUI_FOCUS);
ControlSend($BANEVADER, "", $Input1, "{END}");
;I need another way of doing this above :(
EndIf
If GUICtrlRead($Input1) = "" Or Not($iMatch_Count) And BitAND(WinGetState($hlist_ui), 2) Then
GUISetState(@SW_HIDE, $hlist_ui)
$iCurrIndex = -1
EndIf
If GUICtrlRead($Input1) <> $sCurr_Input Then
CheckInputText()
$sCurr_Input = GUICtrlRead($Input1)
EndIf
AdlibUnRegister("Monitor")
EndFunc
Func CheckInputText()
$sData = "|" ; Start with delimiter so new data always replaces aold
Local $sInput = GUICtrlRead($Input1)
$iMatch_Count = 0
If $sInput <> "" Then
For $i = 0 To UBound($asKeyWords) - 1
If StringInStr($asKeyWords[$i], $sInput,2) Then
$sData &= $asKeyWords[$i] & "|"
$iMatch_Count += 1
EndIf
Next
GUICtrlSetData($hList, $sData)
; Change size of child GUI
Local $iList_Height = $iMatch_Count * (_GUICtrlListBox_GetItemHeight($hList)+1)
If $iList_Height < 20 Then $iList_Height = 20
If $iList_Height > 200 Then $iList_Height = 200
ConsoleWrite($iList_Height & @CR)
WinMove($hlist_ui, "", Default, Default, Default, $iList_Height)
$masterMask = CreateMasterMask();
AddToMask($masterMask,$hlist_ui,$hList);add button to mask
FitMask($masterMask,$hlist_ui);apply the mask to the window
$iCurrIndex = -1
EndIf
EndFunc ;==>CheckInputText
Func Keywords()
Local $sData, $Count, $aKeyWords, $Rows, $Columns
$asKeyWords[0] = "http://autoitscript.com"
$asKeyWords[1] = "http://google.com"
$asKeyWords[2] = "http://yahoo.com"
$asKeyWords[3] = "http://ask.com"
$asKeyWords[4] = "http://theworldisdying.com"
For $I = 0 To 4
$sData &= $asKeyWords[$i] & "|"
Next
GUICtrlSetData($hList, $sData)
$iCurrIndex = -1
_GUICtrlListBox_SetCurSel($hList, $iCurrIndex)
EndFunc ;==>Keywords
Func _SetHooks($Type = False)
Switch $Type
Case True
If Not ($__KM_User32) Then
$__KM_User32 = DllOpen("User32.dll")
EndIf
$__KM_KB_Hook = DllCallbackRegister("_KeyProcess", "long", "int;wparam;lparam")
If Not $__KM_KB_Hook Then Return SetError(1,0,False)
Local $aResult = DllCall("kernel32.dll", "handle", "GetModuleHandleW", "ptr", 0)
If @error Then Return SetError(2, @error, False)
$aResult = DllCall($__KM_User32, "handle", "SetWindowsHookEx", _
"int", 13, _ ; WH_KEYBOARD_LL
"ptr", DllCallbackGetPtr($__KM_KB_Hook), _
"handle", $aResult[0], _
"dword", 0 _
)
If @error Then Return SetError(3, @error, False)
$__KM_Hook = $aResult[0]
Case False
DllCall($__KM_User32, "bool", "UnhookWindowsHookEx", "handle", $__KM_Hook)
DllCallbackFree($__KM_KB_Hook)
DllClose($__KM_User32)
$__KM_User32 = 0
EndSwitch
Return SetError(0,0,True)
EndFunc ;==>_SetHooks
Func Terminate()
Exit
EndFunc

The issue I have is when I click a list item in the popup child window I get a 'flicker' because the popup window takes focus and then loses focus when it is hidden.

Is there a way to prevent the child popup window from taking focus but still allow clicking on list items/scroll bar?

Thanks heaps in advance!

Edited by mpower

Share this post


Link to post
Share on other sites
MouseSpotter

Maybe: ?

Share this post


Link to post
Share on other sites
mpower

Maybe: ?

I've looked in that thread, unfortunately there is no solution there for $WS_POPUP

I have to keep it as $WS_POPUP as otherwise it doesn't work as expected.

Edited by mpower

Share this post


Link to post
Share on other sites
PhoenixXL

The following script can send the click to the button without setting focus to the parent.

Functions

  • Supports only Left Click and Button controls
  • The parent doesn't get focus.
  • The script won't block the click event when over non-client area
  • The script would block the real clicks not the simulated one.
#include-once
#include <WinAPI.au3>
#include <ButtonConstants.au3>
#include <SendMessage.au3>
#include <WindowsConstants.au3>
#include <GUIConstants.au3>

HotKeySet("{ESC}", "Terminate")
OnAutoItExitRegister("Cleanup")

;WH_MOUSE_LL - Check Msdn
Global Const $tagMSLLHOOKSTRUCT = 'int x;int y;DWORD mouseData;DWORD flags;DWORD time;ULONG_PTR dwExtraInfo'

Global $hModule = _WinAPI_GetModuleHandle(0)

Global $hMouseProc = DllCallbackRegister("LowLevelMouseProc", "long", "int;wparam;lparam")
Global $pMouseProc = DllCallbackGetPtr($hMouseProc)
Global $hMouseHook = _WinAPI_SetWindowsHookEx($WH_MOUSE_LL, $pMouseProc, $hModule)

;The Message to check for
Global $iCheck = $WM_LBUTTONDOWN
Global $hWnd = GUICreate("GUI_WithNoFocus", 500, 600, -1, -1, -1, $WS_EX_TOPMOST)
Global $iBtn = GUICtrlCreateButton("Click Me", 10, 10)
Global $hBtn = GUICtrlGetHandle(-1)

GUISetState(@SW_SHOWNOACTIVATE)


While 1
Switch GUIGetMsg()
Case $GUI_EVENT_CLOSE
ExitLoop
Case $iBtn
ConsoleWrite("Button Clicked" & @CRLF)
EndSwitch
WEnd



; http://msdn.microsoft.com/en-us/library/ms644986(v=vs.85).aspx
Func LowLevelMouseProc($nCode, $wParam, $lParam)

Local $tPoint = _WinAPI_GetMousePos()
Local $hActive = _WinAPI_WindowFromPoint($tPoint)
Local $hParent = _WinAPI_GetParent($hActive)

If $nCode >= 0 And ($wParam = $iCheck) And ($hParent = $hWnd Or $hActive = $hWnd) Then

; http://msdn.microsoft.com/en-us/library/ms644970(v=vs.85).aspx
Local $MSLLHOOKSTRUCT = DllStructCreate($tagMSLLHOOKSTRUCT, $lParam)
Local $iRealClick = (DllStructGetData($MSLLHOOKSTRUCT, 'flags') = 0) ;The Click is real, not injected(or simulated)
Local $iClickOnClient = _IsCLickOnClient($hWnd, DllStructGetData($MSLLHOOKSTRUCT, 1), DllStructGetData($MSLLHOOKSTRUCT, 2)); Clicked at Client-Area

;Block if the event is real and on the client area only
If $iRealClick And $iClickOnClient Then ;

;This would only work for buttons
$iControlID = _WinAPI_GetDlgCtrlID($hActive)
$iWParam = _WinAPI_MakeLong($iControlID, $BN_CLICKED)
_SendMessage($hParent, $WM_COMMAND, $iWParam, $hActive)

Return 1 ;Block the Main Click

EndIf

EndIf

Return _WinAPI_CallNextHookEx($hMouseHook, $nCode, $wParam, $lParam)

EndFunc ;==>LowLevelMouseProc

Func _IsCLickOnClient($hWnd, $iX, $iY)

$tRect = _WinAPI_GetClientRect($hWnd)
$tPoint = DllStructCreate($tagPoint)
DllStructSetData($tPoint, 1, 0)
DllStructSetData($tPoint, 2, 0)
_WinAPI_ClientToScreen($hWnd, $tPoint)

DllStructSetData($tRect, 1, DllStructGetData($tPoint, 1))
DllStructSetData($tRect, 2, DllStructGetData($tPoint, 2))
DllStructSetData($tRect, 3, DllStructGetData($tPoint, 1) + DllStructGetData($tRect, 3))
DllStructSetData($tRect, 4, DllStructGetData($tPoint, 2) + DllStructGetData($tRect, 4))
DllStructSetData($tPoint, 1, $iX)
DllStructSetData($tPoint, 2, $iY)

Return _WinAPI_PtInRect($tRect, $tPoint)

EndFunc ;==>_IsCLickOnClient

Func Cleanup()
_WinAPI_UnhookWindowsHookEx($hMouseHook)
DllCallbackFree($hMouseProc)
EndFunc ;==>Cleanup

Func Terminate()
Exit
EndFunc ;==>Terminate

You can even try with Global Const $WS_EX_NOACTIVATE = 0x08000000

With list controls I had no luck.

It may help you

Regards :)

Edited by PhoenixXL
  • Like 1

My code:

PredictText: Predict Text of an Edit Control Like Scite. Remote Gmail: Execute your Scripts through Gmail. StringRegExp:Share and learn RegExp.

Run As System: A command line wrapper around PSEXEC.exe to execute your apps scripts as System (LSA). Database: An easier approach for _SQ_LITE beginners.

MathsEx: A UDF for Fractions and LCM, GCF/HCF. FloatingText: An UDF for make your text floating. Clipboard Extendor: A clipboard monitoring tool. 

Custom ScrollBar: Scroll Bar made with GDI+, user can use bitmaps instead. RestrictEdit_SRE: Restrict text in an Edit Control through a Regular Expression.

Share this post


Link to post
Share on other sites
PhoenixXL

This instead should help you more

#include <GUIConstantsEx.au3>

HotKeySet("{ESC}", "Terminate")
Global Const $WS_EX_NOACTIVATE = 0x08000000

Global $hMainGUI = GUICreate("Main GUI", -1, -1, -1, -1, -1, $WS_EX_NOACTIVATE)
Global $iList = GUICtrlCreateList("Create Child Win", 10, 10)
GUICtrlSetData($iList, "Data1|Data2|Data3|Data4|So on...")

GUISetState(@SW_SHOWNOACTIVATE)

Global $hWnd, $iList

While 1
Switch GUIGetMsg()
Case $GUI_EVENT_CLOSE
ExitLoop

EndSwitch
WEnd

Func Terminate()
Exit
EndFunc   ;==>Terminate
Regards :)
  • Like 1

My code:

PredictText: Predict Text of an Edit Control Like Scite. Remote Gmail: Execute your Scripts through Gmail. StringRegExp:Share and learn RegExp.

Run As System: A command line wrapper around PSEXEC.exe to execute your apps scripts as System (LSA). Database: An easier approach for _SQ_LITE beginners.

MathsEx: A UDF for Fractions and LCM, GCF/HCF. FloatingText: An UDF for make your text floating. Clipboard Extendor: A clipboard monitoring tool. 

Custom ScrollBar: Scroll Bar made with GDI+, user can use bitmaps instead. RestrictEdit_SRE: Restrict text in an Edit Control through a Regular Expression.

Share this post


Link to post
Share on other sites
mpower

The following script can send the click to the button without setting focus to the parent.

Functions

  • Supports only Left Click and Button controls
  • The parent doesn't get focus.
  • The script won't block the click event when over non-client area
  • The script would block the real clicks not the simulated one.
You can even try with Global Const $WS_EX_NOACTIVATE = 0x08000000

With list controls I had no luck.

It may help you

Regards :)

Thank you PhoenixXL!

This solution is probably what I am looking for however it doesn't appear to be working for a list :( .

Wondering how I can modify this to work with the list:

;This would only work for buttons
$iControlID = _WinAPI_GetDlgCtrlID($hActive)
$iWParam = _WinAPI_MakeLong($iControlID, $BN_CLICKED)
_SendMessage($hParent, $WM_COMMAND, $iWParam, $hActive)
Edited by mpower

Share this post


Link to post
Share on other sites
PhoenixXL

Does this work for you ?

#include-once
#include <WinAPI.au3>
#include <GUIListBox.au3>
#include <SendMessage.au3>
#include <WindowsConstants.au3>
#include <GUIConstants.au3>

HotKeySet("{ESC}", "Terminate")
OnAutoItExitRegister("Cleanup")

;WH_MOUSE_LL - Check Msdn
Global Const $tagMSLLHOOKSTRUCT = 'int x;int y;DWORD mouseData;DWORD flags;DWORD time;ULONG_PTR dwExtraInfo'

Global $hModule = _WinAPI_GetModuleHandle(0)

Global $hMouseProc = DllCallbackRegister("LowLevelMouseProc", "long", "int;wparam;lparam")
Global $pMouseProc = DllCallbackGetPtr($hMouseProc)
Global $hMouseHook = _WinAPI_SetWindowsHookEx($WH_MOUSE_LL, $pMouseProc, $hModule)

;The Message to check for
Global $iCheck = $WM_LBUTTONDOWN
Global $hWnd = GUICreate("GUI_WithNoFocus", 500, 600, -1, -1, -1, $WS_EX_TOPMOST)
Global $iBtn = GUICtrlCreateList("", 10, 10)
GUICtrlSetData(-1, "Row1|Row2|Row3|Row4|Row5", "Row4")

GUISetState(@SW_SHOWNOACTIVATE)


While 1
Switch GUIGetMsg()
Case $GUI_EVENT_CLOSE
ExitLoop
Case $iBtn
ConsoleWrite("ListBox Clicked" & @CRLF)
EndSwitch
WEnd



; http://msdn.microsoft.com/en-us/library/ms644986(v=vs.85).aspx
Func LowLevelMouseProc($nCode, $wParam, $lParam)

Local $tPoint = _WinAPI_GetMousePos()
Local $hActive = _WinAPI_WindowFromPoint($tPoint)
Local $hParent = _WinAPI_GetParent($hActive)

;No need to process if the window is activated.
If WinGetHandle("[ACTIVE]") = $hParent Then Return _WinAPI_CallNextHookEx($hMouseHook, $nCode, $wParam, $lParam)


If $nCode >= 0 And ($wParam = $iCheck) And ($hParent = $hWnd Or $hActive = $hWnd) Then

; http://msdn.microsoft.com/en-us/library/ms644970(v=vs.85).aspx
Local $MSLLHOOKSTRUCT = DllStructCreate($tagMSLLHOOKSTRUCT, $lParam)
Local $iRealClick = (DllStructGetData($MSLLHOOKSTRUCT, 'flags') = 0) ;The Click is real, not injected(or simulated)
Local $iClickOnClient = _IsCLickOnClient($hWnd, DllStructGetData($MSLLHOOKSTRUCT, 1), DllStructGetData($MSLLHOOKSTRUCT, 2)); Clicked at Client-Area

;Block if the event is real and on the client area only
If $iRealClick And $iClickOnClient Then ;

$iIndex = _GUICtrlListBox_ItemFromPoint($hActive, _WinAPI_GetMousePosX(True, $hActive), _WinAPI_GetMousePosY(True, $hActive))
_SendMessage($hActive, $LB_SETCURSEL, $iIndex) ;Change the selection

;Send Parent the notification
$iControlID = _WinAPI_GetDlgCtrlID($hActive)
$iWParam = _WinAPI_MakeLong($iControlID, $LBN_SELCHANGE)
_SendMessage($hParent, $WM_COMMAND, $iWParam, $hActive)

Return 1 ;Block the Main Click

EndIf

EndIf

Return _WinAPI_CallNextHookEx($hMouseHook, $nCode, $wParam, $lParam)

EndFunc ;==>LowLevelMouseProc

Func _IsCLickOnClient($hWnd, $iX, $iY)

$tRect = _WinAPI_GetClientRect($hWnd)
$tPoint = DllStructCreate($tagPoint)
DllStructSetData($tPoint, 1, 0)
DllStructSetData($tPoint, 2, 0)
_WinAPI_ClientToScreen($hWnd, $tPoint)

DllStructSetData($tRect, 1, DllStructGetData($tPoint, 1))
DllStructSetData($tRect, 2, DllStructGetData($tPoint, 2))
DllStructSetData($tRect, 3, DllStructGetData($tPoint, 1) + DllStructGetData($tRect, 3))
DllStructSetData($tRect, 4, DllStructGetData($tPoint, 2) + DllStructGetData($tRect, 4))
DllStructSetData($tPoint, 1, $iX)
DllStructSetData($tPoint, 2, $iY)

Return _WinAPI_PtInRect($tRect, $tPoint)

EndFunc ;==>_IsCLickOnClient

Func Cleanup()
_WinAPI_UnhookWindowsHookEx($hMouseHook)
DllCallbackFree($hMouseProc)
EndFunc ;==>Cleanup

Func Terminate()
Exit
EndFunc ;==>Terminate

The script satisfies the same functions as specified above just replace button with list.

For keyboard support you need to send WM_VKEYTOITEM and WM_CHARTOITEM with a keyboard hook or with GUISetAccelerators.

Thumbs up if helped

Regards :)

Edited by PhoenixXL
  • Like 1

My code:

PredictText: Predict Text of an Edit Control Like Scite. Remote Gmail: Execute your Scripts through Gmail. StringRegExp:Share and learn RegExp.

Run As System: A command line wrapper around PSEXEC.exe to execute your apps scripts as System (LSA). Database: An easier approach for _SQ_LITE beginners.

MathsEx: A UDF for Fractions and LCM, GCF/HCF. FloatingText: An UDF for make your text floating. Clipboard Extendor: A clipboard monitoring tool. 

Custom ScrollBar: Scroll Bar made with GDI+, user can use bitmaps instead. RestrictEdit_SRE: Restrict text in an Edit Control through a Regular Expression.

Share this post


Link to post
Share on other sites
mpower

Does this work for you ?

#include-once
#include <WinAPI.au3>
#include <GUIListBox.au3>
#include <SendMessage.au3>
#include <WindowsConstants.au3>
#include <GUIConstants.au3>

HotKeySet("{ESC}", "Terminate")
OnAutoItExitRegister("Cleanup")

;WH_MOUSE_LL - Check Msdn
Global Const $tagMSLLHOOKSTRUCT = 'int x;int y;DWORD mouseData;DWORD flags;DWORD time;ULONG_PTR dwExtraInfo'

etc...
Thumbs up if helped

Regards :)

That works great! Thank you so much! :)

Edited by mpower

Share this post


Link to post
Share on other sites
mpower
Question, how do I also let the user "scroll" through the list using the scroll bar on the right? Edited by mpower

Share this post


Link to post
Share on other sites
PhoenixXL

it would require a couple of increase in the code.

Just for curiosity, what is the problem with this

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>

HotKeySet("{ESC}", "Terminate")
Global Const $WS_EX_NOACTIVATE = 0x08000000

Global $hMainGUI = GUICreate("Main GUI", -1, -1, -1, -1, $WS_POPUP, $WS_EX_NOACTIVATE)
Global $iList = GUICtrlCreateList("Create Child Win", 10, 10, 200, 100)
GUICtrlSetData($iList, "Data1|Data2|Data3|Data4|Data1|Data2|Data3|Data4|Data1|Data2|Data3|Data4|So on...")

GUISetState(@SW_SHOWNOACTIVATE)

Global $hWnd, $iList

While 1
Switch GUIGetMsg()
Case $GUI_EVENT_CLOSE
ExitLoop
Case $iList
ConsoleWrite("list" & @CRLF)
EndSwitch
WEnd

Func Terminate()
Exit
EndFunc   ;==>Terminate
  • Like 1

My code:

PredictText: Predict Text of an Edit Control Like Scite. Remote Gmail: Execute your Scripts through Gmail. StringRegExp:Share and learn RegExp.

Run As System: A command line wrapper around PSEXEC.exe to execute your apps scripts as System (LSA). Database: An easier approach for _SQ_LITE beginners.

MathsEx: A UDF for Fractions and LCM, GCF/HCF. FloatingText: An UDF for make your text floating. Clipboard Extendor: A clipboard monitoring tool. 

Custom ScrollBar: Scroll Bar made with GDI+, user can use bitmaps instead. RestrictEdit_SRE: Restrict text in an Edit Control through a Regular Expression.

Share this post


Link to post
Share on other sites
mpower

it would require a couple of increase in the code.

Just for curiosity, what is the problem with this

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>

HotKeySet("{ESC}", "Terminate")
Global Const $WS_EX_NOACTIVATE = 0x08000000

Global $hMainGUI = GUICreate("Main GUI", -1, -1, -1, -1, $WS_POPUP, $WS_EX_NOACTIVATE)
Global $iList = GUICtrlCreateList("Create Child Win", 10, 10, 200, 100)
GUICtrlSetData($iList, "Data1|Data2|Data3|Data4|Data1|Data2|Data3|Data4|Data1|Data2|Data3|Data4|So on...")

GUISetState(@SW_SHOWNOACTIVATE)

Global $hWnd, $iList

While 1
Switch GUIGetMsg()
Case $GUI_EVENT_CLOSE
ExitLoop
Case $iList
ConsoleWrite("list" & @CRLF)
EndSwitch
WEnd

Func Terminate()
Exit
EndFunc ;==>Terminate

 

This doesnt work as I have a Main GUI thats Active and the additional list child gui only pops up when a user types text into an input box. Pretty much like an autocomplete popup in google.

 

Edited by mpower

Share this post


Link to post
Share on other sites
PhoenixXL

I'm currently in this project, for autosuggestion. ;)

Will post when the script is ready

Regards :)

Edited by PhoenixXL
  • Like 1

My code:

PredictText: Predict Text of an Edit Control Like Scite. Remote Gmail: Execute your Scripts through Gmail. StringRegExp:Share and learn RegExp.

Run As System: A command line wrapper around PSEXEC.exe to execute your apps scripts as System (LSA). Database: An easier approach for _SQ_LITE beginners.

MathsEx: A UDF for Fractions and LCM, GCF/HCF. FloatingText: An UDF for make your text floating. Clipboard Extendor: A clipboard monitoring tool. 

Custom ScrollBar: Scroll Bar made with GDI+, user can use bitmaps instead. RestrictEdit_SRE: Restrict text in an Edit Control through a Regular Expression.

Share this post


Link to post
Share on other sites
mpower

I'm currently in this project, for autosuggestion. ;)

Will post when the script is ready

Regards :)

Wow thanks heaps for your help with everything!

Share this post


Link to post
Share on other sites
PhoenixXL

This would do your needs

#include <WindowsConstants.au3>
#include <WinAPI.au3>
#include <GuiListBox.au3>
#include <ScrollBarConstants.au3>
#include <Misc.au3>

$hMain = GUICreate("", -1, -1, 100, 100)
Global $Input = GUICtrlCreateInput("", 10, 10, -1, 20)
GUISetState()

GUICreate("", 100, 71, 100 + 10 + 15, 100 + 10 + 20 + 25, $WS_POPUP, $WS_EX_TOPMOST)
GUICtrlCreateList("", 0, 0, 100, 80)
GUICtrlSetData(-1, "1|2|3|4|5|6|7|8|9")

Global Const $MA_NOACTIVATE = 3; check WM_MOUSEACTIVATE
OnAutoItExitRegister("MemRelease")

; Register callback function and obtain handle to _New_WndProc
Global $___hNew_WndProc = DllCallbackRegister("WM_MOUSEACTIVATE", "int", "hwnd;uint;wparam;lparam")
; Get pointer to _New_WndProc
Global $___pNew_WndProc = DllCallbackGetPtr($___hNew_WndProc)
Global $___pOld_WndProc = _SubClass(GUICtrlGetHandle(-1), $___pNew_WndProc)

GUISetState(@SW_SHOWNOACTIVATE)

GUISwitch($hMain) ;Switch to main GUI

While GUIGetMsg() <> -3
Sleep(10)
WEnd

Func WM_MOUSEACTIVATE($hWnd, $iMsg, $wParam, $lParam)

Switch $iMsg

Case $WM_MOUSEACTIVATE
Return $MA_NOACTIVATE

Case $WM_LBUTTONDOWN, $WM_RBUTTONDOWN, $WM_MBUTTONDOWN, $WM_LBUTTONDBLCLK, $WM_RBUTTONDBLCLK, $WM_MBUTTONDBLCLK

;Get the Item
$iIndex = _GUICtrlListBox_ItemFromPoint($hWnd, _WinAPI_GetMousePosX(True, $hWnd), _WinAPI_GetMousePosY(True, $hWnd))

_SendMessage($hWnd, $LB_SETCURSEL, $iIndex) ;Change the selection

;Set the Text
GUICtrlSetData($Input, _GUICtrlListBox_GetText($hWnd, $iIndex))

Return 1; Block Windows processing

EndSwitch

Return _WinAPI_CallWindowProc($___pOld_WndProc, $hWnd, $iMsg, $wParam, $lParam)

EndFunc ;==>WM_MOUSEACTIVATE

Func _SubClass($hWnd, $pNew_WindowProc)
Local $iRes = _WinAPI_SetWindowLong($hWnd, -4, $pNew_WindowProc)
If @error Then Return SetError(1, 0, 0)
If $iRes = 0 Then Return SetError(1, 0, 0)
Return SetError(0, 0, $iRes)
EndFunc ;==>_SubClass

Func MemRelease()
_SubClass(GUICtrlGetHandle(-1), $___pOld_WndProc)
DllCallbackFree($___hNew_WndProc)
EndFunc ;==>MemRelease
You can add further features.

To add support of scrolling list through up, down keys and mouse wheel, you have to subclass edit control and redirect those WM_KEYDOWN|WM_MOUSEWHEEL messages to the listbox.

The UDF is still at very beggining stage :P.

Regards :)

Edited by PhoenixXL
  • Like 1

My code:

PredictText: Predict Text of an Edit Control Like Scite. Remote Gmail: Execute your Scripts through Gmail. StringRegExp:Share and learn RegExp.

Run As System: A command line wrapper around PSEXEC.exe to execute your apps scripts as System (LSA). Database: An easier approach for _SQ_LITE beginners.

MathsEx: A UDF for Fractions and LCM, GCF/HCF. FloatingText: An UDF for make your text floating. Clipboard Extendor: A clipboard monitoring tool. 

Custom ScrollBar: Scroll Bar made with GDI+, user can use bitmaps instead. RestrictEdit_SRE: Restrict text in an Edit Control through a Regular Expression.

Share this post


Link to post
Share on other sites
mpower

This would do your needs

#include <WindowsConstants.au3>
#include <WinAPI.au3>
#include <GuiListBox.au3>
#include <ScrollBarConstants.au3>
#include <Misc.au3>

$hMain = GUICreate("", -1, -1, 100, 100)
Global $Input = GUICtrlCreateInput("", 10, 10, -1, 20)
GUISetState()

GUICreate("", 100, 71, 100 + 10 + 15, 100 + 10 + 20 + 25, $WS_POPUP, $WS_EX_TOPMOST)
GUICtrlCreateList("", 0, 0, 100, 80)
GUICtrlSetData(-1, "1|2|3|4|5|6|7|8|9")

Global Const $MA_NOACTIVATE = 3; check WM_MOUSEACTIVATE
OnAutoItExitRegister("MemRelease")

; Register callback function and obtain handle to _New_WndProc
Global $___hNew_WndProc = DllCallbackRegister("WM_MOUSEACTIVATE", "int", "hwnd;uint;wparam;lparam")
; Get pointer to _New_WndProc
Global $___pNew_WndProc = DllCallbackGetPtr($___hNew_WndProc)
Global $___pOld_WndProc = _SubClass(GUICtrlGetHandle(-1), $___pNew_WndProc)

GUISetState(@SW_SHOWNOACTIVATE)

GUISwitch($hMain) ;Switch to main GUI

While GUIGetMsg() <> -3
Sleep(10)
WEnd

Func WM_MOUSEACTIVATE($hWnd, $iMsg, $wParam, $lParam)

Switch $iMsg

Case $WM_MOUSEACTIVATE
Return $MA_NOACTIVATE

Case $WM_LBUTTONDOWN, $WM_RBUTTONDOWN, $WM_MBUTTONDOWN, $WM_LBUTTONDBLCLK, $WM_RBUTTONDBLCLK, $WM_MBUTTONDBLCLK

;Get the Item
$iIndex = _GUICtrlListBox_ItemFromPoint($hWnd, _WinAPI_GetMousePosX(True, $hWnd), _WinAPI_GetMousePosY(True, $hWnd))

_SendMessage($hWnd, $LB_SETCURSEL, $iIndex) ;Change the selection

;Set the Text
GUICtrlSetData($Input, _GUICtrlListBox_GetText($hWnd, $iIndex))

Return 1; Block Windows processing

EndSwitch

Return _WinAPI_CallWindowProc($___pOld_WndProc, $hWnd, $iMsg, $wParam, $lParam)

EndFunc ;==>WM_MOUSEACTIVATE

Func _SubClass($hWnd, $pNew_WindowProc)
Local $iRes = _WinAPI_SetWindowLong($hWnd, -4, $pNew_WindowProc)
If @error Then Return SetError(1, 0, 0)
If $iRes = 0 Then Return SetError(1, 0, 0)
Return SetError(0, 0, $iRes)
EndFunc ;==>_SubClass

Func MemRelease()
_SubClass(GUICtrlGetHandle(-1), $___pOld_WndProc)
DllCallbackFree($___hNew_WndProc)
EndFunc ;==>MemRelease
You can add further features.

To add support of scrolling list through up, down keys and mouse wheel, you have to subclass edit control and redirect those WM_KEYDOWN|WM_MOUSEWHEEL messages to the listbox.

The UDF is still at very beggining stage :P.

Regards :)

Thanks PhoenixXL, this is great! Love your work!! Edited by mpower

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
Sign in to follow this  

×