分享
 
 
 

一份很有价值的子类化的源代码!

王朝other·作者佚名  2006-01-09
窄屏简体版  字體: |||超大  

' 新建一个 ActiveX DLL 工程,名称 SmartSubClassLib

' 以下代码放在标准模块里,模块名 mSmartSubClass

' ----------------------------------------------------

' Module mSmartSubClass

'

' Version... 1.0

' Date...... 24 April 2001

'

' Copyright (C) 2001 Andr閟 Pons (andres@vbsmart.com)

' ----------------------------------------------------

'API declarations:

Option Explicit

Public Const SSC_OLDPROC = "SSC_OLDPROC"

Public Const SSC_OBJADDR = "SSC_OBJADDR"

Private Declare Function GetProp Lib "user32" Alias "GetPropA" ( _

ByVal hWnd As Long, _

ByVal lpString As String) As Long

Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" ( _

Destination As Any, _

Source As Any, _

ByVal Length As Long)

'

' Function StartSubclassWindowProc()

'

' This is the first windowproc that receives messages

' for all subclassed windows.

' The aim of this function is to just collect the message

' and deliver it to the right SmartSubClass instance.

'

Public Function SmartSubClassWindowProc( _

ByVal hWnd As Long, _

ByVal uMsg As Long, _

ByVal wParam As Long, _

ByVal lParam As Long) As Long

Dim lRet As Long

Dim oSmartSubClass As SmartSubClass

'Get the memory address of the class instance...

lRet = GetProp(hWnd, SSC_OBJADDR)

If lRet <> 0 Then

'oSmartSubClass will point to the class instance

'without incrementing the class reference counter...

CopyMemory oSmartSubClass, lRet, 4

'Send the message to the class instance...

SmartSubClassWindowProc = oSmartSubClass.WindowProc(hWnd, _

uMsg, wParam, lParam)

'Remove the address from memory...

CopyMemory oSmartSubClass, 0&, 4

End If

End Function

' 以下代码放在类模块里,模块名 SmartSubClass

' ----------------------------------------------------

' Class SmartSubClass

'

' Version... 1.0

' Date...... 24 April 2001

'

' Copyright (C) 2001 Andr閟 Pons (andres@vbsmart.com)

' ----------------------------------------------------

Option Explicit

'Public event:

Public Event NewMessage( _

ByVal hWnd As Long, _

ByRef uMsg As Long, _

ByRef wParam As Long, _

ByRef lParam As Long, _

ByRef Cancel As Boolean)

'Private variables:

Private m_hWnds() As Long

'API declarations:

Private Const GWL_WNDPROC = (-4)

Private Declare Function GetWindowLong Lib "user32" Alias "GetWindowLongA" ( _

ByVal hWnd As Long, _

ByVal nIndex As Long) As Long

Private Declare Function SetWindowLong Lib "user32" Alias "SetWindowLongA" ( _

ByVal hWnd As Long, _

ByVal nIndex As Long, _

ByVal dwNewLong As Long) As Long

Private Declare Function CallWindowProc Lib "user32" Alias "CallWindowProcA" ( _

ByVal lpPrevWndFunc As Long, _

ByVal hWnd As Long, _

ByVal Msg As Long, _

ByVal wParam As Long, _

ByVal lParam As Long) As Long

Private Declare Function GetProp Lib "user32" Alias "GetPropA" ( _

ByVal hWnd As Long, _

ByVal lpString As String) As Long

Private Declare Function SetProp Lib "user32" Alias "SetPropA" ( _

ByVal hWnd As Long, _

ByVal lpString As String, _

ByVal hData As Long) As Long

Private Declare Function RemoveProp Lib "user32" Alias "RemovePropA" ( _

ByVal hWnd As Long, _

ByVal lpString As String) As Long

Private Declare Function IsWindow Lib "user32" ( _

ByVal hWnd As Long) As Long

'

' Function SubClassHwnd

'

' This is the core function in this class.

' You can use it to both subclass and unsubclass a window.

' Once a window is subclassed the event NewMessage will

' be raised every time a message is sent to the window.

'

Public Function SubClassHwnd(ByVal hWnd As Long, _

ByVal bSubClass As Boolean) As Boolean

Dim lRet As Long

lRet = 0

'Make sure that hWnd is a valid window handler...

If IsWindow(hWnd) Then

If bSubClass Then

'We are subclassing a window...

'Make sure that the window wasn't already subclassed...

If GetProp(hWnd, SSC_OLDPROC) = 0 Then

'Now we subclass the window by changing its windowproc

lRet = SetWindowLong(hWnd, GWL_WNDPROC, _

AddressOf SmartSubClassWindowProc)

'Check if we've managed to subclass...

If lRet <> 0 Then

'Store the old windowproc and the memory

' address of this class...

SetProp hWnd, SSC_OLDPROC, lRet

SetProp hWnd, SSC_OBJADDR, ObjPtr(Me)

'Add the window to an internal list of

' subclassed windows...

pAddHwndToList hWnd

End If

End If

Else

'We are unsubclassing a window...

'Get the old windowproc...

lRet = GetProp(hWnd, SSC_OLDPROC)

If lRet <> 0 Then

'Unsubclass the window...

lRet = SetWindowLong(hWnd, GWL_WNDPROC, lRet)

End If

'Remove any extra information...

RemoveProp hWnd, SSC_OLDPROC

RemoveProp hWnd, SSC_OBJADDR

'Remove the window from the internal list...

pRemoveHwndFromList hWnd

End If

Else

'If hWnd is not a valid window,

'make sure that there isn't stored garbage...

RemoveProp hWnd, SSC_OLDPROC

RemoveProp hWnd, SSC_OBJADDR

pRemoveHwndFromList hWnd

End If

SubClassHwnd = (lRet <> 0)

End Function

'

' Function WindowProc

'

' This is the link between the windowproc and the class instance.

' Every time SmartSubClassWindowProc receives a window message,

' it will post it to the right class instance.

'

Friend Function WindowProc( _

ByVal hWnd As Long, _

ByVal uMsg As Long, _

ByVal wParam As Long, _

ByVal lParam As Long) As Long

Dim lRet As Long

Dim bCancel As Boolean

bCancel = False

WindowProc = 0

'Raise the event NewMessage...

'This will tell the owner of the class variable that a

'new message is ready to be processed.

'The owner will be able to cancel the message by setting

'the variable bCancel to True.

RaiseEvent NewMessage(hWnd, uMsg, wParam, lParam, bCancel)

'If the event hasn't been canceled by the owner

'we need to send it to the original windowproc

If Not bCancel Then

lRet = GetProp(hWnd, SSC_OLDPROC)

If lRet <> 0 Then

'Send the message to the original windowproc...

WindowProc = CallWindowProc(lRet, hWnd, uMsg, wParam, lParam)

End If

End If

End Function

'

' Every instance of the class mantains an internal

' list of subclassed windows.

'

Private Sub Class_Initialize()

ReDim m_hWnds(0) As Long

End Sub

'

' When the class terminates it makes sure that

' there are no remainig subclassed windows.

'

Private Sub Class_Terminate()

Dim i As Long

For i = UBound(m_hWnds) To 1 Step -1

If m_hWnds(i) > 0 Then

SubClassHwnd m_hWnds(i), False

End If

Next i

End Sub

'

' Private Function pFindHwndInList()

'

' This functions searches for a specific window

' in its internal list. If it doesn't find the

' window it returns 0.

'

Private Function pFindHwndInList(ByVal hWnd As Long) As Long

Dim i As Long

Dim lPos As Long

lPos = 0

For i = 1 To UBound(m_hWnds)

If m_hWnds(i) = hWnd And m_hWnds(i) > 0 Then

lPos = i

Exit For

End If

Next i

pFindHwndInList = lPos

End Function

'

' Private Sub pAddHwndToList()

'

' This procedure adds a window handle to the internal list...

'

Private Sub pAddHwndToList(ByVal hWnd As Long)

Dim lPos As Long

If pFindHwndInList(hWnd) = 0 Then

lPos = pFindNextPositionAvailableInList

If lPos <> 0 Then

m_hWnds(lPos) = hWnd

Else

lPos = UBound(m_hWnds) + 1

ReDim Preserve m_hWnds(lPos) As Long

m_hWnds(lPos) = hWnd

End If

End If

End Sub

'

' Private Sub pRemoveHwndFromList()

'

' This procedure removes a window handle from the internal list...

'

Private Sub pRemoveHwndFromList(ByVal hWnd As Long)

Dim lPos As Long

lPos = pFindHwndInList(hWnd)

If lPos <> 0 Then

If lPos = UBound(m_hWnds) Then

ReDim Preserve m_hWnds(lPos - 1) As Long

Else

m_hWnds(lPos) = -1

End If

End If

End Sub

'

' Private Function pFindNextPositionAvailableInList()

'

' This functions searches for an "empty" entry in the

' internal list of window handles. When an entry is

' removed its is marked as empty by setting its value to -1.

'

' If there are no positions available, the function returns 0.

'

Private Function pFindNextPositionAvailableInList() As Long

Dim i As Long

Dim lPos As Long

lPos = 0

For i = 1 To UBound(m_hWnds)

If m_hWnds(i) <= 0 Then

lPos = i

Exit For

End If

Next i

pFindNextPositionAvailableInList = lPos

End Function

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
推荐阅读
 
 
 
>>返回首頁<<
 
靜靜地坐在廢墟上,四周的荒凉一望無際,忽然覺得,淒涼也很美
© 2005- 王朝網路 版權所有