我想獲得一個計數和列表ComboBox
控制這不是我的,所以我不能修改代碼。檢索ComboBox通過使用SendMessage API計數和項目
例如,通過使用SendMessage
API可以控制目標應用程序。
但是,如何通過掛鉤檢索目標控件的整個列表?
我想獲得一個計數和列表ComboBox
控制這不是我的,所以我不能修改代碼。檢索ComboBox通過使用SendMessage API計數和項目
例如,通過使用SendMessage
API可以控制目標應用程序。
但是,如何通過掛鉤檢索目標控件的整個列表?
你可以找到ComboBox
控制消息在這裏的列表:
要獲得項目數,您需要使用CB_GETCOUNT
消息,並獲得一個項目的文本你可以使用CB_GETLBTEXT
消息。
例
在這裏,我創建了一個ComboBoxHelper
類,你可以通過傳遞ComboBox
的Handle
創建它的實例,並使用其屬性:
SelectedIndex
爲Integer
:選擇指數返回,返回 - 1如果沒有選擇項目。Selectedtext
作爲String
:返回所選項目的文本,如果未選擇項目,則返回String.Empty
。ItemsCount
as Integer
:返回項目數。Items(index)
爲String
:返回文本中指定的項目(在指定索引的項目)Items
爲List(of String)
的:返回組合框的項目列表。如果沒有項目,它將返回一個空列表。Public Class ComboBoxHelper
Private hWnd As IntPtr
Const CB_GETCURSEL As Integer = &H147
Const CB_SETCURSEL As Integer = &H14E
Const CB_GETCOUNT As Integer = &H146
Const CB_GETLBTEXT As Integer = &H148
Const CB_GETLBTEXTLEN As Integer = &H149
<System.Runtime.InteropServices.DllImport("user32.dll")> _
Shared Function SendMessage(ByVal hWnd As IntPtr, ByVal Msg As Integer, _
ByVal wParam As Integer, ByRef lParam As Integer) As IntPtr
End Function
<System.Runtime.InteropServices.DllImport("user32.dll")> _
Shared Function SendMessage(ByVal hWnd As IntPtr, ByVal Msg As Integer, _
ByVal wParam As Integer, ByVal lParam As System.Text.StringBuilder) As IntPtr
End Function
Public Sub New(handle As IntPtr)
hWnd = handle
End Sub
Public Property SelectedIndex As Integer
Get
Return SendMessage(hWnd, CB_GETCURSEL, 0, 0).ToInt32()
End Get
Set(ByVal value As Integer)
SendMessage(hWnd, CB_SETCURSEL, value, 0).ToInt32()
End Set
End Property
Public ReadOnly Property ItemsCount As Integer
Get
Return SendMessage(hWnd, CB_GETCOUNT, 0, 0).ToInt32()
End Get
End Property
Public ReadOnly Property SelectedText As String
Get
Dim index = Me.SelectedIndex
If (Me.SelectedIndex = -1) Then
Return String.Empty
End If
Return Me.Items(index)
End Get
End Property
Public ReadOnly Property Items() As List(Of String)
Get
If (ItemsCount > 0) Then
Return Enumerable.Range(0, ItemsCount) _
.Select(Function(index) Items(index)).ToList()
Else
Return New List(Of String)
End If
End Get
End Property
Public ReadOnly Property Items(index As Integer) As String
Get
If (index < 0 OrElse index >= ItemsCount) Then
Throw New ArgumentOutOfRangeException("index")
End If
Dim length = SendMessage(hWnd, CB_GETLBTEXTLEN, index, 0).ToInt32()
Dim text As New System.Text.StringBuilder(length)
SendMessage(hWnd, CB_GETLBTEXT, index, text)
Return text.ToString()
End Get
End Property
End Class
下面是類的使用的一個示例:
Dim combo As New ComboBoxHelper(hWnd) 'You have hWnd
MessageBox.Show(combo.ItemsCount.ToString())
MessageBox.Show(combo.SelectedIndex.ToString())
MessageBox.Show(combo.SelectedText.ToString())
combo.Items.ForEach(Function(item) MessageBox.Show(item))
您不能通過進程邊界發送'CB_GETLBTEXT'(或任何窗口類私人消息)。對不起,沒有解決方案。 -1。 – IInspectable
@IInspectable不要太急於downvote的答案。首先測試它們。我使用兩種不同的流程對其進行了測試,並且它可以正常工作:) –
@IInspectable您可以使用2個不同的應用程序對其進行簡單測試,其中一個包含組合框,另一個使用我的ComboBoxHelper獲取項目文本和計數。在你測試之後,如果你喜歡答案,可以投下贊成票。我會在答案中保存一個虛擬變化,讓你改變你的投票;) –
可以使用UI自動化 –
[GetComboBoxInfo](https://msdn.microsoft.com/en-us /library/windows/desktop/bb775939(v=vs.85).aspx)並使用[COMBOBOXINFO]中的'hwndList'(https://msdn.microsoft.com/en-us/library/windows/desktop/bb775798( v = vs.85).aspx)? – RbMm
您已將您建議的解決方案交錯到問題描述中。請詢問您正在嘗試解決的問題。這意味着刪除所有對*「'SendMessage'」*和*「hooking」*的引用。 – IInspectable