重庆分公司,新征程启航
为企业提供网站建设、域名注册、服务器等服务
'把图片的声明放在外面,类里面过程外面,而且要用As,不然等会儿没法用
10年积累的网站设计、成都网站制作经验,可以快速应对客户对网站的新想法和需求。提供各种问题对应的解决方案。让选择我们的客户得到更好、更有力的网络服务。我虽然不认识你,你也不认识我。但先网站设计后付款的网站建设流程,更有建宁免费网站建设让你可以放心的选择与我们合作。
Dim myPicture As New System.Windows.Forms.PictureBox()
'动态生成的控件,加一行
Private Sub UserControl1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load
Me.Panel3.Controls.Add(myPicture)
myPicture.Size =New System.Drawing.Size(115, 160)
myPicture.TabStop =False
myPicture.Name ="p"
myPicture.Cursor = Cursors.Hand
AddHandler myPicture.Click, AddressOf mypic_Click '添加事件
AddHandler returnid, AddressOf idReturned '绑定事件和过程
End Sub
'再来个事件,放在声明的地方,就是类里面、过程外面
Private Event returnid(ByVal id As String) '这个事件可以传递值哦~
'普通的单击事件
Private Sub mypic_Click()
RaiseEvent returnid(myPicture.Name)
End Sub
'会传值的事件过程
Private Sub idReturned(ByVal id As String)
Dim bookInfo As New BookInfo
bookInfo.Show()
Me.Parent.Enabled = False
'用id变量做点什么吧
End Sub
如果要改事件的签名(参数一类的)的话,得重写控件。你可以这样自己弄一个事件。
TextBox1_TextChanged() 'TextBox1.text属性改变时发生
Label1_Click() 'Label1被鼠标点击时发生
MenuItem1_Click() 'MenuItem1被鼠标点击时发生
Label1_MouseDown() '鼠标左键在Label1上按下时发生
Label1_DoubleClick() '有点难我也不太清楚,在MSDN上查了下:
双击操作由用户操作系统的鼠标设置确定。用户可以设置两次单击鼠标按钮之间的时间以便将这两次单击认为是双击而不是两次单击。每当双击控件时,就会引发 Click 事件。例如,如果您有 Form 的 Click 和 DoubleClick 事件的事件处理程序,则当双击该窗体并同时调用这两个方法时,会引发 Click 和 DoubleClick 事件。如果双击一个控件并且该控件不支持 DoubleClick 事件,则 Click 事件可能被引发两次。
Label1_MouseUp() '鼠标左键在Label1上放开时发生,一般与Label1_MouseDown()搭配使用
TextBox2_MouseMove() '鼠标停留在TextBox2上时发生
Form1_load() '加载窗体时发生
Form1_click() '点击窗体时发生
Form1_Resize() '窗体调整大小后发生
Form1_KeyPress() '当窗体有焦点键盘有操作时发生
Form1_KeyDown() '当窗体具有焦点并键盘有按键按下时发生
Form1_KeyUp() '当窗体焦点并键盘有按键放开时发生
熟悉VB的朋友对使用ActiveX控件一定不会陌生,众多控件极大地方便了编程,但
唯一的缺陷是不能动态加载控件,必须在设计时通过引用,将控件放置在窗体上。
VB6.0已能够解决该问题,只是帮助中没有明确说明,并且没有描述到一些关键功能,
由于以前的版本中可以动态创建进程外服务:如果对象是外部可创建的,可在 Set 语
句中用 New 关键字、CreateObject 或 GetObject 从部件外面将对象引用赋予变量。
如果对象是从属对象,则需使用高层对象的方法,在 Set 语句中指定一个对象引用:
Dim xlApp1 As Excel.Application
Set xlApp1 = New Excel.Application
或
Dim xlApp As Object '定义存放引用对象的变量。
Set xlApp = CreateObject("excel.application")
xlApp.Visible = True
---- 这些语法很容易造成误导,以为动态加载ActiveX控件也是此方法,可能有朋友也
象我一样利用CreateObject尝试了无数次,却无功而返,不知微软公司是出于何种考
虑,动态加载ActiveX控件是扩展控件集合的方式实现,通过实际摸索,终于就如何实
现动态ActiveX控件找出了一条切实可行的方法,下面以一个具体的实例来详细说明。
一、ActiveX控件
---- ActiveX 控件是 Visual Basic 工具箱的扩充部分。使用 ActiveX 控件的方法与
使用其它标准内装的控件,如 CheckBox 控件,完全一样。在程序中加入 ActiveX 控
件后,它将成为开发和运行环境的一部分,并为应用程序提供新的功能。
---- ActiveX 部件通过客户端/服务器关系与应用程序— 及与部件相互之间— 交互作
用。客户端是使用部件功能的应用程序代码或部件。服务器是部件及其关联的对象。例
如,假设应用程序使用 ActiveX 控件来提供一个标准的雇员窗体,供公司的多种应用
程序使用。提供雇员窗体的 ActiveX 控件就是服务器,使用这个控件的应用程序就是
服务器的客户端。
二、加载方法
---- VB6.0中对Controls 集合进行了扩展,以前版本中Controls 集合在窗体上列举出
已加载的控件,这在迭代过程中是很有用的。Controls 集合标识一个叫做 Controls
的内在窗体级变量。如果忽略可选的 object 所在处的整数,则关键字 Controls 必须
包括在内。我们通常在窗口中使用如下代码:
Text1.Text="Hello, world"
其实也可以使用如下代码达到同一目的:
Controls(1).Text="Hello, world"
---- 在VB6.0中除了原来的Clear、Remove 方法外(很奇怪,为什么微软在VB5.0中只提
供这两种方法,而没有提供Add方法,因为没有Add,这两种方法也就没什么用处),增
加了Add方法,该方法就是用于动态加载控件的:
Controls.Add(progid as String, Name as String);
progid: ActiveX部件的ProgID,如:"VB.CheckBox";
Name:ActiveX部件加载后的名称,如: "MyCheckBox";
若要在窗体上添加一个名为MyButton的按钮,可以使用:
dim oControl as Object '窗体级变量
注意:这里声明为Object对象类型
Private Sub LoadControl()
Set oControl = Controls.Add
("VB.CommandButton", "MyButton")
oControl.Left = 10
oControl.Top = 10
oControl.Visible = True '使控件可见
End Sub
---- 这是VB6.0的标准语法,它在例程中也是如此演示的,不过该方法虽然现实了控件
的动态加载,按钮显示在窗体上,可以象普通按钮一样按下去,但加载的控件不能预先
设计响应事件代码,如:事件Sub MyButton_Click()将是非法的,当然,可以将要响应
的事件封装在控件内部。就编程的观点来看该方法没什么大的用处,开发ActiveX控件
的目的是为了资源共享,为了被其他开发人员利用,所以要提供必要的事件接口,显然
利用该方法不行,通过分析VBControls等相关对象,找出VBControlExtender对象与
EventInfo相结合能提供事件陷井捕捉,VBControlExtender对象对动态添加控件特别有
用,它提供了一套通用的属性、方法、事件给开发人员,它的一个突出特点是能编程设
计控件的事件,熟习类编程的朋友对带事件的对象声明一定不会陌生:
---- Dim WithEvents objElemt as CElemtVBControlExtender也不例外,声明的语法
一样,只不过它有个特殊的事件ObjectEvent(Info As EventInfo),它能捕捉到对象使
用RaiseEvent产生的所有事件,EventInfo数据结构映射了事件的名称、参数个数和参
数的值。VBControlExtender和 EventInfo相结合,采用Select Case 就可以预先将不
同类对象的事件放置一起,各自独立运作。将上面的代码改写一下就能提供Click事件
了:
---- Dim WithEvents oControl As VBControlExtender '带事件声明声明之后您就可
以在代码窗口的左上角的对象下拉框中发现该对象出现了,也就是说,该对象有了事件
或方法了,它的事件有DragDrop,DragOver ,LostFocus ,GotFocus ,ObjectEvent
和Validate,其中ObjectEvent是通用的事件捕捉。
Private Sub LoadControl()
Set oControl = Controls.Add
("VB. CommandButton", "MyButton")
oControl.Visible = True
End Sub
Private Sub oControl_ObjectEvent(Info As EventInfo)
Select Case Info.Name
Case "Click" 'Click事件
'您可以添加处理Click事件代码
MsgBox "您按了MyButton!"
Case Else ' 其他事件
' Handle unknown events here.
End Select
End Sub
---- 当然对微软提供的标准控件能采用该方法添加,大家都不会怀疑,但自己开发的
控件也能吗?答案是肯定的,我们可以用一个实际的例子进行说明。
声明事件只需用
private event 事件名称(参数表)
在通用部分声明
引用这个词不太恰当,应该说是触发
在需要触发的地方用
raiseevent 事件名称(参数表)就可以了
在VB.Net当中,事件的"关联"是需要明显标志的,不像vb6当中,声明一个过程就是事件执行过程了
Handles用来静态"关联"一个或多个事件到一个过程
"关联"时,过程的签名必须与事件的签名相同(签名的意义请查看相关文档)
在VB.Net当中,事件也是一个对象(VB.Net当中一切皆为对象)
使用Handles时实际就相当于创建了一个对委托的实现(委托的意义请查看相关文档)
可以简单的认为,当事件被触发时,被Handles"关联"了的那些过程代码将被执行
而且,被"关联"的过程可以任意起名,不需要与事件和对象的名称相对应
上述代码如果去掉Handles 及其后面的内容,它将是一个最普通不过的过程,与其它过程没有两样,也不会有任何事件被触发时去执行这段代码,正因为加入了Handles 及其后面的一堆事件,它才会因事件被触发而被执行
说得再简单一点: 当PictureBox1.DoubleClick, PictureBox4.DoubleClick, PictureBox3.DoubleClick,PictureBox2.DoubleClick当中的任何一个事件被触发时,上述这个过程的代码都将被执行
再说说参数: sender表示触发了此事件的对象,在这里就是PictureBox1/PictureBox2/PictureBox3/PictureBox4当中的某一个,利用它能知道到底是哪个对象触发了此事件,e在这里没有用处,利用不到什么,之所以有它,是因为Object/EventArgs是.Net事件的基本签名方式,它的好处在你以后对.Net深入之后能体会到.
这些参数的值都是通过被触发的事件传递过来的,可以简单的认为[事件调用了此过程并为参数赋了值]
在代码的开头:
用WithEvents声明类,比如 Private WithEvents 变量名 As New 类名
用Handles邦定事件,比如Private Sub 过程名() Handles 变量.事件名
最后引发事件就相当于执行定义好的一个绑定过程