[唠叨两句]窗体间传值及其同步更新显示
时间:2010-10-15 来源:誓言
今天唠叨两句一个特别经典的话题:“窗体间传值 及 同步更新两个窗体间的数据”,作为菜鸟无论是知识、技术、还是能力都有限,说的不好、望大家莫笑。
我们老师在给我们讲课时惯用的一个套路就是:以实例由简到繁、由易到难,将知识点及其用法贯穿于始终。今天我也献丑试一试,嘿嘿… 见笑、见笑!
窗体简单设计如下: 父窗体 :Form1 包含两个控件:TextBox类型控件,Name属性 txt1; Button类型控件, Name属性 btn1; 子窗体 :Form2 包含两个控件:TextBox类型控件,Name属性 txt2; Button类型控件, Name属性 btn2; 默认启动父窗体 Form1
|
好了、有了上面的两个窗体之后就可以,真正的实验就可以开始啦!
第一步目标:单击btn1时,显示Form2 窗体 并将Form1 窗体中txt1的文本值 赋值于 Form2窗体的 txt2控件。
|
|
【先多唠叨两句、简单的思考一下:】 |
其实这个过程就是将父窗体的一个数据传到子窗体中、然后在控件中显示出来,即属于“父传子”。
而类于类之间进行数据传递(或者说是窗体与窗体之间、窗体的本质就是类),无非是借助字段(公有的)、属性、构造函数、索引、方法、委托、事件完成的,当然还有可能是其他的方式、不过我想本质上还应该是借助了如上所说的方式。
|
|
字段、在我看来它是一个全局变量,习惯上使用private 关键字进行修饰,它在类实例化时(即执行new的时候)被初始化并赋值,此后可在类内部的任意位置访问该字段。 |
属性: |
属性呢,它 等效于 两个特殊的方法,这两个个特殊方法分别满足如下条件(以string类型为例):
当执行set 访问器的时候、它等效于 一个 只有一个string 类型的参数(这个参数是匿名的用Value关键字代替)并且 返回值为void 类型的 方法。
【注意:】 1、属性可以是任何类型的、当然 void 类型除外。
2、属性的get 和 set访问器 可有可无,但必须有其中一个。 |
构造函数: |
构造函数也可以称为特殊的方法,其特殊性在于返回值的特殊、构造函数的没有显示的表名其返回值,但却有硬性的定义了其返回值为其所在类的类型、或者是 所在的结构的类型(因为在结构中存在默认的无参构造函数、在结构中不可以显示的声明无参构造函数、但可对其进行重载)。
构造函数会在使用new 关键字实例化 实例的同时隐式的调用。 |
索引: |
由于他们可以都有get和 set 访问器的缘故,索引也可以看作是两个特殊的方法,这一点与属性很相似。在这一点上还有一点不同的就是 索引显示的定义了一个形参,并且形参的类型可以与返回值的类型可以不相同,而属性则其参数与返回值的类型是相同的。 并且,在访问方式上 索引也不同于属于、字段,字段和属性是通过"."运算符进行访问、而索引是通过"[]"运算符进行访问。 |
方法: |
方法这个东东太深了、涵盖面也太广了、面向对象语言的三大特征 继承、封装、多态 样样都离不开方法,好多东东还未能理解、在此不便多说。 |
委托: |
委托使用 delegate关键字进行定义,它和结构、类一样也是一种类型,都可以作为类的成员变量去使用。
依我的个人的理解、委托就是对特定方法签名的方法的引用,当执行委托时、委托会依次调用执行该委托所指向的方法(我这里说“依次”、是因为一个委托实例可以同时指向多个特定方法签名的方法、称之为多播委托,这需要使用 =、 +=、 -= 运算符的配合使用)。
委托、委托、委托,顾名思义就是委派别人,托付别人做某事,也就是说实现细节交给别人、别的方法。
说的再形象一点就是:委托就是一个公司的老板,它所指向的方法就是这个公司的员工,例如下列情况、老板发话了“十天后、项目交工,赶紧把他们弄完!”,这时老板这个“委托”发生了,并且员工们(委托指向的方法)也开始加班加点的工作,等项目做完后交工。如果这个委托是同步执行的,等十天、或者员工们做完项目交工后 该委托执行完毕;但是如果委托是异步执行,当老板说完话之后,委托就执行完毕了。 |
事件: |
事件 与 委托很相似,它使用Event关键字进行定义,并且也可以作为类的成员变量去使用。 在用法上它只允许使用+= 和 -= 运算符、而不可以使用 = ,而+= 、-= 的右边都是委托实例,也就是说当事件被触发时、它会调用相应的委托去执行相应的操作。
对于事件也可以这样理解:一个软件公司的业务人员拉来一单生意,当业务人员告诉老板说 生意来了、这是老板就会通知某个项目经理“这个项目、你来负责!”,由此看来事件也是委托、是一种特殊的委托,或者称委托是事件执行过程中需要的一部分。 |
|
|
唉,不知不觉的说了这么多废话了、赶紧步入正题。
刚刚也说过了、这个传递过程是一个“父传子”的过程,我优先使用了构造函数、至于原因和争执、我想也是必然也有的,出于个人喜好、我选择了构造函数,至于代码嘛、也简单、如下:
目标一 |
单击btn1时,显示Form2 窗体 并将Form1 窗体中txt1的文本值 赋值于 Form2窗体的 txt2控件的Text属性。 |
Form1 |
代码 public partial class Form1 : Form
|
Form2
|
代码 public partial class Form2 : Form
|
嘿嘿、挺简单、目标完成。
目标二、单击btn2 将Form2 窗体中txt2控件的文本值赋值于Form1窗体的txt1控件的Text属性
【简单的思考一下:放心吧、这次不会有太多废话哦】
这个过程就是 “子传父” 的过程,要想在子窗体里访问父窗体的某一个成员变量、肯定需要在子窗体里得到父窗体的一个实例,然后通过实例 的 "." 运算符 调用某一个成员变量。 但是 txt1是private的呀,咋办? 改成public的? 不太好!还是用属性将txt1的 Text 属性单独公开 吧!好啦,看代码。
目标二 |
单击btn2 将Form2 窗体中txt2控件的文本值赋值于Form1窗体的txt1控件的Text属性 |
Form1 |
代码
|
Form2 |
代码 public partial class Form2 : Form
|
当写完上面的代码后、暗自发笑、嘿嘿,目标完成。
突然间 鼠标单击了一下Form1窗体的btn1按钮,咿? 咋又出来一个窗体呢? 嘿嘿、差点忘了… 后面的不说了、Repair bug 让Form1 中的 数据可以不断的传递到 Form2中,至于方法嘛、简单,仿照Form1、在Form2中 公开一个属性用来访问Form2中的txt2的Text属性,然后将实例化Form2 的代码放在 Form1 的 Load 事件里即可。
小节: |
窗体间数据传递: “父传子”借 “构造”;“子传父” 访 “属性”;当然它们不是惟一的选择、而是这样的选择很方便、代码量相对较少,用构造函数传递有一点需要注意、因为构造函数在它在一个实例的生命周期中只被隐式的调用一次,所以它只能向子窗体中传递一次数据,如果是传递多次建议使用属性、更甚至是方法。 |
反过来再想一想,这只是两个窗体间进行数据传递,要是三个、四个窗体甚至更多的窗体间进行数据传递,怎办呢?
我个人认为一个不错的方法,那就是 属性 + 事件,大致思路如下:
定义一个数据类,类里面有一个私有字段、一个公有属性、一个公有事件,在属性的set访问器里触发事件,然后在需要获取数据进行数据同步的地方 侦听该事件即可。一旦事件发生、在事件的处理方法里更改相应的UI显示就可以啦。
目标三 |
使用属性+ 事件的方式实现数据同步 |
DataClass |
代码 /// <summary>
|
Form1 |
代码 public partial class Form1 : Form
|
Form2 |
代码 public partial class Form2 : Form
|
其实呢,对于数据同步在.NET下还有更简单的一种处理方式,那就是“数据绑定”,并且在.NET下的大部分可视化控件都是支持数据绑定的,至于数据绑定的更多东东 请参见:
http://www.cnblogs.com/08shiyan/archive/2010/08/13/1798652.html
http://www.cnblogs.com/08shiyan/archive/2010/08/12/1797748.html
作者:誓言
博客:http://www.cnblogs.com/08shiyan
别人写的东西无论是好还是差、至少是一番心血,如有友情传播及转载请标明出处 http://www.cnblogs.com/08shiyan,谢谢。