找回密码
 加入
搜索
楼主: kk_lee69

[AU3基础] 如何使用左键单点击达成LISTVIEW连续选中状态??

  [复制链接]
发表于 2017-8-28 10:11:28 | 显示全部楼层
本帖最后由 yamakawa 于 2017-8-28 10:17 编辑

WM_NOTIFY还是可以注册的。。。这个是用上面代码加上帮助文件复制来的wm_notify示例
#include <WindowsConstants.au3>
#include <WinAPI.au3>
#include <GuiListView.au3>
#include <GUIConstantsEx.au3>
#include <GuiStatusBar.au3>
 
Opt('GUIOnEventMode', 1)
 
Global $idListView, $hListView, $pListViewFunc, $idAddSingleSel, $idDelSingleSel
 
Example()
While 1
        Sleep(1000)
WEnd
 
Func Example()
        ; Create GUI
        GUICreate("ctrl+single-click --> single-click", 420, 200)
        GUISetOnEvent(-3, '_Exit')
        ; Create ListView
        $idListView = GUICtrlCreateListView("", 10, 10, 400, 180, $GUI_SS_DEFAULT_LISTVIEW - $LVS_SINGLESEL, $WS_EX_CLIENTEDGE)
        _GUICtrlListView_SetExtendedListViewStyle($idListView, $LVS_EX_DOUBLEBUFFER + $LVS_EX_FULLROWSELECT)
        $hListView = GUICtrlGetHandle($idListView)
 
        ; Add columns to ListView
        _GUICtrlListView_InsertColumn($idListView, 0, "Column 1", 94)
        _GUICtrlListView_InsertColumn($idListView, 1, "Column 2", 94)
        _GUICtrlListView_InsertColumn($idListView, 2, "Column 3", 94)
        _GUICtrlListView_InsertColumn($idListView, 3, "Column 4", 94)
 
        ; Fill ListView
        Local $iItems = 100
        For $i = 0 To $iItems - 1
                GUICtrlCreateListViewItem($i & "/Column 1|" & $i & "/Column 2|" & $i & "/Column 3|" & $i & "/Column 4", $idListView)
        Next
 
        ; Subclass ListView to receive keyboard/mouse messages
        $pListViewFunc = DllCallbackGetPtr(DllCallbackRegister("ListViewFunc", "lresult", "hwnd;uint;wparam;lparam;uint_ptr;dword_ptr"))
        _WinAPI_SetWindowSubclass($hListView, $pListViewFunc, 0, 0) ; $iSubclassId = 0, $pData = 0
 
        ; Add/del single selection
        $idAddSingleSel = GUICtrlCreateDummy()
        GUICtrlSetOnEvent(-1, '_AddSingleSel')
        $idDelSingleSel = GUICtrlCreateDummy()
        GUICtrlSetOnEvent(-1, '_DelSingleSel')
 
        ;GUIRegisterMsg
                GUIRegisterMsg($WM_NOTIFY,"wm_notify")
        ; Show GUI
        GUISetState(@SW_SHOW)
EndFunc   ;==>Example
 

Func ListViewFunc($hWnd, $iMsg, $wParam, $lParam, $iSubclassId, $pData)
        If $iMsg <> $WM_LBUTTONDOWN Then
                Local $result = DllCall("comctl32.dll", "lresult", "DefSubclassProc", "hwnd", $hWnd, "uint", $iMsg, "wparam", $wParam, "lparam", $lParam)
                If Not @error Then
                        Return $result[0]
                Else
                        Return
                EndIf
        EndIf
        Switch $wParam
                Case 0x0001
                        If _GUICtrlListView_GetSelectedCount($idListView) Then
                                Local $aHit = _GUICtrlListView_HitTest(GUICtrlGetHandle($idListView), BitAND($lParam, 0xFFFF), BitShift($lParam, 16))
                                If Not (@error Or $aHit[0] = -1) Then
                                        If _GUICtrlListView_GetItemSelected($idListView, $aHit[0]) Then
                                                GUICtrlSendToDummy($idDelSingleSel, $aHit[0])
                                        Else
                                                GUICtrlSendToDummy($idAddSingleSel, $aHit[0])
                                        EndIf
                                EndIf
                                Return 0
                        EndIf
                Case 0x0009
                        Return 0
        EndSwitch
        Local $result = DllCall("comctl32.dll", "lresult", "DefSubclassProc", "hwnd", $hWnd, "uint", $iMsg, "wparam", $wParam, "lparam", $lParam)
        If Not @error Then
                Return $result[0]
        Else
                Return
        EndIf
        #forceref $iSubclassId, $pData
EndFunc   ;==>ListViewFunc
 
Func _AddSingleSel()
        Local $iItem = GUICtrlRead($idAddSingleSel)
        _GUICtrlListView_SetItemSelected($idListView, $iItem, True)
        _GUICtrlListView_SetItemFocused($idListView, $iItem)
EndFunc   ;==>_AddSingleSel
Func _DelSingleSel()
        Local $iItem = GUICtrlRead($idDelSingleSel)
        _GUICtrlListView_SetItemSelected($idListView, $iItem, False)
        _GUICtrlListView_SetItemFocused($idListView, $iItem)
EndFunc   ;==>_DelSingleSel
Func _Exit()
        _WinAPI_RemoveWindowSubclass($hListView, $pListViewFunc, 0)
        GUIDelete()
        Exit
EndFunc   ;==>_Exit
 
Func _WinAPI_SetWindowSubclass($hWnd, $pSubclassProc, $idSubClass, $pData = 0)
        Local $aRet = DllCall('comctl32.dll', 'bool', 'SetWindowSubclass', 'hwnd', $hWnd, 'ptr', $pSubclassProc, 'uint_ptr', $idSubClass, _
                        'dword_ptr', $pData)
        If @error Then Return SetError(@error, @extended, 0)
        ; If Not $aRet[0] Then Return SetError(1000, 0, 0)
 
        Return $aRet[0]
EndFunc   ;==>_WinAPI_SetWindowSubclass
Func _WinAPI_RemoveWindowSubclass($hWnd, $pSubclassProc, $idSubClass)
        Local $aRet = DllCall('comctl32.dll', 'bool', 'RemoveWindowSubclass', 'hwnd', $hWnd, 'ptr', $pSubclassProc, 'uint_ptr', $idSubClass)
        If @error Then Return SetError(@error, @extended, False)
        Return $aRet[0]
EndFunc   ;==>_WinAPI_RemoveWindowSubclass


Func WM_NOTIFY($hWnd, $iMsg, $wParam, $lParam)
    #forceref $hWnd, $iMsg, $wParam
    Local $hWndFrom, $iIDFrom, $iCode, $tNMHDR, $hWndListView, $tInfo
    $hWndListView = $idListView
    If Not IsHWnd($idListView) Then $hWndListView = GUICtrlGetHandle($idListView)

    $tNMHDR = DllStructCreate($tagNMHDR, $lParam)
    $hWndFrom = HWnd(DllStructGetData($tNMHDR, "hWndFrom"))
    $iIDFrom = DllStructGetData($tNMHDR, "IDFrom")
    $iCode = DllStructGetData($tNMHDR, "Code")
    Switch $hWndFrom
        Case $hWndListView
            Switch $iCode
                                
                Case $LVN_COLUMNCLICK ; A column was clicked
                    $tInfo = DllStructCreate($tagNMLISTVIEW, $lParam)
                    _DebugPrint("$LVN_COLUMNCLICK" & @CRLF & "--> hWndFrom:" & @TAB & $hWndFrom & @CRLF & _
                            "-->IDFrom:" & @TAB & $iIDFrom & @CRLF & _
                            "-->Code:" & @TAB & $iCode & @CRLF & _
                            "-->Item:" & @TAB & DllStructGetData($tInfo, "Item") & @CRLF & _
                            "-->SubItem:" & @TAB & DllStructGetData($tInfo, "SubItem") & @CRLF & _
                            "-->NewState:" & @TAB & DllStructGetData($tInfo, "NewState") & @CRLF & _
                            "-->OldState:" & @TAB & DllStructGetData($tInfo, "OldState") & @CRLF & _
                            "-->Changed:" & @TAB & DllStructGetData($tInfo, "Changed") & @CRLF & _
                            "-->ActionX:" & @TAB & DllStructGetData($tInfo, "ActionX") & @CRLF & _
                            "-->ActionY:" & @TAB & DllStructGetData($tInfo, "ActionY") & @CRLF & _
                            "-->Param:" & @TAB & DllStructGetData($tInfo, "Param"))
                    ; No return value
                Case $LVN_DELETEITEM ; An item is about to be deleted
                    $tInfo = DllStructCreate($tagNMLISTVIEW, $lParam)
                    _DebugPrint("$LVN_DELETEITEM" & @CRLF & "--> hWndFrom:" & @TAB & $hWndFrom & @CRLF & _
                            "-->IDFrom:" & @TAB & $iIDFrom & @CRLF & _
                            "-->Code:" & @TAB & $iCode & @CRLF & _
                            "-->Item:" & @TAB & DllStructGetData($tInfo, "Item") & @CRLF & _
                            "-->SubItem:" & @TAB & DllStructGetData($tInfo, "SubItem") & @CRLF & _
                            "-->NewState:" & @TAB & DllStructGetData($tInfo, "NewState") & @CRLF & _
                            "-->OldState:" & @TAB & DllStructGetData($tInfo, "OldState") & @CRLF & _
                            "-->Changed:" & @TAB & DllStructGetData($tInfo, "Changed") & @CRLF & _
                            "-->ActionX:" & @TAB & DllStructGetData($tInfo, "ActionX") & @CRLF & _
                            "-->ActionY:" & @TAB & DllStructGetData($tInfo, "ActionY") & @CRLF & _
                            "-->Param:" & @TAB & DllStructGetData($tInfo, "Param"))
                    ; No return value

                Case $LVN_KEYDOWN ; A key has been pressed
                    $tInfo = DllStructCreate($tagNMLVKEYDOWN, $lParam)
                    _DebugPrint("$LVN_KEYDOWN" & @CRLF & "--> hWndFrom:" & @TAB & $hWndFrom & @CRLF & _
                            "-->IDFrom:" & @TAB & $iIDFrom & @CRLF & _
                            "-->Code:" & @TAB & $iCode & @CRLF & _
                            "-->VKey:" & @TAB & DllStructGetData($tInfo, "VKey") & @CRLF & _
                            "-->Flags:" & @TAB & DllStructGetData($tInfo, "Flags"))
                    ; No return value
                Case $NM_CLICK ; Sent by a list-view control when the user clicks an item with the left mouse button
                    $tInfo = DllStructCreate($tagNMITEMACTIVATE, $lParam)
                    _DebugPrint("$NM_CLICK" & @CRLF & "--> hWndFrom:" & @TAB & $hWndFrom & @CRLF & _
                            "-->IDFrom:" & @TAB & $iIDFrom & @CRLF & _
                            "-->Code:" & @TAB & $iCode & @CRLF & _
                            "-->Index:" & @TAB & DllStructGetData($tInfo, "Index") & @CRLF & _
                            "-->SubItem:" & @TAB & DllStructGetData($tInfo, "SubItem") & @CRLF & _
                            "-->NewState:" & @TAB & DllStructGetData($tInfo, "NewState") & @CRLF & _
                            "-->OldState:" & @TAB & DllStructGetData($tInfo, "OldState") & @CRLF & _
                            "-->Changed:" & @TAB & DllStructGetData($tInfo, "Changed") & @CRLF & _
                            "-->ActionX:" & @TAB & DllStructGetData($tInfo, "ActionX") & @CRLF & _
                            "-->ActionY:" & @TAB & DllStructGetData($tInfo, "ActionY") & @CRLF & _
                            "-->lParam:" & @TAB & DllStructGetData($tInfo, "lParam") & @CRLF & _
                            "-->KeyFlags:" & @TAB & DllStructGetData($tInfo, "KeyFlags"))
                    ; No return value
                Case $NM_DBLCLK ; Sent by a list-view control when the user double-clicks an item with the left mouse button
                    $tInfo = DllStructCreate($tagNMITEMACTIVATE, $lParam)
                    _DebugPrint("$NM_DBLCLK" & @CRLF & "--> hWndFrom:" & @TAB & $hWndFrom & @CRLF & _
                            "-->IDFrom:" & @TAB & $iIDFrom & @CRLF & _
                            "-->Code:" & @TAB & $iCode & @CRLF & _
                            "-->Index:" & @TAB & DllStructGetData($tInfo, "Index") & @CRLF & _
                            "-->SubItem:" & @TAB & DllStructGetData($tInfo, "SubItem") & @CRLF & _
                            "-->NewState:" & @TAB & DllStructGetData($tInfo, "NewState") & @CRLF & _
                            "-->OldState:" & @TAB & DllStructGetData($tInfo, "OldState") & @CRLF & _
                            "-->Changed:" & @TAB & DllStructGetData($tInfo, "Changed") & @CRLF & _
                            "-->ActionX:" & @TAB & DllStructGetData($tInfo, "ActionX") & @CRLF & _
                            "-->ActionY:" & @TAB & DllStructGetData($tInfo, "ActionY") & @CRLF & _
                            "-->lParam:" & @TAB & DllStructGetData($tInfo, "lParam") & @CRLF & _
                            "-->KeyFlags:" & @TAB & DllStructGetData($tInfo, "KeyFlags"))
                    ; No return value
                Case $NM_KILLFOCUS ; The control has lost the input focus
                    _DebugPrint("$NM_KILLFOCUS" & @CRLF & "--> hWndFrom:" & @TAB & $hWndFrom & @CRLF & _
                            "-->IDFrom:" & @TAB & $iIDFrom & @CRLF & _
                            "-->Code:" & @TAB & $iCode)
                    ; No return value
                Case $NM_RCLICK ; Sent by a list-view control when the user clicks an item with the right mouse button
                    $tInfo = DllStructCreate($tagNMITEMACTIVATE, $lParam)
                    _DebugPrint("$NM_RCLICK" & @CRLF & "--> hWndFrom:" & @TAB & $hWndFrom & @CRLF & _
                            "-->IDFrom:" & @TAB & $iIDFrom & @CRLF & _
                            "-->Code:" & @TAB & $iCode & @CRLF & _
                            "-->Index:" & @TAB & DllStructGetData($tInfo, "Index") & @CRLF & _
                            "-->SubItem:" & @TAB & DllStructGetData($tInfo, "SubItem") & @CRLF & _
                            "-->NewState:" & @TAB & DllStructGetData($tInfo, "NewState") & @CRLF & _
                            "-->OldState:" & @TAB & DllStructGetData($tInfo, "OldState") & @CRLF & _
                            "-->Changed:" & @TAB & DllStructGetData($tInfo, "Changed") & @CRLF & _
                            "-->ActionX:" & @TAB & DllStructGetData($tInfo, "ActionX") & @CRLF & _
                            "-->ActionY:" & @TAB & DllStructGetData($tInfo, "ActionY") & @CRLF & _
                            "-->lParam:" & @TAB & DllStructGetData($tInfo, "lParam") & @CRLF & _
                            "-->KeyFlags:" & @TAB & DllStructGetData($tInfo, "KeyFlags"))
                    ;Return 1 ; not to allow the default processing
                    Return 0 ; allow the default processing
                Case $NM_RDBLCLK ; Sent by a list-view control when the user double-clicks an item with the right mouse button
                    $tInfo = DllStructCreate($tagNMITEMACTIVATE, $lParam)
                    _DebugPrint("$NM_RDBLCLK" & @CRLF & "--> hWndFrom:" & @TAB & $hWndFrom & @CRLF & _
                            "-->IDFrom:" & @TAB & $iIDFrom & @CRLF & _
                            "-->Code:" & @TAB & $iCode & @CRLF & _
                            "-->Index:" & @TAB & DllStructGetData($tInfo, "Index") & @CRLF & _
                            "-->SubItem:" & @TAB & DllStructGetData($tInfo, "SubItem") & @CRLF & _
                            "-->NewState:" & @TAB & DllStructGetData($tInfo, "NewState") & @CRLF & _
                            "-->OldState:" & @TAB & DllStructGetData($tInfo, "OldState") & @CRLF & _
                            "-->Changed:" & @TAB & DllStructGetData($tInfo, "Changed") & @CRLF & _
                            "-->ActionX:" & @TAB & DllStructGetData($tInfo, "ActionX") & @CRLF & _
                            "-->ActionY:" & @TAB & DllStructGetData($tInfo, "ActionY") & @CRLF & _
                            "-->lParam:" & @TAB & DllStructGetData($tInfo, "lParam") & @CRLF & _
                            "-->KeyFlags:" & @TAB & DllStructGetData($tInfo, "KeyFlags"))
                    ; No return value
                Case $NM_RETURN ; The control has the input focus and that the user has pressed the ENTER key
                    _DebugPrint("$NM_RETURN" & @CRLF & "--> hWndFrom:" & @TAB & $hWndFrom & @CRLF & _
                            "-->IDFrom:" & @TAB & $iIDFrom & @CRLF & _
                            "-->Code:" & @TAB & $iCode)
                    ; No return value
                Case $NM_SETFOCUS ; The control has received the input focus
                    _DebugPrint("$NM_SETFOCUS" & @CRLF & "--> hWndFrom:" & @TAB & $hWndFrom & @CRLF & _
                            "-->IDFrom:" & @TAB & $iIDFrom & @CRLF & _
                            "-->Code:" & @TAB & $iCode)
                    ; No return value
                                                        Case $NM_CUSTOMDRAW
                    _DebugPrint("$NM_CUSTOMDRAW")
                    $tDraw = DllStructCreate($tagNMLVCUSTOMDRAW, $lParam)
                    $iDrawStage = DllStructGetData($tDraw, "dwDrawStage")
                    $iItemSpec = DllStructGetData($tDraw, "dwItemSpec")
                    Switch $iDrawStage
                        Case $CDDS_PREPAINT
                            _DebugPrint("$CDDS_PREPAINT")
                            Return $CDRF_NOTIFYITEMDRAW
                        Case $CDDS_ITEMPREPAINT
                            _DebugPrint("$CDDS_ITEMPREPAINT")
                            If BitAND($iItemSpec, 1) = 1 Then
                                DllStructSetData($tDraw, "clrTextBk", 0xff00cc)
                            Else
                                DllStructSetData($tDraw, "clrTextBk", 0xccff00)
                            EndIf
                            Return $CDRF_NEWFONT
EndSwitch
            EndSwitch
    EndSwitch
    Return $GUI_RUNDEFMSG
EndFunc   ;==>WM_NOTIFY

Func _DebugPrint($s_Text, $sLine = @ScriptLineNumber)
    ConsoleWrite( _
            "!===========================================================" & @CRLF & _
            "+======================================================" & @CRLF & _
            "-->Line(" & StringFormat("%04d", $sLine) & "):" & @TAB & $s_Text & @CRLF & _
            "+======================================================" & @CRLF)
EndFunc   ;==>_DebugPrint
发表于 2017-8-28 10:22:34 | 显示全部楼层
回复 30# kk_lee69


    因为原来代码里面有句
Return DllCall( "comctl32.dll", "lresult", "DefSubclassProc", "hwnd", $hWnd, "uint", $iMsg, "wparam", $wParam, "lparam", $lParam )[0]
这句理解起来就是,把没处理的交还给系统,让系统处理,然后就可以用wm_notify处理了
 楼主| 发表于 2017-8-28 11:03:32 | 显示全部楼层
回复 32# yamakawa

果然可以ㄟ

不過我不能理解的是 我嘗試過 註冊 WM_LBUTTONDOWN

卻只能在非 LISTVIEW 區域 接收到訊息

對方 大神 怎麼查到資料  知道要這樣去做的.....

真想了解多點
发表于 2017-8-28 11:11:00 | 显示全部楼层
回复 33# kk_lee69


    因为你在控件上按下鼠标,产生的消息被控件(listview)捕捉了。所以窗口收不到你消息
发表于 2017-8-29 13:31:20 | 显示全部楼层
回复 32# yamakawa

同一窗口有二个GUICtrlCreateListView控件,
点击第二个Listview2 控件,第一个Listview1 控件己选择的条目就失去高亮,
怎样才能保持第一个Listview1 控件己选择的条目高亮
 楼主| 发表于 2017-8-29 13:34:59 | 显示全部楼层
回复 35# chzj589

如果內定高亮 肯定不行吧 因為失去焦點了.....

這時候 我會選擇 用自繪背景 的方式 上顏色  這樣就不怕失去焦點.....
发表于 2017-8-29 14:18:30 | 显示全部楼层
回复 22# afan
请教, 同一窗口有二个GUICtrlCreateListView控件,
点击第二个Listview2 控件,第一个Listview1 控件己选择的条目就失去高亮,
点击第二个Listview2 控件,能保持第一个Listview1 控件己选择的条目高亮?
 楼主| 发表于 2017-8-30 11:30:01 | 显示全部楼层
回复 37# chzj589

這樣的效果嗎??



圖片中 可看到 原來的焦點 因為 點了另外一個 LISTVIEW

顏色就會變成反灰色  這個 要讓這個功能 失效的話 我看 會有點難

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?加入

×
发表于 2017-8-30 11:42:57 | 显示全部楼层
回复 38# kk_lee69

就是图片上hListView与hListView2的上色,
点击hListView2,
己选择的hListView条目上色不消失。
发表于 2017-8-30 11:50:01 | 显示全部楼层
回复 7# chzj589


本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?加入

×
 楼主| 发表于 2017-8-30 12:01:18 | 显示全部楼层
回复 40# chzj589


你有看到我的 圖片中 爸爸11 嗎  那個是最後點選的位置.....  所以  跟你現在的一樣  會變灰色

但是 你看到 上面的沒變灰色的原因 是 因為 他們並沒有 SELECTED 而是 CHECKED

所以 不會變色   我只是把 CHECKED 弄得很像 SELECTED 而已

CHECKED 與 SELECTED 是不一樣的
 楼主| 发表于 2017-8-30 12:05:18 | 显示全部楼层
回复 40# chzj589


    或者先提供一下你寫的範例吧
发表于 2017-8-30 14:13:21 | 显示全部楼层
回复 40# chzj589


   官网的这个代码,因为他本身就是截取鼠标单击事件,所以看起来是selected选中状态,其实是假的,和正常系统处理的方法是不一样的,所以失去焦点,就变了。。俺能看懂,但是怎么改。暂时没头绪。也许该去官网问问。。
 楼主| 发表于 2017-8-30 14:35:49 | 显示全部楼层
回复 43# yamakawa


    你的看法跟我剛好相反
我的看法是  SELECTED 是真的   但是 只要是 SELECTED 的方式  失去焦點 就會變色

反而是 CHECKED 加上 背景色 這樣 看起來像 SELECTED    但是 失去焦點 不會變色
 楼主| 发表于 2017-8-30 15:31:17 | 显示全部楼层
回复 39# chzj589

你寫的程式給我  我幫你改看看
您需要登录后才可以回帖 登录 | 加入

本版积分规则

QQ|手机版|小黑屋|AUTOIT CN ( 鲁ICP备19019924号-1 )谷歌 百度

GMT+8, 2024-3-29 15:29 , Processed in 0.070996 second(s), 14 queries .

Powered by Discuz! X3.5 Licensed

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表