12.并以下面代码替换Form.cs 中由系统产生的InitializeComponent过程。< br>
private void InitializeCompon ent ( )
{
this.button1 = new System.Windows.Forms.Butt on ( ) ;
this.button2 = new System.Windows.Forms.Button ( ) ;
this.textBox1 = new Sy stem.Windows.Forms.TextBox ( ) ;
this.textBox2 = new Syst em.Windows.Forms.TextBox ( ) ;
this.label1 = new System.W indows.Forms.Label ( ) ;
th is.label2 = new System.Windows .Forms.Label ( ) ;
this.lab el3 = new System.Windows.Forms .Label ( ) ;
this.textBox3 = new System.Windows.Forms.Tex tBox ( ) ;
this.SuspendLayo ut ( ) ;
this.button1.FlatS tyle = System.Windows.Forms.Fl atStyle.Flat ;
this.button1 .Location = new System.Drawing .Point ( 128 , 128 ) ;
this .button1.Name = "
button1& quot;
;
this.button1.Size = new System.Drawing.Size ( 112 , 40 ) ;
this.button1.TabI ndex = 0 ;
this.button1.Tex t = "
获取"
;
this.b utton1.Click += new System.Eve ntHandler ( this.button1_Click ) ;
this.button2.FlatStyle = System.Windows.Forms.FlatSt yle.Flat ;
this.button2.Loc ation = new System.Drawing.Poi nt ( 128 , 184 ) ;
this.but ton2.Name = "
button2" ;
;
this.button2.Size = new System.Drawing.Size ( 112 , 4 0 ) ;
this.button2.TabIndex = 1 ;
this.button2.Text = "
对时"
;
this.butto n2.Click += new System.EventHa ndler ( this.button2_Click ) ;
this.textBox1.Location = n ew System.Drawing.Point ( 120 , 56 ) ;
this.textBox1.Name = "
textBox1"
;
t his.textBox1.Size = new System .Drawing.Size ( 200 , 21 ) ;
this.textBox1.TabIndex = 2 ;
this.textBox1.Text = " ;
"
;
this.textBox2.Loc ation = new System.Drawing.Poi nt ( 120 , 88 ) ;
this.text Box2.Name = "
textBox2&quo t;
;
this.textBox2.Size = n ew System.Drawing.Size ( 200 , 21 ) ;
this.textBox2.TabIn dex = 3 ;
this.textBox2.Tex t = "
"
;
this.lab el1.Location = new System.Draw ing.Point ( 48 , 56 ) ;
thi s.label1.Name = "
label1&q uot;
;
this.label1.TabIndex = 4 ;
this.label1.Text = & quot;
本地时间:"
;
this.lab el2.Location = new System.Draw ing.Point ( 40 , 88 ) ;
thi s.label2.Name = "
label2&q uot;
;
this.label2.Size = n ew System.Drawing.Size ( 88 , 24 ) ;
this.label2.TabIndex = 5 ;
this.label2.Text = & quot;
服务器时间:"
;
this.la bel3.Location = new System.Dra wing.Point ( 16 , 24 ) ;
th is.label3.Name = "
label3& quot;
;
this.label3.Size = new System.Drawing.Size ( 112 , 23 ) ;
this.label3.TabInd ex = 6 ;
this.label3.Text = "
设定服务器地址:"
;
thi s.textBox3.Location = new Syst em.Drawing.Point ( 120 , 24 ) ;
this.textBox3.Name = &quo t;
textBox3"
;
this.tex tBox3.Size = new System.Drawin g.Size ( 200 , 21 ) ;
this. textBox3.TabIndex = 7 ;
thi s.textBox3.Text = "
"
;
this.AutoScaleBaseSize = new System.Drawing.Size ( 6 , 14 ) ;
this.ClientSize = n ew System.Drawing.Size ( 352 , 245 ) ;
this.Controls.AddR ange ( new System.Windows.Form s.Control[] {
this.textB ox3 ,
this.textBox2 ,
this.textBox1 ,
this .button2 ,
this.button1 ,
this.label1 ,
th is.label2 ,
this.label3} ) ;
this.MaximizeBox = fal se ;
this.Name = "
Form 1"
;
this.Text = " ;
UDP对时客户端"
;
this.Resu meLayout ( false ) ;
}
至此【UDP对时客 户端】项目的界面设计和程序功能实现的前期工作就基本完成了,其 设计界面如图03所示:
图03:【U DP对时客户端】项目的设计界面
13.在Form1.c s中的InitializeComponent过程之后,添加下 列代码,下列代码的功能是在程序中导入WinAPI函数——Se tSystemTime,这个函数位于文件Kernel32.d ll。程序就是通过此函数来更正系统时间的。
< br>
[ DllImport ( "
Kernel32.dll"
)]
private static extern bo ol SetSystemTime ( SystemTime time ) ;
//引入API函数
14.并把它添加到在导入 WinAPI函数代码之后,再添加下列代码,下列代码是定义“s tart_client”过程。此过程的功能是向服务器端传送对 时请求,并获取从服务器端反馈来的时间日期数据。
{
cli ent = new UdpClient ( port ) ;
IPAddress a = IPAddress.P arse ( "
127001"
) ;
receivePoint = new IPEndP oint ( a , port ) ;
IPAdd ress HostIP ;
bool continu eLoop = true ;
while ( con tinueLoop )
{
string h ostName = Dns.GetHostName ( ) ;
System.Text.ASCIIEncodin g encode
= new S ystem.Text.ASCIIEncoding ( ) ;
//定义发送到服务器端的请求信息
//请求 信息是一个字符串,为客户端名称和接收服务器反馈信息的端口号组 成的字符串
string sendString = hostName + "
/"
+ por t.ToString ( ) ;
byte[] se ndData = encode.GetBytes ( sen dString ) ;
//判断使用者输入的是IP地 址还是计算机名称
try
{
Ho stIP = IPAddress.Parse ( text Box3.Text ) ;
}
catch< br> {
//如果输入的是计算机名称,则按照执行 下列代码。
//发送请求信息
clien t.Send ( sendData , sendData.< br> Length , textBox3.Text , 8080 ) ;
//接收来自服务器端的信息
byte[] re cData =
client.Receive ( ref receivePoint ) ;
timeStri ng = encode.GetString ( recDat a ) ;
client.Close ( ) ;
< br> continueLoop=false ;
< br> return ;
}
//输入的是 IP地址,则执行下列代码
IPEndPoint ho st = new IPEndPoint ( HostIP , 8080 ) ;
//发送请求信息
clie nt.Send ( sendData , sendData. Length , host ) ;
//接收来自服务 器端的信息
byte[] recData1 = cl ient.Receive ( ref receivePoin t ) ;
//获取服务器端的时间和日期
t imeString = encode.GetString ( recData1 ) ;
client.Close ( ) ;
//退出循环
continue Loop=false ;
}
}
如果“start _client”过程正确调用,就把服务器端的时间和日期保存到 timeString字符串中了。
17.用下列代码替换 Form1.cs中button1的“Click”事件的处理代 码。下列代码的功能是调用“start_client”过程,获 取并显示服务器端程序的时间和日期信息。
private void button1_Click ( object sender , System.EventArgs e )
{
start_client ( ) ;
textB ox1.Text = DateTime.Now.ToStri ng ( ) ;
//显示客户端当前时间和日期
textBox2.Text = timeString ;
//显示服务器当前时间和日期
}
18.用下列代码替换 Form1.cs中button2的“Click”事件对应的处 理代码。下列代码的功能是根据获取的服务器时间和日期数据来更正 客户端时间和日期。
< br> private void button2_Cl ick ( object sender , System.E ventArgs e )
{
start_cl ient ( ) ;
//把接收来的数据转换时间日期 格式
try
{
temp = D ateTime.Parse ( timeString ) ;
}
catch
{
M essageBox.Show ( "
错误时间&q uot;
) ;
return ;
} //根据得到的时间日期,来定义时间、日期
Sy stemTime st= new SystemTime ( ) ;
st.year= ( short )tem p.Year ;
st.Month= ( short )temp.Month ;
st.DayOfWee k= ( short )temp.DayOfWeek ;
st.Day= ( short )temp.Day ;
st.Hour=Convert.ToInt16 ( temp.Hour ) ;
if ( st.Hou r>
=12 )
{
st.Hour- = ( short )8 ;
}
else if ( st.Hour >
= 8 )
{ st.Hour-= ( short )8 ;
}
else
{
st.Hour += ( short )16 ;
}
st. Minute=Convert.ToInt16 ( temp. Minute ) ;
st.Second=Conve rt.ToInt16 ( temp.Second ) ;
st.Milliseconds=Convert.ToI nt16 ( temp.Millisecond ) ;
//修改本地端的时间和日期
if ( SetSy stemTime ( st ) )
{
Me ssageBox.Show ( DateTime.Now.T oString ( ) ,"
修改成功"
) ;
}
else
Messag eBox.Show ( "
不成功!"
, "
不成功"
) ;
}
至此,在正确完成上述 步骤,全部保存后,【网络对时客户端】项目的全部工作就完成了。
六.运行基于UDP协议网络对时系统,实现网络对时:< br>首先要确认确认网络对时系统中的服务器端程序已经运行和其 IP地址或主机名。然后在客户机上运行网络对时系统中的客户端程 序,在正确输入运行网络对时系统服务器端程序对应的主机名或者I P地址后,单击客户端程序中【获取】按钮,则在程序的文本框中显 示服务器当前时间和日期和客户端当前的时间和日期。若发现二种存 在差异,单击【对时】按钮,则将以服务器当前时间和日期来修正客 户机的时间和日期。修改成功则弹出【修改成功】提示框,反之则弹 出【不成功】提示框,图04是【UDP对时客户端】项目根据服务 器端当前时间和日期信息成功更改本地时间和日期后的界面:
图04:【UDP对时客户端】项目的运行界面
七.总结:
本文详细介绍了UDP协议,.Net Fr ameWork SDK提供给Visual C#用以操作UDP 协议的主要类库,以及通过一个具体而使用的示例——实现一个网络 对时系统,介绍在Visual C#实现UDP协议的具体方法和 过程。UDP由于其自身的缺点注定在某些领域无法利用它,但在可 以利用它的领域,UDP以其快捷、简单、实用的特点正在受到更多 程序员的欢迎。尤其在现代,网络运行态势越来越好的情况下,可以 预见的是UDP在网络中的应用情景将更广阔。希望本文的内容对您 掌握用Visual C#编写基于UDP的网络应用程序有所帮助 。