1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52 1namespace FileStreamRead
2{
3 class Program
4 {
5 static void Main(string[] args)
6 {
7 FileStream fs;
8 //获得文件所在路径
9 string filePath = "C:\\file1.txt";
10
11 //打开文件
12 try
13 {
14 fs = new FileStream(filePath, FileMode.Open);
15 }
16 catch(Exception)
17 {
18 throw;
19 }
20
21 //尚未读取的文件内容长度
22 long left = fs.Length;
23 //存储读取结果
24 byte[] bytes = new byte[100];
25 //每次读取长度
26 int maxLength = bytes.Length;
27 //读取位置
28 int start = 0;
29 //实际返回结果长度
30 int num = 0;
31 //当文件未读取长度大于0时,不断进行读取
32 while (left > 0)
33 {
34 fs.Position = start;
35 num = 0;
36 if (left < maxLength)
37 num = fs.Read(bytes, 0, Convert.ToInt32(left));
38 else
39 num = fs.Read(bytes, 0, maxLength);
40 if (num == 0)
41 break;
42 start += num;
43 left -= num;
44 Console.WriteLine(Encoding.UTF8.GetString(bytes));
45 }
46 Console.WriteLine("end of file");
47 Console.ReadLine();
48 fs.Close();
49 }
50 }
51}
52
View Code
C#文件列表操作四大重点
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105 1C#文件列表要点1:上传文件
2 HTML部分:
31. 〈 formid=\"form1\"runat=\"
42. server\"method=\"post\"enctype=\
53. "multipart/form-data\"〉
64. 〈 inputid=\"FileUpLoad\"type=\"
75. file\"runat=\"server\"/〉〈 br/〉
86. 后台CS部分按钮事件
97. //stringstrFileFullName=
108. System.IO.Path.GetFileName(this.
119. FileUpLoad.PostedFile.FileName);
1210. //this.FileUpLoad.PostedFile.SaveAs(Server.MapPath(
1311. \"./Xmlzip/\")+strFileFullName);
14 C#文件列表要点2.文件下载
151. ListBox的SelectedIndexChanged事件设
162. 定相关下载连接
173. protectedvoidlst_DownLoadFileList
184. _SelectedIndexChanged(objectsender,EventArgse)
195. {
206. try
217. {
228. stringstrJS=\"window.open(\'Xmlzip/\";
239. strJS+=this.lst_DownLoadFileList.
2410. SelectedItem.Text.Trim();
2511. strJS+=\"\');returnfalse;\";
2612. this.imgbtn_DownLoadFile.Attributes.
2713. Add(\"onclick\",strJS);
2814. }
2915. catch(Exceptionex)
3016. {
3117. ex.ToString();
3218. }
3319. }
3420. 或者也可以通过改变Label的Text值来实现点击
3521. 后实现文件下载的超级连接
3622. this.Label1.Text=\"〈 ahref=
3723. \\\"Xmlzip/a.rar\\\"〉a.rar〈 /a〉\"
38 C#文件列表要点3.文件删除
391. stringstrFilePath=Server.MapPath(
402. \"../CountryFlowMgr/Xmlzip/\"+this.lst_
413. DownLoadFileList.SelectedItem.Text.Trim());
424. if(File.Exists(strFilePath))
435. {
446. File.Delete(strFilePath);
457. if(File.Exists(strFilePath))
468. {
479. Response.Write(\"ok\");
4810. }
4911. else
5012. {
5113. Response.Write(\"ok\");
5214. }
5315. }
54 C#文件列表要点4.得到文件夹下的文件列表
551. #region得到当前可用的文件列表
562. ///〈 summary〉
573. ///得到当前可用的文件列表
584. ///〈 /summary〉
595. ///〈 paramname=\"IsAlert\"〉
606. 是否需要弹出提示信息〈 /param〉
617. privatevoidfn_getCurrFileList(boolIsAlert)
628. {
639. try
6410. {
6511. //查找Xmlzip文件夹下属于其本
6612. 身UnitCoding的相关zip文件
6713. stringstrXmlZipDirectory=
6814. Server.MapPath(\"../Xmlzip/\");
6915. if(Directory.Exists(strXmlZipDirectory))
7016. {
7117. //DirectoryInfodi=newDirectoryInfo(
7218. Environment.CurrentDirectory);
7319. DirectoryInfodi=newDirectoryInfo(
7420. strXmlZipDirectory);
7521.
7622. FileInfo[]FI=di.GetFiles(\"*.zip\"
7723. );//只查.zip文件
7824. if(FI.Length〉0)
7925. {
8026. lst_DownLoadFileList.Items.Clear();
8127. foreach(FileInfotmpFIinFI)
8228. {
8329. ListItemtmpItem=newListItem();
8430. tmpItem.Text=tmpFI.Name;
8531. lst_DownLoadFileList.Items.Add(tmpItem);
8632. }
8733. lst_DownLoadFileList.SelectedIndex=0;
8834. }
8935. else
9036. {
9137. if(IsAlert)
9238. {
9339. Response.write(\"查无可以下载的文件!\");
9440. }
9541. }
9642. }
9743. }
9844. catch(Exceptionex)
9945. {
10046. ex.ToString();
10147. }
10248. }
10349. #endregion
104
105
View Code
Color TabControl(C#)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101 1using System;
2using System.Collections.Generic;
3using System.ComponentModel;
4using System.Drawing;
5using System.Data;
6using System.Text;
7using System.Windows.Forms;
8using System.Drawing.Drawing2D;
9using System.Drawing.Imaging;
10namespace wgscd
11{
12 public partial class myTabControl : TabControl
13 {
14 public myTabControl()
15 {
16 InitializeComponent();
17 this.DrawMode = TabDrawMode.OwnerDrawFixed;//必须
18 SetStyle(ControlStyles.DoubleBuffer | ControlStyles.OptimizedDoubleBuffer | ControlStyles.AllPaintingInWmPaint, true);//避免闪烁
19 UpdateStyles();
20 }
21 protected Color HeaderBackColor1 = Color.DarkGreen;
22 protected Color HeaderBackColor2 = Color.DarkKhaki;
23 protected float headerbackangle = 45;
24 protected Color titlebackcolor1 = Color.Bisque;
25 protected Color titlebackcolor2 = Color.Blue;
26 protected float titlebackangle = 45;
27 protected Font headerfont = new Font("Arial", 12, FontStyle.Bold);
28 protected StringAlignment titlealignment = StringAlignment.Center;
29 protected Color headerfontcolor = Color.Plum;
30 protected Font focusedheaderfont = new Font("Arial", 11, FontStyle.Regular);
31 protected Color focusedheaderfontcolor = Color.PowderBlue;
32 Rectangle r = new Rectangle(1, 1, 200, 200);
33
34 protected override void OnPaint(PaintEventArgs e)//绘制整个TabControl控件背景不起作用。。。。。。。。。。。。
35 {
36 r = new Rectangle(0, 0, this.Width, this.Height);
37 Brush b = new SolidBrush(Color.Azure);
38 Graphics g = e.Graphics;
39 g.FillRectangle(b, r);
40 // base.OnPaint(e);
41
42 }
43
44 protected override void OnDrawItem(DrawItemEventArgs e)
45 {
46
47 Graphics g = e.Graphics;
48 Rectangle endPageRect = GetTabRect(TabPages.Count - 1); //最后一个标题栏的范围
49 Rectangle TitleRect = GetTabRect(e.Index); //当前标题栏的范围
50 Rectangle HeaderBackRect = Rectangle.Empty; //背景区域
51 switch (Alignment)
52 {
53 case TabAlignment.Top:
54 HeaderBackRect = new Rectangle(new Point(endPageRect.X + endPageRect.Width, endPageRect.Y),
55 new Size(Width - endPageRect.X - endPageRect.Width, endPageRect.Height));
56 break;
57 case TabAlignment.Bottom:
58 HeaderBackRect = new Rectangle(new Point(endPageRect.X + endPageRect.Width, endPageRect.Y),
59 new Size(Width - endPageRect.X - endPageRect.Width, endPageRect.Height));
60 break;
61 case TabAlignment.Left:
62 HeaderBackRect = new Rectangle(new Point(endPageRect.X, endPageRect.Y + endPageRect.Height),
63 new Size(endPageRect.Width, Height - endPageRect.Y - endPageRect.Height));
64 break;
65 case TabAlignment.Right:
66 HeaderBackRect = new Rectangle(new Point(endPageRect.X, endPageRect.Y + endPageRect.Height),
67 new Size(endPageRect.Width, Height - endPageRect.Y - endPageRect.Height));
68 break;
69 }
70
71 Brush TitleBackBrush = new LinearGradientBrush(TitleRect, titlebackcolor1, titlebackcolor2, titlebackangle); //渐变角度
72 Font font = headerfont;
73 StringFormat sf = new StringFormat();
74 sf.Alignment = titlealignment;
75 sf.LineAlignment = StringAlignment.Center;
76 Color fontcolor = headerfontcolor;
77
78 if (SelectedIndex == e.Index) //如果绘制的标题就是选中的标题,则使用选中标题的字体,同时更新font和fontcolor
79 {
80 g.DrawRectangle(new Pen(TabPages[e.Index].BackColor), TitleRect); //消除选中标题的矩形方框
81 font = focusedheaderfont;
82 fontcolor = focusedheaderfontcolor;
83 }
84 Brush fontbrush = new SolidBrush(fontcolor);
85 //绘制标题文本
86 g.DrawString(TabPages[e.Index].Text, font, fontbrush, TitleRect, sf);
87 //绘制背景
88 if (HeaderBackRect != Rectangle.Empty)
89 {
90 Brush HeaderBackBrush = new LinearGradientBrush(HeaderBackRect, HeaderBackColor1, HeaderBackColor2, headerbackangle);
91 g.FillRectangle(HeaderBackBrush, HeaderBackRect);
92 }
93
94 // base.OnDrawItem(e);
95 }
96
97
98 }
99}
100
101
View Code
C#词法分析程序
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501 1namespace 词法分析
2{
3 /// <summary>
4 /// Form1 的摘要说明。
5 /// </summary>
6 public class Form1 : System.Windows.Forms.Form
7 {
8 private System.Windows.Forms.Label label1;
9
10 private System.Windows.Forms.Button button1;
11 private System.Windows.Forms.Button button2;
12 private System.Windows.Forms.Button button3;
13
14 private System.Windows.Forms.RichTextBox richTextBox1;
15 private System.Windows.Forms.RichTextBox richTextBox2;
16
17 private System.Windows.Forms.OpenFileDialog openFileDialog1;
18 private System.Windows.Forms.SaveFileDialog saveFileDialog1;
19
20 /// <summary>
21 /// 必需的设计器变量。
22 /// </summary>
23 private System.ComponentModel.Container components = null;
24
25 public Form1()
26 {
27 //
28 // Windows 窗体设计器支持所必需的
29 //
30 InitializeComponent();
31
32 //
33 // TODO: 在 InitializeComponent 调用后添加任何构造函数代码
34 //
35 }
36
37 /// <summary>
38 /// 清理所有正在使用的资源。
39 /// </summary>
40 protected override void Dispose(bool disposing)
41 {
42 if (disposing)
43 {
44 if (components != null)
45 {
46 components.Dispose();
47 }
48 }
49 base.Dispose(disposing);
50 }
51
52 #region Windows 窗体设计器生成的代码
53 /// <summary>
54 /// 设计器支持所需的方法 - 不要使用代码编辑器修改
55 /// 此方法的内容。
56 /// </summary>
57 private void InitializeComponent()
58 {
59 this.label1 = new System.Windows.Forms.Label();
60 this.button1 = new System.Windows.Forms.Button();
61 this.richTextBox1 = new System.Windows.Forms.RichTextBox();
62 this.button2 = new System.Windows.Forms.Button();
63 this.richTextBox2 = new System.Windows.Forms.RichTextBox();
64 this.openFileDialog1 = new System.Windows.Forms.OpenFileDialog();
65 this.saveFileDialog1 = new System.Windows.Forms.SaveFileDialog();
66 this.button3 = new System.Windows.Forms.Button();
67 this.SuspendLayout();
68 //
69 // label1
70 //
71 this.label1.Location = new System.Drawing.Point(8, 8);
72 this.label1.Name = "label1";
73 this.label1.Size = new System.Drawing.Size(72, 24);
74 this.label1.TabIndex = 0;
75 this.label1.Text = "词法分析";
76 //
77 // button1
78 //
79 this.button1.Location = new System.Drawing.Point(240, 8);
80 this.button1.Name = "button1";
81 this.button1.Size = new System.Drawing.Size(64, 23);
82 this.button1.TabIndex = 1;
83 this.button1.Text = "分析";
84 this.button1.Click += new System.EventHandler(this.button1_Click);
85 //
86 // richTextBox1
87 //
88 this.richTextBox1.Location = new System.Drawing.Point(24, 48);
89 this.richTextBox1.Name = "richTextBox1";
90 this.richTextBox1.Size = new System.Drawing.Size(240, 352);
91 this.richTextBox1.TabIndex = 2;
92 this.richTextBox1.Text = "";
93 // this.richTextBox1.TextChanged += new System.EventHandler(this.richTextBox1_TextChanged);
94 //
95 // button2
96 //
97 this.button2.Location = new System.Drawing.Point(96, 8);
98 this.button2.Name = "button2";
99 this.button2.Size = new System.Drawing.Size(64, 23);
100 this.button2.TabIndex = 3;
101 this.button2.Text = "读入";
102 this.button2.Click += new System.EventHandler(this.button2_Click);
103 //
104 // richTextBox2
105 //
106 this.richTextBox2.Location = new System.Drawing.Point(280, 48);
107 this.richTextBox2.Name = "richTextBox2";
108 this.richTextBox2.Size = new System.Drawing.Size(280, 352);
109 this.richTextBox2.TabIndex = 4;
110 this.richTextBox2.Text = "";
111 //
112 // button3
113 //
114 this.button3.Location = new System.Drawing.Point(384, 8);
115 this.button3.Name = "button3";
116 this.button3.Size = new System.Drawing.Size(56, 23);
117 this.button3.TabIndex = 5;
118 this.button3.Text = "保存";
119 this.button3.Click += new System.EventHandler(this.button3_Click);
120 //
121 // Form1
122 //
123 this.AutoScaleBaseSize = new System.Drawing.Size(6, 14);
124 this.ClientSize = new System.Drawing.Size(584, 430);
125 this.Controls.Add(this.button3);
126 this.Controls.Add(this.richTextBox2);
127 this.Controls.Add(this.button2);
128 this.Controls.Add(this.richTextBox1);
129 this.Controls.Add(this.button1);
130 this.Controls.Add(this.label1);
131 this.MaximizeBox = false;
132 this.Name = "Form1";
133 this.Text = "Form1";
134 // this.Load += new System.EventHandler(this.Form1_Load);
135 this.ResumeLayout(false);
136
137 }
138 #endregion
139
140 /// <summary>
141 /// 应用程序的主入口点。
142 /// </summary>
143 [STAThread]
144 static void Main()
145 {
146 Application.Run(new Form1());
147 }
148 /// <summary>
149 /// 词法分析函数
150 /// </summary>
151 /// <param name="sender"></param>
152 /// <param name="e"></param>
153 private void button1_Click(object sender, System.EventArgs e)
154 {
155 //得到想要的字符数组。
156 char[] getch = textToCharArray();
157
158 //将字符数组,转换为词法分析后的 单词数组。
159 string[] stringArray = charArrayToStringArray(getch);
160
161 //将单词数组分类,用数字标出各个单词所在的类别。
162 string[,] twoStringArray = stringArrayToTwoStringArray(stringArray);
163
164 //用于输出二维数组。
165 printString(twoStringArray);
166
167 }
168 /// <summary>
169 /// 输出结果 即用于输出二维数组。
170 /// </summary>
171 /// <param name="twoStringArray"></param>
172 private void printString(string[,] twoStringArray)
173 {
174 //提示说明
175 this.richTextBox2.Text = "1 -> 保留字" + "\r\n" +
176 "2 -> 运算符" + "\r\n" +
177 "3 -> 分隔符" + "\r\n" +
178 "4 -> 数字 " + "\r\n" +
179 "5 -> 其它" + "\r\n";
180 //输出二维数组中的数据
181 for (int x = 0; x < twoStringArray.Length / 2; x++)
182 {
183 for (int y = 0; y < 2; y++)
184 {
185 this.richTextBox2.Text = this.richTextBox2.Text + twoStringArray[y, x] + " ";
186 if (y == 1)
187 {
188 this.richTextBox2.Text = this.richTextBox2.Text + "\r\n";
189 }
190 }
191 }
192 }
193
194 /// <summary>
195 /// 打开方件
196 /// </summary>
197 /// <param name="sender"></param>
198 /// <param name="e"></param>
199 private void button2_Click(object sender, System.EventArgs e)// 文件打开的方法。
200 {
201 openFileDialog1.Filter = "文本文件(*.txt)|*.txt";
202 openFileDialog1.Title = "打开要分析的源文件。";
203
204 if (openFileDialog1.ShowDialog() == DialogResult.OK)
205 {
206 System.IO.StreamReader sr = new
207 System.IO.StreamReader(openFileDialog1.FileName);
208 this.richTextBox1.Text = sr.ReadToEnd();
209 sr.Close();
210 }
211 }
212 /// <summary>
213 /// 保存文件
214 /// </summary>
215 /// <param name="sender"></param>
216 /// <param name="e"></param>
217 private void button3_Click(object sender, System.EventArgs e)
218 {
219 saveFileDialog1.Filter = "文本文件(*.txt)|*.txt";
220 saveFileDialog1.Title = "保存分析结果.";
221 if(saveFileDialog1.ShowDialog() == DialogResult.OK)
222 {
223 System.IO.StreamWriter wr = new System.IO.StreamWriter(saveFileDialog1.FileName);
224 wr.Write(this.richTextBox2.Text);
225 wr.Close();
226 }
227 }
228
229
230 /// <summary>
231 /// 引用二维数组和单词的标志j
232 /// </summary>
233 /// <param name="twoArray"></param>
234 /// <param name="j"></param>
235 private void oneArrayToTwo(ref string[,] twoArray, ref int j)
236 {
237
238 string[,] tempArray = twoArray;
239 twoArray = new string[2, j + 2];
240 for (int x = 0; x < 2; x++)
241 {
242 for (int y = 0; y < j + 1; y++)
243 {
244 twoArray[x, y] = tempArray[x, y];
245 }
246 }
247 j = j + 1;
248 }
249 /// <summary>
250 /// 引用单词数组,和要加入单词数组的单词
251 /// </summary>
252 /// <param name="stringArrange"></param>
253 /// <param name="st"></param>
254 private void stringToArrayString(ref string[] stringArrange, string st)
255 {
256
257 if (stringArrange[0] == "")
258 {
259 stringArrange[0] = st;
260 }
261 else
262 {
263 string[] oldA = stringArrange;//刚得到的字符串
264 int i = oldA.Length + 1;
265 stringArrange = new string[i];//申请一个长一个的字符数组。
266 oldA.CopyTo(stringArrange, 0);//将先前的字符数组考到现在这个数组中。
267 stringArrange[stringArrange.Length - 1] = st;
268 }
269 }
270 /// <summary>
271 /// 将Text中的字符串,存入一个字符数组中。
272 /// </summary>
273 /// <returns></returns>
274 private char[] textToCharArray()
275 {
276 string stringTemp;
277 stringTemp = this.richTextBox1.Text;
278 char[] getch = stringTemp.ToCharArray();//要处理的字符都在getch这个数组中。
279 return getch;
280 }
281 /// <summary>
282 /// 字符数组 到 单词数组
283 /// </summary>
284 /// <param name="getch"></param>
285 /// <returns></returns>
286 private string[] charArrayToStringArray(char[] getch)//将字符数组转换为字符串数组。即词法分析后的单词数组。
287 {
288 string[] stringArrange ={ "" };//用这个字符串数组存放词法分析后得到的单词。
289 char charTemp;
290 string stringSave = "";// 存放一个分析得到的单词
291
292 //一次循环因得到一个单词。
293 for (int i = 0; i < getch.Length; i++)
294 {
295 charTemp = getch[i];
296
297 //由字母开头 数字和字母组成的单词。
298 if (charTemp >= 'a' &&
299 charTemp <= 'z'
300 ||
301 charTemp >= 'A' &&
302 charTemp <= 'Z')
303 {
304 stringSave = charTemp.ToString();
305 i = i + 1;
306 int test = 0;//判断循环是否结束,1 为结束。
307 while (test == 0)
308 {
309 charTemp = getch[i];
310 if (charTemp >= 'a' &&
311 charTemp <= 'z'
312 ||
313 charTemp >= 'A' &&
314 charTemp <= 'Z'
315 ||
316 charTemp >= '0' &&
317 charTemp <= '9')
318 {
319 stringSave = stringSave + charTemp.ToString();
320 i = i + 1;
321 }
322 else
323 test = 1;
324 }
325 stringToArrayString(ref stringArrange, stringSave);
326 }
327 stringSave = "";
328 //由数字组成的单词。
329 if (charTemp >= '0' &&
330 charTemp <= '9')
331 {
332 stringSave = stringSave + charTemp.ToString();
333 i = i + 1;
334 int test1 = 0;
335 while (test1 == 0)
336 {
337 charTemp = getch[i];
338 if (charTemp >= '0' &&
339 charTemp <= '9')
340 {
341 stringSave = stringSave + charTemp.ToString();
342 i = i + 1;
343 }
344 else
345 test1 = 1;
346 }
347 stringToArrayString(ref stringArrange, stringSave);
348 }
349 stringSave = "";
350 //由运算符组成的单词。
351 if (charTemp == '+'
352 || charTemp == '-'
353 || charTemp == '*'
354 || charTemp == '/'
355 || charTemp == '='
356 || charTemp == '<'
357 || charTemp == '>'
358 || charTemp == '!')
359 {
360 stringSave = stringSave + charTemp.ToString();
361 i = i + 1;
362 int test2 = 0;
363 while (test2 == 0)
364 {
365 charTemp = getch[i];
366 if (charTemp == '+'
367 || charTemp == '-'
368 || charTemp == '*'
369 || charTemp == '/'
370 || charTemp == '='
371 || charTemp == '<'
372 || charTemp == '>'
373 || charTemp == '!')
374 {
375 stringSave = stringSave + charTemp.ToString();
376 i = i + 1;
377 }
378 else
379 test2 = 1;
380 }
381 stringToArrayString(ref stringArrange, stringSave);
382 }
383 stringSave = "";
384 //由介符组成的单词。
385 if (charTemp == '('
386 || charTemp == ')'
387 || charTemp == '{'
388 || charTemp == '}'
389 || charTemp == '['
390 || charTemp == ']'
391 || charTemp == ','
392 || charTemp == ':'
393 || charTemp == ';'
394 || charTemp == '"'
395 || charTemp == '\''
396 || charTemp == '\\')
397 {
398 stringSave = stringSave + charTemp.ToString();
399 stringToArrayString(ref stringArrange, stringSave);
400 }
401 }
402 return stringArrange;
403 }
404 /// <summary>
405 /// 单词数组 到 二维单词数组。
406 /// </summary>
407 /// <param name="stringArray"></param>
408 /// <returns></returns>
409 private string[,] stringArrayToTwoStringArray(string[] stringArray)
410 {
411 //存放单词标识后的结果。
412 string[,] twoArray = new string[2, 1];
413 //单词的标志
414 int j = 0;
415
416
417 //每循环一次,把一个单词归于一类,即前面加上一个数字。
418 for (int i = 0; i < stringArray.Length; i++)
419 {
420 //保留字 1
421 if (stringArray[i] == "main"
422 || stringArray[i] == "int"
423 || stringArray[i] == "float"
424 || stringArray[i] == "printf"
425 || stringArray[i] == "if"
426 || stringArray[i] == "for"
427 || stringArray[i] == "while"
428 || stringArray[i] == "do"
429 || stringArray[i] == "return"
430 || stringArray[i] == "break"
431 || stringArray[i] == "continue")
432 {
433 twoArray[0, j] =
434
435 "1";
436 twoArray[1, j] = stringArray[i];
437 this.oneArrayToTwo(ref twoArray, ref j);
438 }
439 //运算符 2
440 else
441 if (stringArray[i] == "+"
442 || stringArray[i] == "-"
443 || stringArray[i] == "*"
444 || stringArray[i] == "/"
445 || stringArray[i] == ">"
446 || stringArray[i] == "<"
447 || stringArray[i] == ">="
448 || stringArray[i] == "<="
449 || stringArray[i] == "!="
450 || stringArray[i] == "=="
451 || stringArray[i] == "++"
452 || stringArray[i] == "--"
453 || stringArray[i] == "=")
454 {
455 twoArray[0, j] = "2";
456 twoArray[1, j] = stringArray[i];
457 this.oneArrayToTwo(ref twoArray, ref j);
458 }
459 //分隔符 3
460 else
461 if (stringArray[i] == "("
462 || stringArray[i] == ")"
463 || stringArray[i] == "{"
464 || stringArray[i] == "}"
465 || stringArray[i] == "["
466 || stringArray[i] == "]"
467 || stringArray[i] == ","
468 || stringArray[i] == ";"
469 || stringArray[i] == ":"
470 || stringArray[i] == "\""
471 || stringArray[i] == "/*"
472 || stringArray[i] == "*/")
473 {
474 twoArray[0, j] = "3";
475 twoArray[1, j] = stringArray[i];
476 this.oneArrayToTwo(ref twoArray, ref j);
477 }
478 //数字 4
479 else
480 if (stringArray[i].ToCharArray()[0] >= '0' &&
481 stringArray[i].ToCharArray()[0] <= '9')
482 {
483 twoArray[0, j] = "4";//数字
484 twoArray[1, j] = stringArray[i];
485 this.oneArrayToTwo(ref twoArray, ref j);
486 }
487 //其它 5(变量等)
488 else
489 {
490 twoArray[0, j] = "5";
491 twoArray[1, j] = stringArray[i];
492 this.oneArrayToTwo(ref twoArray, ref j);
493 }
494 }
495 return twoArray;
496 }
497
498
499 }
500}
501
View Code
IMAP文件夹名称编码和解码方法
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81 1// 编码
2private string IMAPEncode(string folder)
3{
4 string rtn = "", base64;
5 int index = 0;
6 Regex regAsis = new Regex(@"\G(?:[\x20-\x25\x27-\x7e])+");
7 Regex reg26 = new Regex(@"\G&");
8 Regex regEncode = new Regex(@"\G(?:[^\x20-\x7e])+");
9 Regex regEq = new Regex(@"=+$");
10 Regex regSlash = new Regex(@"\/");
11 while (index < folder.Length) {
12 Match m;
13 m = regAsis.Match(folder, index);
14 if(m.Success)
15 {
16 index = index + m.Length;
17 rtn = rtn + m.Value;
18 continue;
19 }
20 m = reg26.Match(folder, index);
21 if(m.Success)
22 {
23 index = index + m.Length;
24 rtn = rtn + "&-";
25 continue;
26 }
27 m = regEncode.Match(folder, index);
28 if(m.Success)
29 {
30 index = index + m.Length;
31 base64 = Convert.ToBase64String(Encoding.GetEncoding("UTF-16BE").GetBytes(m.Value));
32 base64 = regEq.Replace(base64, "");
33 base64 = regSlash.Replace(base64, ",");
34 rtn = rtn + "&" + base64 + "-";
35 continue;
36 }
37 }
38 return rtn;
39}
40
41// 解码
42private string IMAPDeconde(string folder)
43{
44 string rtn = "", base64;
45 int index = 0;
46 Regex regAsis = new Regex(@"\G([^&]+)");
47 Regex reg26 = new Regex(@"\G\&-");
48 Regex regDecode = new Regex(@"\G\&([A-Za-z0-9+,]+)-?");
49 Regex regComma = new Regex(@",");
50 while (index < folder.Length) {
51 Match m;
52 m = regAsis.Match(folder, index);
53 if(m.Success)
54 {
55 index = index + m.Length;
56 rtn = rtn + m.Value;
57 continue;
58 }
59 m = reg26.Match(folder, index);
60 if(m.Success)
61 {
62 index = index + m.Length;
63 rtn = rtn + "&";
64 continue;
65 }
66 m = regDecode.Match(folder, index);
67 if(m.Success)
68 {
69 index = index + m.Length;
70 base64 = m.Value.Substring(1, m.Value.Length - 2);
71 base64 = regComma.Replace(base64, "/");
72 int mod = base64.Length % 4;
73 if(mod > 0 ) base64 = base64.PadRight(base64.Length + (4 - mod), '=');
74 base64 = Encoding.GetEncoding("UTF-16BE").GetString(Convert.FromBase64String(base64));
75 rtn = rtn + base64;
76 continue;
77 }
78 }
79 return rtn;
80}
81
View Code
MFC选项卡的实现
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235 1方案一
2 在对话框上放置一个Tab Control的控件,再在对话框上放置所需的控件(本例放置了2个按钮,试图在每个标签中显示一个)。然后利用Class Wizard来为Tab Control控件创建一个控件变量,该变量是CTabCtrl类的,再为其他控件也创建相应的控件类。 在主对话框的初始函数中CProperty1Dlg::OnInitDialog()加入如下代码:
3 //本例插入两个标签,实际运用中可通过循环插入所需个数的标签,运行后默认第一个标签被选中
4 m_tab.InsertItem( 0, _T("Tab1") );
5 m_tab.InsertItem( 1, _T("Tab2") );
6 //将不是第一个标签的控件隐藏掉,只留下你要的控件
7 m_button2.ShowWindow( SW_HIDE );
8 再利用ClassWizard处理Tab Control的 TCN_SELCHANGE 的消息。在消息处理函数中,利用CWnd::ShowWindow来使相应的控件显示和隐藏。
9 void CProperty1Dlg::OnSelchangeTab1(NMHDR* pNMHDR, LRESULT* pResult)
10 {
11 //GetCurSel返回当前被选中的标签的索引号(以0为基础算起)
12 int sel = m_tab.GetCurSel();
13 switch(sel)
14 {
15 case 0:
16 m_button1.ShowWindow( SW_SHOW );
17 m_button2.ShowWindow( SW_HIDE );
18 break;
19 case 1:
20 m_button2.ShowWindow( SW_SHOW );
21 m_button1.ShowWindow( SW_HIDE );
22 break;
23 }
24 *pResult = 0;
25 }
26 方案二
27 本这个方案中,我将使用MFC中现成的CPropertySheet和CPropertyPage类来完成将控件分散到各个对话框类中。
28 首先加入两个(或数个)对话框资源。修改各对话框资源的属性,将对话框的Caption属性改为你要在标签上所显示的文字。将对话框的Style属性改为:Child, Border属性改为:Thin, 只选中Title Bar复选框,去掉其他复选框。然后你可以在这些对话框中加入要分开显示的各个控件。
29 为上述对话框资源分别制作一个对话框类,该对话框类是从CPropertyPage继承。这样一来各子对话框类就好了,主对话框类可以直接使用CPropertySheet类。使用如下代码即可:
30 CPropertySheet sheet("属性页对话框");
31 CPage1 page1;
32 CPage2 page2;
33 //加入子对话框作为一个属性页
34 sheet.AddPage(&page1);
35 sheet.AddPage(&page2);
36 //产生一个模态对话框,也可以使用Create方法来产生一个非模态对话框(具体参见MSDN)
37 sheet.DoModal();
38 如何在主对话框中放置其他控件呢?如果直接使用CPropertySheet的话,是不可以的,但是别忘了我们可以从CPropertySheet类继承自己的类啊!
39 方案三
40 首先还是要创建那些要在属性页中的显示的子对话框类,创建步骤和方案二一样,都是从CPropertyPage继承。
41 这次我们将从CPropertySheet类继承自己的类(假设类名为CMySheet)。我们要在这里放上一个button控件。那么现在先在CMySheet中加入一个CButton类的成员变量m_button。
42 在CMySheet类中的OnInitDialog()函数里,这样写:
43 BOOL bResult = CPropertySheet::OnInitDialog();
44 //取得属性页的大小
45 CRect rectWnd;
46 GetWindowRect(rectWnd);
47 //调整对话框的宽度
48 SetWindowPos(NULL, 0, 0,rectWnd.Width() + 100,rectWnd.Height(),SWP_NOMOVE | SWP_NOZORDER | SWP_NOACTIVATE);
49 CRect rectButton(rectWnd.Width() + 25, 25,rectWnd.Width()+75, 75);
50 //用程序创建一个按钮
51 m_button.Create("Button", BS_PUSHBUTTON, CRect(rectWnd.Width(), 25,rectWnd.Width()+75, 50) , this, 1);
52 //显示这个按钮
53 m_button.ShowWindow( SW_SHOW );
54 CenterWindow();
55 return bResult;
56 使用方案三虽然能在主对话框中加入控件,但是也比较麻烦,首先所加的控件只能在属性页的右边或下边。并且用程序来产生控件比较烦琐,位置与大小不易控制。那么还有其他方法,既能在对话框中加入属性页,又能在主对话框随意添加控件?
57 方案四
58 不从CPropertySheet继承自己的类,还是直接使用它。各属性页的子对话框类还是需要的,创建方法和上述两个方案相同。
59 首先我们新建一个基于对话框的工程。在编辑已有的一个主对话框中可以自由加一些所需的控件,但是得留出一定的空间用于放置属性页。
60 在主对话框类里加入一个CPropertySheet类的一个成员变量(m_sheet)代表整个属性页。再加入一些各子对话框类的实例作为成员变量(m_page1、m_page2……)。
61 在主对话框类的OnInitDialog()函数中加入:
62 //加入标签,标签名由各个子对话框的标题栏决定
63 m_sheet.AddPage(&m_page1);
64 m_sheet.AddPage(&m_page2);
65 //用Create来创建一个属性页
66 m_sheet.Create(this, WS_CHILD | WS_VISIBLE, WS_EX_CONTROLPARENT);
67 RECT rect;
68 m_sheet.GetWindowRect(&rect);
69 int width = rect.right - rect.left;
70 int height = rect.bottom - rect.top;
71 //调整属性页的大小和位置
72 m_sheet.SetWindowPos(NULL, 20, 50, 0, 0, SWP_NOSIZE | SWP_NOZORDER | SWP_NOACTIVATE);
73 这个方案可以自由在主对话框中加一些必要的控件,而且属性页中的控件也都分散在了各个子对话框类中,使用非常方便。
74
75方案五
76 使用Tab Control,并且从CTabCtrl控件类继承自己的类(CTabSheet)来处理。
77 首先我先介绍一下如何使用CTabSheet。
78 先要制作子对话框类,这次的子对话框类不要从CPropertyPage继承,而是直接从CDialog继承。并且各个子对话框资源的属性应设置为:Style为Child, Border为None。
79 在主对话框资源中,加入一个Tab Control,并且适当调整位置和大小。利用ClassWizard来为这个Tab Control创建一个CTabSheet的控件变量。
80 在主对话框的OnInitDialog()加入:
81 m_sheet.AddPage("tab1", &m_page1, IDD_DIALOG1);
82 m_sheet.AddPage("tab2", &m_page2, IDD_DIALOG2);
83 m_sheet.Show();
84 就这样就可以在对话框上制作出一个完美的属性页了。效果和上图完全一样。
85 下面我就来讲讲CTabSheet类的细节内容。
86 CTabSheet是从CTabCtrl继承来的,用于Tab Control的控件类。在类中有一个成员变量用来记录各子对话框的指针CDialog* m_pPages[MAXPAGE]; MAXPAGE是该类所能加载的标签的最大值。
87 类中有一个AddPage方法,用于记录子对话框的指针和所使用对话框资源的ID号。
88 BOOL CTabSheet::AddPage(LPCTSTR title, CDialog *pDialog,UINT ID)
89 {
90 if( MAXPAGE == m_nNumOfPages )
91 return FALSE;
92 //保存目前总的子对话框数
93 m_nNumOfPages++;
94 //记录子对话框的指针、资源ID、要在标签上显示的文字
95 m_pPages[m_nNumOfPages-1] = pDialog;
96 m_IDD[m_nNumOfPages-1] = ID;
97 m_Title[m_nNumOfPages-1] = title;
98 return TRUE;
99 }
100 在使用AddPage加入了若干子对话框后,必须调用CTabSheet的Show方法来真正生成标签和子对话框。
101 void CTabSheet::Show()
102 {
103 //利用CDialog::Create来创建子对话框,并且使用CTabCtrl::InsertItem来加上相应的标签
104 for( int i=0; i < m_nNumOfPages; i++ )
105 {
106 m_pPages[i]->Create( m_IDD[i], this );
107 InsertItem( i, m_Title[i] );
108 }
109 //由于对话框显示时默认的是第一个标签被选中,所以应该让第一个子对话框显示,其他子对话框隐藏
110 m_pPages[0]->ShowWindow(SW_SHOW);
111 for( i=1; i < m_nNumOfPages; i++)
112 m_pPages[i]->ShowWindow(SW_HIDE);
113 SetRect();
114 }
115 生成好标签和子对话框后,调用CTabSheet::SetRect来计算并调整属性页的大小。
116 void CTabSheet::SetRect()
117 {
118 CRect tabRect, itemRect;
119 int nX, nY, nXc, nYc;
120 //得到Tab Control的大小
121 GetClientRect(&tabRect);
122 GetItemRect(0, &itemRect);
123 //计算出各子对话框的相对于Tab Control的位置和大小
124 nX=itemRect.left;
125 nY=itemRect.bottom+1;
126 nXc=tabRect.right-itemRect.left-2;
127 nYc=tabRect.bottom-nY-2;
128 //利用计算出的数据对各子对话框进行调整
129 m_pPages[0]->SetWindowPos(&wndTop, nX, nY, nXc, nYc, SWP_SHOWWINDOW);
130 for( int nCount=1; nCount < m_nNumOfPages; nCount++ )
131 m_pPages[nCount]->SetWindowPos(&wndTop, nX, nY, nXc, nYc, SWP_HIDEWINDOW);
132 }
133 在单击标签栏后,应该是相应的子对话框显示,正在显示的子对话框应该隐藏。因此利用ClassWizard来处理WM_LBUTTONDOWN消息。
134 void CTabSheet::OnLButtonDown(UINT nFlags, CPoint point)
135 {
136 CTabCtrl::OnLButtonDown(nFlags, point);
137 //判断是否单击了其他标签
138 if(m_nCurrentPage != GetCurFocus())
139 {
140 //将原先的子对话框隐藏
141 m_pPages[m_nCurrentPage]->ShowWindow(SW_HIDE);
142 m_nCurrentPage=GetCurFocus();
143 //显示当前标签所对应的子对话框
144 m_pPages[m_nCurrentPage]->ShowWindow(SW_SHOW);
145 }
146 }
147 这样利用CTabSheet这个类就可以轻松地在对话框上放置自己的属性页了,并且控件都分散在各子对话框类中,符合对象封装的思想。而且用这个方法来制作属性页就可以利用ClassWizard来轻松地生成消息映射处理Tab Control的消息了。例如:可以处理TCN_SELCHANGE消息来对切换了标签时进行一些动作。
148
149方案五另一写法
150 思路:当我们调用InsertItem()这个函数的时候,选项卡控件将会添加一个标签页,这个时候,我们将自己的对话框的窗体的指针与此标签页关联起来,当用户进行标签页的切换的时候,我们根据当前是哪个标签页,显示哪个对话框,不是与当前标签页关联的对话框,我们将其隐藏即可.这样我们便可以实现选项卡控件.
151 第一步:新建一个自己的类CTabSheet继承CTabCtrl.
152 第二步:定义有用的成员变量
153 CDialog* m_dlgWnd[MAXTABPAGE]; //这个是存放对话框指针的指针数组
154 int m_curTabNumber; //记录当前用户添加了几个标签页
155 int m_selTabID; //当前用户点击的标签页的ID
156 第三步:添加成员函数
157 //通过这个函数,可以将一个对话框指针与添加的标签页关联起来,insWnd是创建的非模式对话框的指针,wndID是对话框的ID,pageText是标签页的标题
158 void CreateTabPage(CWnd *insWnd, int wndID,CString pageText)
159 //添加控件的点击事件的处理,当点击后得到当前点击的标签页的ID,然后将与此标签页相关的对话框显示,其它的隐藏即可
160 void OnLButtonDown(UINT nFlags, CPoint point)
161 通过添加以上的成员变量及成员函数即可实现一个简单的选项卡控件的用法
162 下面我将这两个成员函数的代码贴出来,并详细讲解
163 //创建并且增加一个标签页
164 //创建并且增加一个标签页
165 void CTabSheet::CreateTabPage(CWnd *insWnd, int wndID,CString pageText)
166 {
167 if (m_curTabNumber >= MAXTABPAGE)
168 {
169 MessageBox("标签页己经达到最大!","创建出错!",MB_OK);
170 return;
171 }
172 //首先new一个对话框的指针,但是不要调用create函数,再将些指针当成参数传进来即可,创建己由此函数做完
173 if (NULL == insWnd)
174 {
175 MessageBox("标签页为空","创建出错",MB_OK);
176 return;
177 }
178 //创建对话框,并且增加标签页
179 CDialog* curDlg = (CDialog*)insWnd;
180 curDlg->Create(wndID,this);
181 int suc = InsertItem(m_curTabNumber,pageText);
182 if (-1 == suc)
183 {
184 MessageBox("插入标签页失败","失败",MB_OK);
185 return;
186 }
187 curDlg->ShowWindow(SW_SHOW);
188 //将这个对应的窗体指针存放起来
189 m_dlgWnd[m_curTabNumber] = curDlg;
190 //此时选择当前页面
191 SetCurSel(m_curTabNumber);
192 m_selTabID = m_curTabNumber;
193 m_curTabNumber ++;
194 }
195 //点击左键事件,处理
196 void CTabSheet::OnLButtonDown(UINT nFlags, CPoint point)
197 {
198 // TODO: Add your message handler code here and/or call default
199 CTabCtrl::OnLButtonDown(nFlags, point);
200 //得到当前用户点击的标签页的ID
201 int curSelect = GetCurSel();
202 //得到当前标签页的位置以便设置对话框显示的位置
203 CRect curRect;
204 GetClientRect(curRect);
205 if (-1 == curSelect)
206 {
207 return;
208 }
209 //查找标签页,将与当前用户点击的标签页相关的对话框显示出来,其它的对话框隐藏
210 for (int i = 0; i < m_curTabNumber; i ++)
211 {
212 if (i == curSelect)
213 {
214 m_dlgWnd[i]->SetWindowPos(NULL,0,20,curRect.Width(),curRect.bottom,SWP_SHOWWINDOW);
215 }
216 else
217 {
218 m_dlgWnd[i]->SetWindowPos(NULL,0,20,curRect.Width(),curRect.bottom,SWP_HIDEWINDOW);
219 }
220 }
221 m_selTabID = curSelect;
222 Invalidate();
223 //CTabCtrl::OnLButtonDown(nFlags, point);
224 }
225 以上为关键的两个函数,下面介绍调用的方法
226 创建非模式的对话框
227 CTabSheet m_tabSheet;
228 CMyDlg* m_dlg = new CMyDlg;
229 m_tabSheet.CreateTabPage(m_dlg ,IDD_DLG_ID,"第一个标签页");
230 这样就可以产生一个标签页了,当然还可以继续调用此函数添加标签页
231 本文根据网上的资料整理,以下是用方案五写的一个实例程序。
232
233来自:http://c.chinaitlab.com/vc/838702.html
234
235
View Code
Net下几种日志管理方法
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54 1日志是应用程序中不可缺少的一部份,不仅可以记录应用程序的运行状态,还可以记录一些BUG,便于应用程序的更新与修改。
2在.Net有好几种方法可以对日志进行管理。
31、数据库日志。
42、文本日志。
53、系统事件日志。
6首先,对于数据库日志而言,它的使用简单而且方便。这里就不做太多的讨论,相信写过与数据相关的项目的人都会用数据来记录一些日志。然而它唯一不好的就是:必须先保证你的数据库链接是正确无误的。
7然而这一保证不是必然的,所以这里我再讨论一下其它的两种情况,文本日志及系统事件日志。
8文本日志:
9它使用简单,而且查看也方便。不好的就是不便于做大量的日志,而且日志内容的查看与分析都不方便。然而它还是可在在一些不适合数据库日志的地方使用。例如一些测试消息的输出,一些独立组件的少量日志等。
10一般情况下,为了方便管理,以天为单位对日志文件进行分类。这样一来也可以简单的对文件进行管理。例如:你的文件名可以知道这个日志是什么时候的,然后可以简单的做一个类似数据库一样的查询,管理也还方便。毕竟文本对系统来说是如此的简单。
11.Net有一个诊断类,可以把文本以监听的方式添加到Trace以及Debug上,这样一来,你的所有指向Trace和Degug的输出都会记录到文件里去。这是一个很不错的方法。
12using System.Diagnostics;
13Debug.Listeners.Add(new System.Diagnostics.TextWriterTraceListener(DateTime.Now.ToString("yyyyMMdd")+"..log"));
14Debug.Listeners.Add(new System.Diagnostics.TextWriterTraceListener(Console.Out));
15或者:
16Trace.Listeners.Add(new System.Diagnostics.TextWriterTraceListener(DateTime.Now.ToString("yyyyMMdd")+"..log"));
17Trace.Listeners.Add(new System.Diagnostics.TextWriterTraceListener(Console.Out));
18这里的区别是:Trace在Release下可以使用,而Debug只在Debug下使用。
19我觉得所有的文本日志中,上面的方法是最好用的。你只须要再做一个日志管理的类就行了。
20当然,还要注意,就是监听在24小时后要更新一次,应该把当前的监听清理掉,然后重新添加一个。这也简单。
21另一个方法就是自己写文本进行管理。这样的方法要略麻烦一点点,道也不难。
22然而文本日志除了不便于做大量日志的工作以还,还有一个致命的问题:进程冲突!
23因为文本日志要锁定正在写的文本文件,所以其它要写该文件的程序会出现错误。一般情况下,如果应该程序只有一个副本在运行,而且把日志做为一个全局的静态对象来处理,也不会有什么太大的问题。但程序的第二个副本会因为文件不能打开而启动失败。
24这并不是一个无法解决的问题,只用保证程序有一个副本就行了。如果不保证的话,那么小有一点复杂,这里就不再讨论了,下次有机会再讨论这个问题。
25对于上面的问题,我想暂时放弃文本日志,用系统的事件日志来处理。
26系统事件日志:
27.net下有一个EventLog类,它直接与系统的事件日志关联。
28简单的一个:
29EventLog.WriteEntry("LogSource","This is a test log.");
30就可以往系统里写一个事件了。
31然而把它用好也还有点点麻烦。首先是上面的方法会在系统的Application下写一个事件日志,而且为默认为Information类型。这样很不利于管理,大家可以在管理工具里看一下日志,就会发现大量的日志,自己写的一个小日志简直无法找到。
32然而.Net为我们提供了几个方法来更好的管理日志。
331、添加一个新的LogSource。
34什么是LogSource?其实简单的说,它就是日志的一个分类标记,例如你可以用程序一次取出所以LogSource为指定内容的日志。这样一来,只要你记得这个Source名,你就可以读取和分类管理日志了。
35默认情况下,你在直接用EventLog的静态函数写日志的时候,要指定一个LogSource,如果LogSource不存在,那么它就自动在Application下建立一个,因此,创建LogSource就这么简单了。
362、添加一个新的Log.
37什么是Log.这里的Log是指系统事件日志里的大日志分类,一般情况下,系统有Application,System和Sercuity三个日志,每个下面有不同的Soucce,这样就构成了日志系统。
38你不能独立的创建一个Log,因为.NET里没有提供任何方法来创建一个Log,只能通过函数:CreateEventSource(string,string)
39来创建一个Sourcce,此时如果你这样做:CreateEventSource("MySource","MyLog");
40你就会在日志管理器里看到多了一个MyLog类,然而再这样写日志:
41EventLog.WriteEntry("MySource","This is a test log.");
42就可以写一条记录到MyLog分类下,这样就可以很好的管理自己的日志了。
43需要说明的是:
44如果Source已经存在,那么创建会失败。注意:不管Source的哪个Log下,只要Source的名字已经存在,那么你的创建都会失败。例如:如果有一个"Source1"的日志在Application里,那么你就不能再到其它Log里再创建一个名为"Source1"的日志了。另外:你用程序创建的日志不能在日志管理器里删除它(Messages可以删除,但日志分类不能删除)。方法是你还是用程序可以来删除,或者在注册表里来删除它。它的位置:[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Eventlog\]
45看一下注册表,或许你会明白一些。
46最后就是用日志实例对象来写日志。你可以指定一个Log名和一个Source名来写日志,但要注意,必须是Log与Source匹配,否则也会出现错误。这比直接用静态方法来写日志要复杂一点点,但你有更多的自由空间。
47系统事件日志不好的地方就是日志只保存三个月,而且不好管理。如果你可以直接管理服务器,或者就在本机上运行应该会好一些,否则你就不得不自己写些代码来管理日志了。当然,如果一些重要的日志,可以导出到其它文件中。
48它的好处是很多的:
491、不必与数据库链接,效率会高一些,也不会有数据库访问失败的问题。
502、不会有进程冲突问题,它是系统的日志,不管是什么应用程序都可以写日志。
513、全局可用,不管在哪里都可以直接写日志,而且可读。因此可以把它当成一个消息通信平台。(当然,可能只有那些大脑有点问题的人会这样做。)然而我只是想说明:A进程写的日志,B进程可以直接读取。
52好了,关于日志这次就总结这些。
53
54
View Code
VC 给Tab控件的标签贴图
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51 1设置TAB标题前的小图标:
2HIMAGELIST hImageList = ImageList_Create(24,24,ILC_COLOR32,0,2);
3HICON himodify = (HICON)LoadImage(NULL,TEXT("res\\Pictures.ico"),IMAGE_ICON,24,24,LR_LOADFROMFILE);
4ImageList_AddIcon(hImageList , himodify);
5TabCtrl_SetImageList(hTabCtrl ,hImageList);
6TCITEM tabitem;
7tabitem.mask = TCIF_TEXT | TCIF_IMAGE ;
8tabitem.pszText = TEXT("1");
9tabitem.iImage = 0;
10TabCtrl_InsertItem(hTabCtrl,0,&tabitem);
11
12或者采用:
13void CFormTabView::OnInitialUpdate()
14 {
15 m_imagelist.Create(16,16,ILC_MASK,4,4);//创建图标
16
17 HICON hIcon;
18 //hIcon = ::LoadIcon(AfxGetResourceHandle(),MAKEINTRESOURCE(IDI_ICON1));
19 hIcon = AfxGetApp()->LoadIcon(IDI_ICON_LEDON);// icon 0
20 m_imagelist.Add(hIcon);
21 hIcon = AfxGetApp()->LoadIcon(IDI_ICON_LEDOFF);//icon 1
22 m_imagelist.Add(hIcon);
23
24 CRect rect;
25 GetClientRect(rect);
26 rect.top += 0;
27 m_ctTab.MoveWindow(rect);
28
29 m_ctTab.SetImageList(&m_TabImageList);
30 m_ctTab.InsertItem(TCIF_TEXT | TCIF_IMAGE,0,"page0",0,0);//选择的是icon 0,倒数第二个参数
31 m_ctTab.InsertItem(TCIF_TEXT | TCIF_IMAGE,1,"page1",1,0);//选择的是icon 1
32 m_ctTab.InsertItem(TCIF_TEXT | TCIF_IMAGE,2,"page2",1,0);//选择的是icon 1
33 m_ctTab.InsertItem(TCIF_TEXT | TCIF_IMAGE,3,"page3",1,0);//选择的是icon 1
34
35 // m_ctTab.HighlightItem(0);
36 // m_ctTab.SetPadding(CSize(3,3));
37 int x;
38 x = (rect.Width()-10)/m_ctTab.GetItemCount();
39 m_ctTab.SetItemSize(CSize(x,20));
40
41 .......
42
43 }
44 m_imagelist 是 view/dialog成员变量CImageList
45 m_ctTab 是 tabctrl控件映射的变量
46
47 用image 的话是一样的,也用cimagelist
48
49参考:http://topic.csdn.net/t/20050415/16/3939802.html
50
51
View Code
WinForms C#:html编辑器工程源码,含直接写WebBrowser的文件流、IPersistStreamInit接口的声明和一些相关的小方法
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331 1首先多谢朋友们的捧场;
2
3今天给大家带来一个操作WebBrowser的一些高级方法,我专门写了一个html编辑器的实现代码,有需要的朋友可以自己扩充;
4功能实现是直接写流到WebBrowser内不通过临时文件,并且支持对WebBrowser的一些高级控制(其实script可以达到的均可达到,想知道怎么搞的可以阅读代码)。
5
6其中关于IPersistStreamInit接口的声明费了翻工夫,因为以前在 delphi 中没这么麻烦,呵呵。在网络上找了大半天没找到,最后还是祭出Reflector,反编译Windows.Forms,需要的朋友可以不用辛苦的自己搞了!
7
8我在这个演示里,制作的html编辑环境是比简单的,您可以看看,比较比较 CodeProject 上的代码;我采用的是ie自身提供的编辑方法,只是这样的方式都被运用于web方式的编辑器内,就好比这个freeTextBox
9
10以下是主要的代码:
11 1
12
13 /********************************
14 2
15
16 * 初始化浏览器状态
17 3
18
19 * 指向about:blank
20 4
21
22 * *****************************/
23 5
24
25 private void Form1_Load(object sender, System.EventArgs e) {
26 6
27
28 object obj = null;
29 7
30
31 this.Show();
32 8
33
34 this.axWb.Navigate("about:blank",ref obj,ref obj,ref obj,ref obj);
35 9
36
37 //等待完成动作
38 10
39
40 while(axWb.ReadyState < SHDocVw.tagREADYSTATE.READYSTATE_INTERACTIVE)
41 11
42
43 Application.DoEvents();
44 12
45
46
47 13
48
49 //初始化html编辑器
50 14
51
52 InitHtmlEditor();
53 15
54
55 }
56 16
57
58
59 17
60
61 /*******************************
62 18
63
64 * 这里是核心方法
65 19
66
67 * 完全调用IE自身的html编辑功能
68 20
69
70 * 可以看到,我采用了一种兼容的
71 21
72
73 * 方式,用Frame(框架),这样
74 22
75
76 * 的话,默认安装的Windows 98都
77 23
78
79 * 支持html编辑功能;
80 24
81
82 * 关键代码如下:
83 25
84
85 * frame.document.designMode = "on";
86 26
87
88 * 表示开启设计模式
89 27
90
91 ******************************/
92 28
93
94 private void InitHtmlEditor(){
95 29
96
97 string sw = "";
98 30
99
100 sw += "<html>\r\n";
101 31
102
103 sw += "<script language=javascript>\r\n";
104 32
105
106 sw += " function loadSet(){\r\n";
107 33
108
109 sw += " var frame=document.getElementById(\"i-frame\").contentWindow;\r\n";
110 34
111
112 sw += " frame.document.designMode = \"on\";\r\n";
113 35
114
115 sw += " frame.document.open();\r\n";
116 36
117
118 sw += " frame.document.write(\"<html><font color=red>hello 大家好啊!<br>我是S.F. <br>";
119 37
120
121 sw += " <a href=\\\"http://www.cnblogs.com/chinasf\\\">欢迎访问我的weblog</a></font></html>\");\r\n";
122 38
123
124 sw += " frame.document.close();\r\n";
125 39
126
127 sw += " }\r\n";
128 40
129
130 sw += " function setBlod(obj){\r\n";
131 41
132
133 sw += " document.getElementById(\"i-frame\").contentWindow.document.execCommand(\"bold\");\r\n";
134 42
135
136 sw += " }\r\n";
137 43
138
139 sw += "</script>\r\n";
140 44
141
142 //这里加入了一个html的button,也就是说,你可以把web模式的html编辑器的代码完全copy进来
143 45
144
145 sw += "<body onload=\"loadSet()\" scroll=\"yes\"><button onclick=\"setBlod(this);\">Blod</button>\r\n";
146 46
147
148 sw += "<iframe id=\"i-frame\" frameBorder=\"1\" width=\"640\" height=\"480\"></iframe>\r\n";
149 47
150
151 sw += "</body></html>\r\n";
152 48
153
154
155 49
156
157 //写入浏览器
158 50
159
160 WriteHtml(sw);
161 51
162
163 }
164 52
165
166
167 53
168
169 private void WriteHtml(string s){
170 54
171
172 //内存流,用于转换string
173 55
174
175 MemoryStream ms = new MemoryStream();
176 56
177
178 try{
179 57
180
181 byte[] htmlcode = System.Text.Encoding.Default.GetBytes(s);
182 58
183
184 ms.Write(htmlcode,0,htmlcode.Length);
185 59
186
187 Stream dataStream = ms;
188 60
189
190 //恢复指针位置
191 61
192
193 dataStream.Seek(0,0);
194 62
195
196
197 63
198
199 if(axWb.Document!=null){
200 64
201
202 //转换接口,并转换为IStream
203 65
204
205 (axWb.Document as UnsafeNativeMethods.IPersistStreamInit).Load(new UnsafeNativeMethods.ComStreamFromDataStream(dataStream));
206 66
207
208 }
209 67
210
211 }finally{
212 68
213
214 ms.Close();
215 69
216
217 }
218 70
219
220 }
221 71
222
223
224 72
225
226 private void button1_Click(object sender, System.EventArgs e) {
227 73
228
229 //获取document,在IHTMLDocument2中取得桢
230 74
231
232 mshtml.IHTMLDocument3 idoc = (mshtml.IHTMLDocument3)axWb.Document;
233 75
234
235 mshtml.IHTMLFrameBase2 fb= (mshtml.IHTMLFrameBase2)idoc.getElementById("i-frame");
236 76
237
238 object obj=null;
239 77
240
241 fb.contentWindow.document.execCommand("bold",true,obj);
242 78
243
244 }
245 79
246
247
248 80
249
250 private void button3_Click(object sender, System.EventArgs e) {
251 81
252
253 //获取document,在IHTMLDocument2中才有body.style
254 82
255
256 mshtml.IHTMLDocument2 idoc = (mshtml.IHTMLDocument2)axWb.Document;
257 83
258
259 //指定为IHTMLStyle3,才可以定制滚动条颜色
260 84
261
262 mshtml.IHTMLStyle3 istyle = (mshtml.IHTMLStyle3)idoc.body.style;
263 85
264
265 istyle.scrollbarArrowColor = "#0099FF";
266 86
267
268 istyle.scrollbar3dLightColor = "#FFFFFF";
269 87
270
271 istyle.scrollbarDarkShadowColor = "#0099FF";
272 88
273
274 istyle.scrollbarFaceColor = "#99CCFF";
275 89
276
277 istyle.scrollbarHighlightColor = "#0099FF";
278 90
279
280 istyle.scrollbarShadowColor = "#0099FF";
281 91
282
283 istyle.scrollbarTrackColor = "#FFFFFF";
284 92
285
286
287 93
288
289 }
290 94
291
292
293 95
294
295 private void button2_Click(object sender, System.EventArgs e) {
296 96
297
298 //查看源码,文本方式
299 97
300
301 mshtml.IHTMLDocument3 idoc = (mshtml.IHTMLDocument3)axWb.Document;
302 98
303
304 mshtml.IHTMLFrameBase2 fb= (mshtml.IHTMLFrameBase2)idoc.getElementById("i-frame");
305 99
306
307 MessageBox.Show(fb.contentWindow.document.body.innerText);
308100
309
310 }
311101
312
313
314102
315
316 private void button4_Click(object sender, System.EventArgs e) {
317103
318
319 //查看源码,HTML方式
320104
321
322 mshtml.IHTMLDocument3 idoc = (mshtml.IHTMLDocument3)axWb.Document;
323105
324
325 mshtml.IHTMLFrameBase2 fb= (mshtml.IHTMLFrameBase2)idoc.getElementById("i-frame");
326106
327
328 MessageBox.Show(fb.contentWindow.document.body.innerHTML);
329}
330
331
View Code
UDP打洞原理及代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822 1UDP"打洞"原理
2
31. NAT分类
4根据Stun协议(RFC3489),NAT大致分为下面四类
51) Full Cone
6这种NAT内部的机器A连接过外网机器C后,NAT会打开一个端口.然后外网的任何发到这个打开的端口的UDP数据报都可以到达A.不管是不是C发过来的.
7例如 A:192.168.8.100 NAT:202.100.100.100 C:292.88.88.88
8A(192.168.8.100:5000) -> NAT(202.100.100.100 : 8000) -> C(292.88.88.88:2000)
9任何发送到 NAT(202.100.100.100:8000)的数据都可以到达A(192.168.8.100:5000)
102) Restricted Cone
11这种NAT内部的机器A连接过外网的机器C后,NAT打开一个端口.然后C可以用任何端口和A通信.其他的外网机器不行.
12例如 A:192.168.8.100 NAT:202.100.100.100 C:292.88.88.88
13A(192.168.8.100:5000) -> NAT(202.100.100.100 : 8000) -> C(292.88.88.88:2000)
14任何从C发送到 NAT(202.100.100.100:8000)的数据都可以到达A(192.168.8.100:5000)
153) Port Restricted Cone
16这种NAT内部的机器A连接过外网的机器C后,NAT打开一个端口.然后C可以用原来的端口和A通信.其他的外网机器不行.
17例如 A:192.168.8.100 NAT:202.100.100.100 C:292.88.88.88
18A(192.168.8.100:5000) -> NAT(202.100.100.100 : 8000) -> C(292.88.88.88:2000)
19C(202.88.88.88:2000)发送到 NAT(202.100.100.100:8000)的数据都可以到达A(192.168.8.100:5000)
20以上三种NAT通称Cone NAT.我们只能用这种NAT进行UDP打洞.
214) Symmetic
22对于这种NAT.连接不同的外部目标.原来NAT打开的端口会变化.而Cone NAT不会.虽然可以用端口猜测.但是成功的概率很小.因此放弃这种NAT的UDP打洞.
232. UDP hole punching
24对于Cone NAT.要采用UDP打洞.需要一个公网机器C来充当”介绍人”.内网的A,B先分别和C通信.打开各自的NAT端口.C这个时候知道A,B的公网IP: Port. 现在A和B想直接连接.比如A给B发.除非B是Full Cone.否则不能通信.反之亦然.但是我们可以这样.
25A要连接B.A给B发一个UDP包.同时.A让那个介绍人给B发一个命令,让B同时给A发一个UDP包.这样双方的NAT都会记录对方的IP,然后就会允许互相通信.
263. 同一个NAT后面的情况
27如果A,B在同一个NAT后面.如果用上面的技术来进行互连.那么如果NAT支持loopback(就是本地到本地的转换),A,B可以连接,但是比较浪费带宽和NAT.有一种办法是,A,B和介绍人通信的时候,同时把自己的local IP也告诉服务器.A,B通信的时候,同时发local ip和公网IP.谁先到就用哪个IP.但是local ip就有可能不知道发到什么地方去了.比如A,B在不同的NAT后面但是他们各自的local ip段一样.A给B的local IP发的UDP就可能发给自己内部网里面的某某某了.
28还有一个办法是服务器来判断A,B是否在一个NAT后面.(网络拓朴不同会不会有问题?)
29
30WellKnown.cs
31
32//WellKnown公用库
33using System;
34using System.IO;
35using System.Runtime.Serialization.Formatters.Binary;
36using System.Net;
37using System.Net.Sockets;
38using System.Collections;
39
40namespace P2PWellKnown
41{
42 /// <summary>
43 /// UDP用户登录事件委托
44 /// </summary>
45 /// <param name="sender">事件源对象</param>
46 /// <param name="e">事件实体</param>
47 public delegate void UdpUserLogInDelegate(object sender, UDPSockEventArgs e);
48
49 /// <summary>
50 /// 一般UDP消息事件委托
51 /// </summary>
52 /// <param name="sender">事件源对象</param>
53 /// <param name="e">事件实体</param>
54 public delegate void UdpMessageDelegate(object sender, UDPSockEventArgs e);
55
56 /// <summary>
57 /// 初始化一个新连接的事件委托
58 /// </summary>
59 /// <param name="sender">事件源对象</param>
60 /// <param name="e">事件实体</param>
61 public delegate void UdpNewConnectDelegate(object sender, UDPSockEventArgs e);
62
63 /// <summary>
64 /// P2P共享数据类
65 /// </summary>
66 public class P2PConsts
67 {
68 /// <summary>
69 /// UDP服务器监听端口
70 /// </summary>
71 public const int UDP_SRV_PORT = 2280;
72
73 /// <summary>
74 ///TCP服务器监听端口
75 /// </summary>
76 public const int TCP_SRV_PORT = 2000;
77 }
78
79
80
81 /// <summary>
82 /// FormatterHelper 序列化,反序列化消息的帮助类
83 /// </summary>
84 public class FormatterHelper
85 {
86
87 public static byte[] Serialize(object obj)
88 {
89 BinaryFormatter binaryF = new BinaryFormatter();
90 MemoryStream ms = new MemoryStream(1024 * 10);
91 binaryF.Serialize(ms, obj);
92 ms.Seek(0, SeekOrigin.Begin);
93 byte[] buffer = new byte[(int)ms.Length];
94 ms.Read(buffer, 0, buffer.Length);
95 ms.Close();
96 return buffer;
97 }
98
99
100
101 public static object Deserialize(byte[] buffer)
102 {
103 BinaryFormatter binaryF = new BinaryFormatter();
104 MemoryStream ms = new MemoryStream(buffer, 0, buffer.Length, false);
105 object obj = binaryF.Deserialize(ms);
106 ms.Close();
107 return obj;
108 }
109
110 }
111
112
113
114 /// <summary>
115 /// 用于承载UDPSock信息的事件类
116 /// </summary>
117 public class UDPSockEventArgs : EventArgs
118 {
119 /// <summary>
120 /// 要承载的消息
121 /// </summary>
122 private string m_strMsg;
123
124 /// <summary>
125 /// 用户信息
126 /// </summary>
127 private string m_strUserName;
128
129
130 /// <summary>
131 /// 触发该事件的公共终端
132 /// </summary>
133 private IPEndPoint m_EndPoint;
134
135
136 /// <summary>
137 /// 初始化UDPSock事件
138 /// </summary>
139 /// <param name="sMsg">用户发送的信息</param>
140 public UDPSockEventArgs(string sMsg)
141 : base()
142 {
143 this.m_strMsg = sMsg;
144 }
145
146 /// <summary>
147 /// 远端用户名
148 /// </summary>
149 public string RemoteUserName
150 {
151 get
152 {
153 return m_strUserName;
154 }
155 set
156 {
157 m_strUserName = value;
158 }
159 }
160
161
162 /// <summary>
163 /// 一般套接字消息
164 /// </summary>
165 public string SockMessage
166 {
167 get
168 {
169 return m_strMsg;
170 }
171 set
172 {
173 m_strMsg = value;
174 }
175 }
176
177
178 /// <summary>
179 /// 公共远端节点
180 /// </summary>
181 public IPEndPoint RemoteEndPoint
182 {
183 get
184 {
185 return m_EndPoint;
186 }
187 set
188 {
189 m_EndPoint = value;
190 }
191 }
192 }
193}
194
195
196
197
198
199
200
201
202
203UDPP2PSock.cs
204
205
206//UDPP2PSock.cs
207using System;
208using System.Collections.Generic;
209using System.Text;
210using System.Net;
211using System.Net.Sockets;
212using System.Threading;
213
214using P2PWellKnown;
215
216namespace UDPP
217{
218 /// <summary>
219 /// UDPP2P套接字管理类
220 /// </summary>
221 public class UDPP2PSock
222 {
223 /// <summary>
224 /// 用户登录事件
225 /// </summary>
226 public event UdpUserLogInDelegate OnUserLogInU;
227
228 /// <summary>
229 /// 一般UDP消息事件
230 /// </summary>
231 public event UdpMessageDelegate OnSockMessageU;
232
233 /// <summary>
234 /// 初始化一个新连接事件
235 /// </summary>
236 public event UdpNewConnectDelegate OnNewConnectU;
237
238 /// <summary>
239 /// UDP服务器
240 /// </summary>
241 private UdpClient m_udpServer;
242
243 /// <summary>
244 /// UDP客户端
245 /// </summary>
246 private UdpClient m_udpClient;
247
248 /// <summary>
249 /// 服务器实际上在本地机器上监听的
250 /// 端口,用于当一台计算机上同时启
251 /// 动两个可两以上服务器进程时,标
252 /// 识不同的服务器进程
253 /// </summary>
254 private int m_iMyServerPort;
255
256 /// <summary>
257 /// 客户端在本地机器上实际使用的端口,
258 /// 用于当一台计算机上同时有两个或两
259 /// 个以上客户端进程在运行时,标识不
260 /// 同的客户端进程
261 /// </summary>
262 private int m_iMyClientPort;
263
264 /// <summary>
265 /// 标识是否已成功创服务器
266 /// </summary>
267 private bool m_bServerCreated;
268
269 /// <summary>
270 /// 标识是否已成功创建客户端
271 /// </summary>
272 private bool m_bClientCreated;
273
274 /// <summary>
275 /// 服务器使用的线程
276 /// </summary>
277 private Thread m_serverThread;
278
279 /// <summary>
280 /// 客户端使用的线程
281 /// </summary>
282 private Thread m_clientThread;
283
284 /// <summary>
285 /// 打洞线程
286 /// </summary>
287 //private Thread m_burrowThread;
288
289 /// <summary>
290 /// 远端节点
291 /// </summary>
292 private IPEndPoint m_remotePoint;
293
294 /// <summary>
295 /// 当前进程作为客户端的公共终端
296 /// </summary>
297 private string m_strMyPublicEndPoint;
298
299 /// <summary>
300 /// 当前进程作为客户端的私有终端
301 /// </summary>
302 private string m_strMyPrivateEndPoint;
303
304 /// <summary>
305 /// 用于接受信息的 StringBuilder实例
306 /// </summary>
307 private StringBuilder m_sbResponse = new StringBuilder();
308
309 /// <summary>
310 /// P2P打洞时标识是否收到回应消息
311 /// </summary>
312 private bool m_bRecvAck = false;
313
314 /// <summary>
315 /// 请求向其方向打洞的私有终端
316 /// </summary>
317 private IPEndPoint m_requestPrivateEndPoint;
318
319 /// <summary>
320 /// 请求向其方向打洞的公共终端
321 /// </summary>
322 private IPEndPoint m_requestPublicEndPoint;
323
324 /// <summary>
325 /// 打洞消息要发向的节点
326 /// </summary>
327 private ToEndPoint m_toEndPoint;
328
329 /// <summary>
330 /// 用于标识是否已经和请求客户端建立点对连接
331 /// </summary>
332 //private bool m_bHasConnected=false ;
333
334 /// <summary>
335 /// 创建服务器或客户端的最大尝试
336 /// 次数,为(65536-60000),防止
337 /// 因不能创建而限入死循环或使用
338 /// 无效端口
339 /// </summary>
340 private const int MAX_CREATE_TRY = 5536;
341
342 /// <summary>
343 /// 打洞时尝试连接的最大尝试次数
344 /// </summary>
345 private const int MAX_CONNECT_TRY = 10;
346
347
348 /// <summary>
349 /// 构造函数,初始化UDPP2P实例
350 /// </summary>
351 public UDPP2PSock()
352 {
353 m_iMyServerPort = P2PConsts.UDP_SRV_PORT;
354 m_iMyClientPort = 60000;
355 m_bClientCreated = false;
356 m_bServerCreated = false;
357 m_toEndPoint = new ToEndPoint();
358 m_serverThread = new Thread(new ThreadStart(RunUDPServer));
359 m_clientThread = new Thread(new ThreadStart(RunUDPClient));
360 //m_burrowThread = new Thread(new ThreadStart(BurrowProc));
361 }
362
363 /// <summary>
364 /// 创建UDP 服务器
365 /// </summary>
366 public void CreateUDPSever()
367 {
368 int iTryNum = 0;
369
370 //开始尝试创建服务器
371 while (!m_bServerCreated && iTryNum < MAX_CREATE_TRY)
372 {
373 try
374 {
375 m_udpServer = new UdpClient(m_iMyServerPort);
376 m_bServerCreated = true;
377 }
378 catch
379 {
380 m_iMyServerPort++;
381 iTryNum++;
382 }
383 }
384
385 //创建失败,抛出异常
386 if (!m_bServerCreated && iTryNum == MAX_CREATE_TRY)
387 {
388 throw new Exception("创建服务器尝试失败!");
389 }
390 m_serverThread.Start();
391
392 }
393
394 /// <summary>
395 /// 创建UDP客户端
396 /// </summary>
397 /// <param name="strServerIP"& gt;服务器IP</param>
398 /// <param name="iServerPort"& gt;服务器端口</param>
399 public void CreateUDPClient(string strServerIP, int iServerPort)
400 {
401 int iTryNum = 0;
402
403 //开始尝试创建服务器
404 while (!m_bClientCreated && iTryNum < MAX_CREATE_TRY)
405 {
406 try
407 {
408 m_udpClient = new UdpClient(m_iMyClientPort);
409 m_bClientCreated = true;
410 string strIPAddress = (System.Net.Dns.GetHostAddresses("localhost")[0]).ToString();
411 m_strMyPrivateEndPoint = strIPAddress + ":" + m_iMyClientPort.ToString();
412 }
413 catch
414 {
415 m_iMyClientPort++;
416 iTryNum++;
417 }
418 }
419
420 //创建失败,抛出异常
421 if (!m_bClientCreated && iTryNum == MAX_CREATE_TRY)
422 {
423 throw new Exception("创建客户端尝试失败!");
424 }
425
426 IPEndPoint hostPoint = new IPEndPoint(IPAddress.Parse(strServerIP), iServerPort);
427 string strLocalIP = (System.Net.Dns.GetHostAddresses("localhost"))[0].ToString();
428 SendLocalPoint(strLocalIP, m_iMyClientPort, hostPoint);
429 m_clientThread.Start();
430 }
431
432
433 /// <summary>
434 /// 运行UDP 服务器
435 /// </summary>
436 private void RunUDPServer()
437 {
438 while (true)
439 {
440 byte[] msgBuffer = m_udpServer.Receive(ref m_remotePoint);
441 m_sbResponse.Append(System.Text.Encoding.Default.GetString(msgBuffer));
442 CheckCommand();
443 Thread.Sleep(10);
444 }
445 }
446
447
448 /// <summary>
449 /// 运行UDP客户端
450 /// </summary>
451 private void RunUDPClient()
452 {
453 while (true)
454 {
455 byte[] msgBuffer = m_udpClient.Receive(ref m_remotePoint);
456 m_sbResponse.Append(System.Text.Encoding.Default.GetString(msgBuffer));
457 CheckCommand();
458 Thread.Sleep(10);
459 }
460 }
461
462
463 /// <summary>
464 /// 销毁UDP 服务器
465 /// </summary>
466 public void DisposeUDPServer()
467 {
468 m_serverThread.Abort();
469 m_udpServer.Close();
470 }
471
472 /// <summary>
473 /// 销毁UDP客房端
474 /// </summary>
475 public void DisposeUDPClient()
476 {
477 m_clientThread.Abort();
478 m_udpClient.Close();
479 }
480
481 /// <summary>
482 /// 发送消息
483 /// </summary>
484 /// <param name="strMsg"& gt;消息内容</param>
485 /// <param name="REP"& gt;接收节点</param>
486 public void SendData(string strMsg, IPEndPoint REP)
487 {
488 byte[] byMsg = System.Text.Encoding.Default.GetBytes(strMsg.ToCharArray());
489 m_udpClient.Send(byMsg, byMsg.Length, REP);
490 }
491
492
493 /// <summary>
494 /// 发送消息,服务器专用
495 /// </summary>
496 /// <param name="strMsg"& gt;消息内容</param>
497 /// <param name="REP"& gt;接收节点</param>
498 private void ServerSendData(string strMsg, IPEndPoint REP)
499 {
500 byte[] byMsg = System.Text.Encoding.Default.GetBytes(strMsg.ToCharArray());
501 m_udpServer.Send(byMsg, byMsg.Length, REP);
502 }
503
504
505 /// <summary>
506 /// 发送本地节点信息
507 /// </summary>
508 /// <param name="strLocalIP"& gt;本地IP</param>
509 /// <param name="iLocalPort"& gt;本地端口</param>
510 public void SendLocalPoint(string strLocalIP, int iLocalPort, IPEndPoint REP)
511 {
512 string strLocalPoint = "\x01\x02" + strLocalIP + ":" + iLocalPort.ToString() + "\x02\x01";
513 SendData(strLocalPoint, REP);
514 }
515
516
517 /// <summary>
518 /// 同时向指定的终端(包括公共终端和私有终端)打洞
519 /// </summary>
520 /// <param name="pubEndPoint"& gt;公共终端</param>
521 /// <param name="prEndPoint"& gt;私有终端</param>
522 /// <returns>打洞成功返回true,否则返回false</returns>
523 public void StartBurrowTo(IPEndPoint pubEndPoint, IPEndPoint prEndPoint)
524 {
525 Thread burrowThread = new Thread(new ThreadStart(BurrowProc));
526 m_toEndPoint.m_privateEndPoint = prEndPoint;
527 m_toEndPoint.m_publicEndPoint = pubEndPoint;
528 burrowThread.Start();
529 }
530
531
532 /// <summary>
533 /// 打洞线程
534 /// </summary>
535 private void BurrowProc()
536 {
537 IPEndPoint prEndPoint = m_toEndPoint.m_privateEndPoint;
538 IPEndPoint pubEndPoint = m_toEndPoint.m_publicEndPoint;
539 int j = 0;
540 for (int i = 0; i < MAX_CONNECT_TRY; i++)
541 {
542 SendData("\x01\x07\x07\x01", prEndPoint);
543 SendData("\x01\x07\x07\x01", pubEndPoint);
544
545 // 等待接收线程标记修改
546 for (j = 0; j < MAX_CONNECT_TRY; j++)
547 {
548 if (m_bRecvAck)
549 {
550 m_bRecvAck = false;
551 SendData("\x01\x07\x07\x01", prEndPoint);
552 Thread.Sleep(50);
553 SendData("\x01\x07\x07\x01", pubEndPoint);
554
555 UDPSockEventArgs args = new UDPSockEventArgs("");
556 args.RemoteEndPoint = pubEndPoint;
557 if (OnNewConnectU != null)
558 {
559 OnNewConnectU(this, args);
560 }
561 //Thread .Sleep (System .Threading.Timeout .Infinite );
562 return;
563 }
564 else
565 {
566 Thread.Sleep(100);
567 }
568 }
569
570 //如果没有收到目标主机的回应,表明本次打
571 // 洞尝试失败,等待100毫秒后尝试下一次打洞
572 Thread.Sleep(100);
573 }
574
575 //MAX_CONNECT_TRY 尝试都失败,表明打洞失败,抛出异常
576 //throw new Exception(" 打洞失败!");
577 System.Windows.Forms.MessageBox.Show("打洞失败!");////////////
578 }
579
580
581 /// <summary>
582 /// 转发打洞请求消息,在服务器端使用
583 /// </summary>
584 /// <param name="strSrcPrEndpoint"& gt;请求转发的源私有终端</param>
585 /// <param name="strSrcPubEndPoint"& gt;请求转发的源公共终端</param>
586 /// <param name="REP"& gt;转发消息到达的目的终端</param>
587 public void SendBurrowRequest(string strSrcPrEndpoint, string strSrcPubEndPoint, IPEndPoint REP)
588 {
589 string strBurrowMsg = "\x04\x07" + strSrcPrEndpoint + " " + strSrcPubEndPoint + "\x07\x04";
590 ServerSendData(strBurrowMsg, REP);
591 }
592
593
594 /// <summary>
595 /// 检查字符串中的命令
596 /// </summary>
597 private void CheckCommand()
598 {
599 int nPos;
600 string strCmd = m_sbResponse.ToString();
601
602 //如果接收远端用户名
603 if ((nPos = strCmd.IndexOf("\x01\x02")) > -1)
604 {
605 ReceiveName(strCmd, nPos);
606
607 // 反馈公共终给端远端主机
608 string strPubEPMsg = "\x03\x07" + m_remotePoint.ToString() + "\x07\x03";
609 SendData(strPubEPMsg, m_remotePoint);
610
611 return;
612 }
613
614 //如果接收我的公共终端
615 if ((nPos = strCmd.IndexOf("\x03\x07")) > -1)
616 {
617 ReceiveMyPublicEndPoint(strCmd, nPos);
618 return;
619 }
620
621 //如果是打洞请求消息
622 if ((nPos = strCmd.IndexOf("\x04\x07")) > -1)
623 {
624 ReceiveAndSendAck(strCmd, nPos);
625 return;
626 }
627
628 //如果是打洞回应消息
629 if ((nPos = strCmd.IndexOf("\x01\x07")) > -1)
630 {
631 m_bRecvAck = true;
632 int nPos2 = strCmd.IndexOf("\x07\x01");
633 if (nPos2 > -1)
634 {
635 m_sbResponse.Remove(nPos, nPos2 - nPos + 2);
636 }
637
638
639
640 return;
641 }
642
643 //一般聊天消息
644 m_sbResponse.Remove(0, strCmd.Length);
645 RaiseMessageEvent(strCmd);
646 }
647
648
649 /// <summary>
650 /// 接收远端用户名
651 /// </summary>
652 /// <param name="strCmd"& gt;包含用户名的控制信息</param>
653 /// <param name="nPos"></param>
654 private void ReceiveName(string strCmd, int nPos)
655 {
656 int nPos2 = strCmd.IndexOf("\x02\x01");
657 if (nPos2 == -1)
658 {
659 return;
660 }
661 m_sbResponse.Remove(nPos, nPos2 - nPos + 2);
662
663 string strUserName = strCmd.Substring(nPos + 2, nPos2 - nPos - 2);
664 UDPSockEventArgs e = new UDPSockEventArgs("");
665 e.RemoteUserName = strUserName;
666 e.RemoteEndPoint = m_remotePoint;
667
668 //触发用户登录事件
669 if (OnUserLogInU != null)
670 {
671 OnUserLogInU(this, e);
672 }
673 }
674
675
676 /// <summary>
677 /// 接收打洞请求的消息并发送回应
678 /// </summary>
679 /// <param name="strCmd"></param>
680 /// <param name="nPos"></param>
681 private void ReceiveAndSendAck(string strCmd, int nPos)
682 {
683 int nPos2 = strCmd.IndexOf("\x07\x04");
684 if (nPos2 == -1)
685 {
686 return;
687 }
688 m_sbResponse.Remove(nPos, nPos2 - nPos + 2);
689
690 string strBurrowMsg = strCmd.Substring(nPos + 2, nPos2 - nPos - 2);
691
692 string[] strSrcPoint = strBurrowMsg.Split(' ');
693
694 //分析控制字符串包含的节点信息
695 string[] strPrEndPoint = strSrcPoint[0].Split(':');
696 string[] strPubEndPoint = strSrcPoint[1].Split(':');
697 m_requestPrivateEndPoint = new IPEndPoint(IPAddress.Parse(strPrEndPoint[0]), int.Parse(strPrEndPoint[1]));
698 m_requestPublicEndPoint = new IPEndPoint(IPAddress.Parse(strPubEndPoint[0]), int.Parse(strPubEndPoint[1]));
699
700 //向请求打洞终端的方向打洞
701 StartBurrowTo(m_requestPublicEndPoint, m_requestPrivateEndPoint);
702 }
703
704
705 /// <summary>
706 /// 接收我的公共终端
707 /// </summary>
708 /// <param name="strCmd"& gt;包含公共终端的控制信息</param>
709 /// <param name="nPos"& gt;控制字符串的起始位置</param>
710 private void ReceiveMyPublicEndPoint(string strCmd, int nPos)
711 {
712 int nPos2 = strCmd.IndexOf("\x07\x03");
713 if (nPos2 == -1)
714 {
715 return;
716 }
717 m_sbResponse.Remove(nPos, nPos2 - nPos + 2);
718
719 m_strMyPublicEndPoint = strCmd.Substring(nPos + 2, nPos2 - nPos - 2);
720 }
721
722
723 /// <summary>
724 /// 触发一般UDP消息事件
725 /// </summary>
726 /// <param name="strMsg"& gt;消息内容</param>
727 private void RaiseMessageEvent(string strMsg)
728 {
729 UDPSockEventArgs args = new UDPSockEventArgs("");
730 args.SockMessage = strMsg;
731 args.RemoteEndPoint = m_remotePoint;
732 if (OnSockMessageU != null)
733 {
734 OnSockMessageU(this, args);
735 }
736 }
737
738
739 /// <summary>
740 /// 获取当前进程作为客户端的公共终端
741 /// </summary>
742 public string MyPublicEndPoint
743 {
744 get
745 {
746 return m_strMyPublicEndPoint;
747 }
748 }
749
750
751 /// <summary>
752 /// 获取当前进程作为客户端的私有终端
753 /// </summary>
754 public string MyPrivateEndPoint
755 {
756 get
757 {
758 return m_strMyPrivateEndPoint;
759 }
760 }
761 }
762
763
764 /// <summary>
765 /// 保存打洞消息要发向的节点信息
766 /// </summary>
767 class ToEndPoint
768 {
769 /// <summary>
770 /// 私有节点
771 /// </summary>
772 public IPEndPoint m_privateEndPoint;
773
774 /// <summary>
775 /// 公共节点
776 /// </summary>
777 public IPEndPoint m_publicEndPoint;
778 }
779}
780
781
782
783
784
785
786关于如何使用上述程序包的一些说明:
787主要程序的初始化,参考代码如下:
788
789
790using UDPP;
791using P2PWellKnown;
792
793
794//创建UDP服务器和客户端
795try
796{
797 string strServerIP = "127.0.0.1";
798 UDPP2PSock udpSock = new UDPP2PSock();
799 udpSock.OnUserLogInU += new UdpUserLogInDelegate(OnUserLogInU);
800 udpSock.OnNewConnectU += new UdpNewConnectDelegate(OnNewConnectU);
801 udpSock.CreateUDPSever();
802 udpSock.CreateUDPClient(strServerIP, P2PConsts.UDP_SRV_PORT);
803}
804catch (Exception ex)
805{
806
807}
808
809经上面的初始化后,就可以使用类UDPP2PSock中的方法了。
810
811注:
812udpSock.OnUserLogInU += new UdpUserLogInDelegate(OnUserLogInU);
813udpSock.OnNewConnectU += new UdpNewConnectDelegate(OnNewConnectU);
814中的OnUserLogInU和OnNewConnectU是事件名称
815如
816private void test(object sender, UDPSockEventArgs e)
817{
818 MessageBox.Show("ok");
819}
820个性签名:做要做好,做到不三不四不如不做。
821
822
View Code
c# 中如何结束进程explorer.exe
1
2
3
4
5
6
7
8 1foreach (System.Diagnostics.Process thisproc in System.Diagnostics.Process.GetProcesses())
2{
3if(thisproc.ProcessName.Equals("explorer"))
4{
5thisproc.Kill();
6}
7}
8
View Code
c#换ip代理源码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513 1很多朋友都想如何提高自己的网站流量,可是都没有什么好的办法
2经过很长时间的研究,在C#中实现了,当然了,这部分代码其中一部分是网上的,不是原创。
3
4using System;
5using System.Drawing;
6using System.Collections;
7using System.ComponentModel;
8using System.Windows.Forms;
9using System.Data;
10using System.Runtime.InteropServices;
11using System.Diagnostics;
12using System.IO;
13using System.Text.RegularExpressions;
14using System.Text;
15using System.Net;
16namespace WebSock
17{
18 /// <summary>
19 /// Form1 的摘要说明。
20 /// </summary>
21 public class Form1 : System.Windows.Forms.Form
22 {
23 private System.Windows.Forms.GroupBox groupBox1;
24 private AxSHDocVw.AxWebBrowser axWebBrowser1;
25 private System.Windows.Forms.Button button1;
26 private System.Windows.Forms.Button button2;
27 private System.Windows.Forms.OpenFileDialog openFileDialog1;
28 private System.Windows.Forms.Timer timer1;
29 private System.ComponentModel.IContainer components;
30 private System.Windows.Forms.StatusBar statusBar1;
31 private System.Windows.Forms.StatusBarPanel statusBarPanel1;
32 private System.Windows.Forms.GroupBox groupBox2;
33 private System.Windows.Forms.GroupBox groupBox3;
34 private System.Windows.Forms.GroupBox groupBox4;
35 private System.Windows.Forms.Button button3;
36 ArrayList arrText = new ArrayList();
37 int Total = 0;
38 int i,k=0;
39 private System.Windows.Forms.GroupBox groupBox5;
40 private System.Windows.Forms.Label label1;
41 private System.Windows.Forms.TextBox txtWebUrl;
42 private const string TitleInfo = "程序制作红色银狐";
43 private System.Windows.Forms.ListBox listBox1;
44 private string strUrl = "";
45 public Form1()
46 {
47 //
48 // Windows 窗体设计器支持所必需的
49 //
50 InitializeComponent();
51 //
52 // TODO: 在 InitializeComponent 调用后添加任何构造函数代码
53 //
54 }
55
56 /// <summary>
57 /// 清理所有正在使用的资源。
58 /// </summary>
59 protected override void Dispose( bool disposing )
60 {
61 if( disposing )
62 {
63 if (components != null)
64 {
65 components.Dispose();
66 }
67 }
68 base.Dispose( disposing );
69 }
70
71 #region Windows 窗体设计器生成的代码
72 /// <summary>
73 /// 设计器支持所需的方法 - 不要使用代码编辑器修改
74 /// 此方法的内容。
75 /// </summary>
76 private void InitializeComponent()
77 {
78 this.components = new System.ComponentModel.Container();
79 System.Resources.ResourceManager resources = new System.Resources.ResourceManager(typeof(Form1));
80 this.groupBox1 = new System.Windows.Forms.GroupBox();
81 this.groupBox3 = new System.Windows.Forms.GroupBox();
82 this.axWebBrowser1 = new AxSHDocVw.AxWebBrowser();
83 this.groupBox2 = new System.Windows.Forms.GroupBox();
84 this.listBox1 = new System.Windows.Forms.ListBox();
85 this.button1 = new System.Windows.Forms.Button();
86 this.button2 = new System.Windows.Forms.Button();
87 this.openFileDialog1 = new System.Windows.Forms.OpenFileDialog();
88 this.timer1 = new System.Windows.Forms.Timer(this.components);
89 this.statusBar1 = new System.Windows.Forms.StatusBar();
90 this.statusBarPanel1 = new System.Windows.Forms.StatusBarPanel();
91 this.groupBox4 = new System.Windows.Forms.GroupBox();
92 this.button3 = new System.Windows.Forms.Button();
93 this.groupBox5 = new System.Windows.Forms.GroupBox();
94 this.label1 = new System.Windows.Forms.Label();
95 this.txtWebUrl = new System.Windows.Forms.TextBox();
96 this.groupBox1.SuspendLayout();
97 this.groupBox3.SuspendLayout();
98 ((System.ComponentModel.ISupportInitialize)(this.axWebBrowser1)).BeginInit();
99 this.groupBox2.SuspendLayout();
100 ((System.ComponentModel.ISupportInitialize)(this.statusBarPanel1)).BeginInit();
101 this.groupBox4.SuspendLayout();
102 this.groupBox5.SuspendLayout();
103 this.SuspendLayout();
104 //
105 // groupBox1
106 //
107 this.groupBox1.Controls.Add(this.groupBox3);
108 this.groupBox1.Controls.Add(this.groupBox2);
109 this.groupBox1.Location = new System.Drawing.Point(0, 0);
110 this.groupBox1.Name = "groupBox1";
111 this.groupBox1.Size = new System.Drawing.Size(810, 440);
112 this.groupBox1.TabIndex = 0;
113 this.groupBox1.TabStop = false;
114 //
115 // groupBox3
116 //
117 this.groupBox3.Controls.Add(this.axWebBrowser1);
118 this.groupBox3.Location = new System.Drawing.Point(312, 8);
119 this.groupBox3.Name = "groupBox3";
120 this.groupBox3.Size = new System.Drawing.Size(490, 424);
121 this.groupBox3.TabIndex = 2;
122 this.groupBox3.TabStop = false;
123 this.groupBox3.Text = "浏览器";
124 //
125 // axWebBrowser1
126 //
127 this.axWebBrowser1.Anchor = ((System.Windows.Forms.AnchorStyles)((((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom)
128 | System.Windows.Forms.AnchorStyles.Left)
129 | System.Windows.Forms.AnchorStyles.Right)));
130 this.axWebBrowser1.ContainingControl = this;
131 this.axWebBrowser1.Enabled = true;
132 this.axWebBrowser1.Location = new System.Drawing.Point(8, 16);
133 this.axWebBrowser1.OcxState = ((System.Windows.Forms.AxHost.State)(resources.GetObject("axWebBrowser1.OcxState")));
134 this.axWebBrowser1.Size = new System.Drawing.Size(474, 400);
135 this.axWebBrowser1.TabIndex = 0;
136 //
137 // groupBox2
138 //
139 this.groupBox2.Controls.Add(this.listBox1);
140 this.groupBox2.Location = new System.Drawing.Point(8, 8);
141 this.groupBox2.Name = "groupBox2";
142 this.groupBox2.Size = new System.Drawing.Size(296, 424);
143 this.groupBox2.TabIndex = 1;
144 this.groupBox2.TabStop = false;
145 this.groupBox2.Text = "代理IP地址";
146 //
147 // listBox1
148 //
149 this.listBox1.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
150 this.listBox1.ItemHeight = 12;
151 this.listBox1.Location = new System.Drawing.Point(8, 16);
152 this.listBox1.Name = "listBox1";
153 this.listBox1.Size = new System.Drawing.Size(280, 398);
154 this.listBox1.TabIndex = 2;
155 //
156 // button1
157 //
158 this.button1.Location = new System.Drawing.Point(310, 16);
159 this.button1.Name = "button1";
160 this.button1.Size = new System.Drawing.Size(176, 32);
161 this.button1.TabIndex = 1;
162 this.button1.Text = "载入代理IP";
163 this.button1.Click += new System.EventHandler(this.button1_Click_1);
164 //
165 // button2
166 //
167 this.button2.Location = new System.Drawing.Point(486, 16);
168 this.button2.Name = "button2";
169 this.button2.Size = new System.Drawing.Size(176, 32);
170 this.button2.TabIndex = 2;
171 this.button2.Text = "开始刷流量";
172 this.button2.Click += new System.EventHandler(this.button2_Click);
173 //
174 // timer1
175 //
176 this.timer1.Interval = 10000;
177 this.timer1.Tick += new System.EventHandler(this.timer1_Tick);
178 //
179 // statusBar1
180 //
181 this.statusBar1.Dock = System.Windows.Forms.DockStyle.None;
182 this.statusBar1.Location = new System.Drawing.Point(0, 552);
183 this.statusBar1.Name = "statusBar1";
184 this.statusBar1.Panels.AddRange(new System.Windows.Forms.StatusBarPanel[] {
185 this.statusBarPanel1});
186 this.statusBar1.ShowPanels = true;
187 this.statusBar1.Size = new System.Drawing.Size(810, 24);
188 this.statusBar1.TabIndex = 3;
189 //
190 // statusBarPanel1
191 //
192 this.statusBarPanel1.Width = 820;
193 //
194 // groupBox4
195 //
196 this.groupBox4.Controls.Add(this.button3);
197 this.groupBox4.Controls.Add(this.button2);
198 this.groupBox4.Controls.Add(this.button1);
199 this.groupBox4.Location = new System.Drawing.Point(0, 496);
200 this.groupBox4.Name = "groupBox4";
201 this.groupBox4.Size = new System.Drawing.Size(810, 56);
202 this.groupBox4.TabIndex = 4;
203 this.groupBox4.TabStop = false;
204 this.groupBox4.Text = "操作区";
205 //
206 // button3
207 //
208 this.button3.Location = new System.Drawing.Point(134, 16);
209 this.button3.Name = "button3";
210 this.button3.Size = new System.Drawing.Size(176, 32);
211 this.button3.TabIndex = 3;
212 this.button3.Text = "从网络获取代理IP";
213 this.button3.Click += new System.EventHandler(this.button3_Click);
214 //
215 // groupBox5
216 //
217 this.groupBox5.Controls.Add(this.label1);
218 this.groupBox5.Controls.Add(this.txtWebUrl);
219 this.groupBox5.Location = new System.Drawing.Point(0, 444);
220 this.groupBox5.Name = "groupBox5";
221 this.groupBox5.Size = new System.Drawing.Size(810, 48);
222 this.groupBox5.TabIndex = 5;
223 this.groupBox5.TabStop = false;
224 this.groupBox5.Text = "要刷网站地址";
225 //
226 // label1
227 //
228 this.label1.Location = new System.Drawing.Point(16, 21);
229 this.label1.Name = "label1";
230 this.label1.Size = new System.Drawing.Size(56, 16);
231 this.label1.TabIndex = 1;
232 this.label1.Text = "网站地址";
233 //
234 // txtWebUrl
235 //
236 this.txtWebUrl.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle;
237 this.txtWebUrl.Location = new System.Drawing.Point(80, 16);
238 this.txtWebUrl.Name = "txtWebUrl";
239 this.txtWebUrl.Size = new System.Drawing.Size(720, 21);
240 this.txtWebUrl.TabIndex = 0;
241 this.txtWebUrl.Text = "http://www.51solve.com/";
242 //
243 // Form1
244 //
245 this.AutoScaleBaseSize = new System.Drawing.Size(6, 14);
246 this.ClientSize = new System.Drawing.Size(810, 575);
247 this.Controls.Add(this.groupBox5);
248 this.Controls.Add(this.groupBox4);
249 this.Controls.Add(this.statusBar1);
250 this.Controls.Add(this.groupBox1);
251 this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedSingle;
252 this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));
253 this.MaximizeBox = false;
254 this.Name = "Form1";
255 this.StartPosition = System.Windows.Forms.FormStartPosition.CenterScreen;
256 this.Text = "网站流量访问程序制作:红色银狐";
257 this.groupBox1.ResumeLayout(false);
258 this.groupBox3.ResumeLayout(false);
259 ((System.ComponentModel.ISupportInitialize)(this.axWebBrowser1)).EndInit();
260 this.groupBox2.ResumeLayout(false);
261 ((System.ComponentModel.ISupportInitialize)(this.statusBarPanel1)).EndInit();
262 this.groupBox4.ResumeLayout(false);
263 this.groupBox5.ResumeLayout(false);
264 this.ResumeLayout(false);
265
266 }
267 #endregion
268
269 /// <summary>
270 /// 应用程序的主入口点。
271 /// </summary>
272 [STAThread]
273 static void Main()
274 {
275 Application.Run(new Form1());
276 }
277 //定义结构体代理信息
278 public struct Struct_INTERNET_PROXY_INFO
279 {
280 public int dwAccessType;
281 public IntPtr proxy;
282 public IntPtr proxyBypass;
283 };
284 [DllImport("wininet.dll", SetLastError = true)]
285 private static extern bool InternetSetOption(IntPtr hInternet, int dwOption, IntPtr lpBuffer, int lpdwBufferLength);
286
287 private void RefreshIESettings(string strProxy)
288 {
289 const int INTERNET_OPTION_PROXY = 38;
290 const int INTERNET_OPEN_TYPE_PROXY = 3;
291
292 Struct_INTERNET_PROXY_INFO struct_IPI;
293
294 // Filling in structure
295 struct_IPI.dwAccessType = INTERNET_OPEN_TYPE_PROXY;
296 struct_IPI.proxy = Marshal.StringToHGlobalAnsi(strProxy);
297 struct_IPI.proxyBypass = Marshal.StringToHGlobalAnsi("local");
298
299 // Allocating memory
300 IntPtr intptrStruct = Marshal.AllocCoTaskMem(Marshal.SizeOf(struct_IPI));
301
302 // Converting structure to IntPtr
303 Marshal.StructureToPtr(struct_IPI, intptrStruct, true);
304
305 bool iReturn = InternetSetOption(IntPtr.Zero, INTERNET_OPTION_PROXY, intptrStruct, Marshal.SizeOf(struct_IPI));
306 }
307
308 private void StartShua()
309 {
310 statusBar1.Panels[0].Text = "正在使用" + arrText[k].ToString() + "代理IP访问网站";
311 this.listBox1.SetSelected(k,true);
312 RefreshIESettings(arrText[k].ToString());
313 System.Object nullObject = 0;
314 string strTemp = String.Empty;
315 System.Object nullObjStr = strTemp;
316 axWebBrowser1.Navigate(strUrl, ref nullObject, ref nullObjStr, ref nullObjStr, ref nullObjStr);
317 k+=1;
318 if(k>=i)k=0;
319 }
320 private void button1_Click_1(object sender, System.EventArgs e)
321 {
322 arrText.Clear();
323 i = 0;
324 if(openFileDialog1.ShowDialog() ==DialogResult.OK)
325 {
326 string strPath,strLine = "";
327 strPath = openFileDialog1.FileName.ToString();
328 StreamReader sr = new StreamReader(strPath);
329 while(strLine != null)
330 {
331 strLine = sr.ReadLine();
332 if(strLine != null)
333 {
334 i+=1;
335 arrText.Add(strLine);
336 listBox1.Items.Add(strLine);
337 }
338 }
339 sr.Close();
340 }
341 }
342 private void timer1_Tick(object sender, System.EventArgs e)
343 {
344 StartShua();
345 }
346
347 private void button2_Click(object sender, System.EventArgs e)
348 {
349 Total = listBox1.Items.Count;
350 strUrl = txtWebUrl.Text;
351 if(button2.Text == "开始刷流量")
352 {
353 if(i == 0 && Total == 0)return;
354 if(strUrl.Length == 0)return;
355 StartShua();
356 button2.Text = "停止刷流量";
357 timer1.Enabled = true;
358 timer1.Start();
359 button1.Enabled = false;
360 button3.Enabled = false;
361 }
362 else
363 {
364 timer1.Stop();
365 timer1.Enabled = false;
366 button2.Text = "开始刷流量";
367 button1.Enabled = true;
368 button3.Enabled = true;
369 arrText.Clear();
370 }
371 }
372
373 private void button3_Click(object sender, System.EventArgs e)
374 {
375 arrText.Clear();
376 i = 0;
377 listBox1.Items.Clear();
378 string strHtml = "";
379 string strPort = "";
380 string strResultIP = "";
381 long PosB = 0;
382 long PosA = 0;
383 long PosC = 0;
384 string Url = "http://www.pass-e.com/proxy/";
385 try
386 {
387 strHtml = GetHtml(Url);
388 strHtml = checkStr(strHtml);
389 strHtml = strHtml.ToLower();
390 PosA = strHtml.IndexOf("list",0);
391 //MessageBox.Show(GetHtml(Url));
392 while(PosA>0)
393 {
394 i+=1;
395 PosB = strHtml.IndexOf(",",(int)PosA);
396 strResultIP = strHtml.Substring((int)PosA,(int)PosB-(int)PosA);
397 strResultIP = strResultIP.Replace("list","");
398 PosC = strHtml.IndexOf(",",(int)PosB+1);
399 strPort = strHtml.Substring((int)PosB,(int)PosC-(int)PosB);
400 strPort = strPort.Replace(",","");
401 listBox1.Items.Add(strResultIP+":"+strPort);
402 PosA = strHtml.IndexOf("list",(int)PosC);
403 arrText.Add(strResultIP+":"+strPort);
404 }
405 }
406 catch(Exception ex)
407 {
408 MessageBox.Show(ex.Message,TitleInfo,MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
409 }
410 }
411 public string checkStr(string html)
412 {
413 string str = Convert.ToString((char)34);
414
415 Regex regex1 = new Regex(@"<mce:script[/s/S]+</script *><!--
416", RegexOptions.IgnoreCase);
417 Regex regex2 = new Regex(@" href *= *[/s/S]*script *:", RegexOptions.IgnoreCase);
418 Regex regex3 = new Regex(@" no[/s/S]*=", RegexOptions.IgnoreCase);
419 Regex regex4 = new Regex(@"<iframe[/s/S]+</iframe *>", RegexOptions.IgnoreCase);
420 Regex regex5 = new Regex(@"<frameset[/s/S]+</frameset *>", RegexOptions.IgnoreCase);
421 Regex regex6 = new Regex(@"/<img[^/>]+/>", RegexOptions.IgnoreCase);
422 Regex regex7 = new Regex(@"</p>", RegexOptions.IgnoreCase);
423 Regex regex8 = new Regex(@"<p>", RegexOptions.IgnoreCase);
424 Regex regex9 = new Regex(@"<[^>]*>", RegexOptions.IgnoreCase);
425 html = html.Replace("/r/n","");
426 //html = regex1.Replace(html, ""); //过滤<script>
427// --></mce:script>标记
428 html = regex2.Replace(html, ""); //过滤href=javascript: (<A>) 属性
429 html = regex3.Replace(html, " _disibledevent="); //过滤其它控件的on...事件
430 html = regex4.Replace(html, ""); //过滤iframe
431 html = regex5.Replace(html, ""); //过滤frameset
432 html = regex6.Replace(html, ""); //过滤frameset
433 html = regex7.Replace(html, ""); //过滤frameset
434 html = regex8.Replace(html, ""); //过滤frameset
435 html = regex9.Replace(html, "");
436 html = html.Replace(" ", "");
437 html = html.Replace("</strong>", "");
438 html = html.Replace("<strong>", "");
439 html = html.Replace("/n","");
440 html = html.Replace(str ,"");
441 html = html.Replace("}" ,"");
442 html = html.Replace("(" ,"");
443 html = html.Replace(")" ,"");
444 //html = html.Replace(";" ,"");
445 html = html.Replace("'" ,"");
446 html = html.Replace(" " ,"");
447 html = html.Replace(" ","");
448 return html;
449 }
450 public string GetHtml(string myUrl)
451 {
452 HttpWebRequest myHttpWebRequest;
453
454 HttpWebResponse myHttpWebResponse;
455
456 //string Html;
457
458 try
459 {
460
461 string URL = myUrl;
462
463 Uri myUri = new Uri(myUrl);
464
465 WebRequest myWebRequest = WebRequest.Create(URL);
466
467 //使用Creat方法创建WebRequest实例
468
469 myHttpWebRequest = (HttpWebRequest)myWebRequest;
470
471 //实现WebRequest类型和HttpWebRequest类型的转换
472
473 WebResponse myWebResponse = myHttpWebRequest.GetResponse();
474
475 //获得响应信息
476
477 myHttpWebResponse = (HttpWebResponse)myWebResponse;
478
479 Stream myStream = myHttpWebResponse.GetResponseStream();
480
481 //获得从当前Internet资源返回的响应流数据
482
483 StreamReader srReader = new StreamReader(myStream, Encoding.Default);
484
485 //利用获得的响应流和系统缺省编码来初始化StreamReader实例。
486
487 string sTemp = srReader.ReadToEnd();
488
489 //从响应流从读取数据
490
491 srReader.Close();
492
493 return sTemp;
494 }
495
496 //显示读取的数据 ( )
497
498 catch (WebException WebExcp)
499 {
500
501 return WebExcp.Message.ToString();
502 }
503 }
504 }
505
506}
507
508
509
510
511
512通过它的实现,只要你有足够的代理IP那么你的网站流量变飞速的提升。
513
View Code
c#中WinForm的TextBox循环自动滚动示例
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76 1这个问题来自论坛提问,演示代码如下
2
3using System;
4using System.Collections.Generic;
5using System.ComponentModel;
6using System.Data;
7using System.Drawing;
8using System.Text;
9using System.Windows.Forms;
10using System.Runtime.InteropServices;
11namespace WindowsApplication27
12{
13 /// <summary>
14 /// 演示如何在TextBox中让文字循环滚动:
15 /// 作者jinjazz
16 /// 作者blog:http://blog.csdn.net/jinjazz
17 /// </summary>
18 public partial class Form1 : Form
19 {
20 public Form1()
21 {
22 InitializeComponent();
23
24 this.textBox1.Clear();
25 for (int i = 0; i <= 20;i++ )
26 {
27 this.textBox1.Text += string.Format("{0}:jinjazz__{1} ", i,i);
28 }
29 this.timer1.Interval = 200;
30 this.timer1.Start();
31 }
32
33 //发送消息
34 [DllImport("user32.dll", EntryPoint = "SendMessage")]
35 public static extern int SendMessage(IntPtr hWnd, int wMsg, int wParam, int lParam);
36 //获取滚动条位置
37 [DllImport("user32")]
38 public static extern int GetScrollPos(IntPtr hwnd, int nBar);
39 //设置滚动条位置
40 [DllImport("user32.dll")]
41 static extern int SetScrollPos(IntPtr hWnd, int nBar,
42 int nPos, bool bRedraw);
43
44 public const int EM_LINESCROLL = 0xb6;
45
46 private void timer1_Tick(object sender, EventArgs e)
47 {
48 int i= GetScrollPos(this.textBox1.Handle,1);
49
50 //向下滚动一行
51 SendMessage(this.textBox1.Handle, EM_LINESCROLL, 0, 1);//0,1代表垂直滚动条向下滚动
52
53 //判断是否有位置变化,如果没有则说明到了底部,返回开始处
54 if (i == GetScrollPos(this.textBox1.Handle, 1))
55 {
56 //回到顶部,这里用SetScrollPos似乎有问题,滚动条和文字不是同步更新
57 this.textBox1.SelectionStart = 0;
58 this.textBox1.SelectionLength = 1;
59 this.textBox1.ScrollToCaret();
60 this.textBox1.SelectionLength = 0;
61 }
62 Console.WriteLine(i);
63 }
64
65 private void textBox1_MouseEnter(object sender, EventArgs e)
66 {
67 this.timer1.Stop();
68 }
69
70 private void textBox1_MouseLeave(object sender, EventArgs e)
71 {
72 this.timer1.Start();
73 }
74 }
75}
76
View Code
wpf翻页效果
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618 1教你打造Silverlight超酷翻页实例
2作者:洗碗心得 | 出处:博客园 | 2011/10/18 19:47:52 | 阅读22次
3经常阅读电子杂志的朋友对其流畅自然的翻页过渡效果应当留下了十分深刻的印象。这些杂志都是使用Flash技术制作而成的。总想着能用Silverlight实现这样的效果,去网上查查资料,找到了一个微软官方提供的翻页效果例子(教程说明点这里,在线实例演示及源代码下载点这里)。这里再推荐一个外国网站的Silverlight翻页在线实例。
4
5
6
7
8
9效果是十分的赞,只可惜控制的逻辑是用JavaScript代码实现的,这就不利于程序逻辑的整体控制。笔者最近在CodePlex上,找到了一个开源的翻页控件WPF and Silverlight BookControls(点这里进入),用它进行Silverlight翻页效果的开发就显得十分得心应手了。下面就向大家一步一步地介绍Silverlight翻页效果的实现过程。
10
11导航:
12①建立翻页项目解决方案
13②添加必要文件
14③构建应用程序界面
15④设置应用程序控制逻辑
16⑤最终效果图
17
181、建立翻页项目解决方案
19点击File->Projects...菜单选项,新建一个ASP.NET Web Application。
20
21
22
23
24将新建工程名称命名为FlipPage。
25
26
27
28
29在解决方案下继续添加一个Silverlight应用程序项目,将该工程命名为SilverlightClient。
30
31
32
33
34在弹出的对话框中,直接点OK按钮。
35
36
37
38
39点击一下“全部保存”按钮,完成项目工程的创建。
40
412、添加必要文件
42在SilverlightClient项目文件夹下,新建一个名为Dll的文件夹,在里面放入WPF and Silverlight BookControls的动态链接库文件SLMitsuControls.dll(如下图)。在FlipPage项目文件夹下,新建一个名为mediaPictures的子文件夹,在里面放入将在书中显示的图片,如下图所示命名。同样的,在SilverlightClient项目文件夹下,新建一个名为PageType的文件夹,然后再新建两个类分别命名为LeftPage.cs和RightPage.cs(如下图),它们分别代表了书的偶数和奇数页面,具体代码如下所示(详细的说明请见代码注释)。
43
44
45
46
47
48
49LeftPage.cs文件代码:
50
51Code System;
52using System.Net;
53using System.Windows;
54using System.Windows.Controls;
55using System.Windows.Documents;
56using System.Windows.Ink;
57using System.Windows.Input;
58using System.Windows.Media;
59using System.Windows.Media.Animation;
60using System.Windows.Media.Imaging;
61using System.Windows.Shapes;
62
63namespace SilverlightClient.TypePage
64{
65 public class LeftPage : Canvas
66 {
67 //定义将在页面上显示的元素
68 private Image imgPhoto;
69 private Button btnPrevious;
70 private Rectangle RecBorder;
71 private TextBlock PageNum;
72
73 //构造函数
74 public LeftPage()
75 {
76 //页面的设置
77 this.Width = 452;
78 this.Height = 630;
79 this.Background = new SolidColorBrush(Colors.White);
80 Canvas.SetLeft(this, 0);
81 Canvas.SetTop(this, 0);
82 //页面边框的设置
83 RecBorder = new Rectangle();
84 RecBorder.Width = 452;
85 RecBorder.Height = 630;
86 Canvas.SetLeft(RecBorder, 0);//设置页面边框在Canvas中的位置,下同。
87 Canvas.SetTop(RecBorder, 0);
88 RecBorder.Stroke = new SolidColorBrush(Colors.Black);
89 RecBorder.StrokeThickness = 0;
90 this.Children.Add(RecBorder);
91 //照片的设置
92 imgPhoto = new Image();
93 imgPhoto.Width = 450;
94 imgPhoto.Height = 600;
95 Canvas.SetLeft(imgPhoto, 1);
96 Canvas.SetTop(imgPhoto, 1);
97 this.Children.Add(imgPhoto);
98 //“前一页”按钮的设置
99 btnPrevious = new Button();
100 btnPrevious.Width = 150;
101 btnPrevious.Height = 20;
102 btnPrevious.Content = "<< 前一页";
103 btnPrevious.HorizontalContentAlignment = HorizontalAlignment.Center;
104 btnPrevious.VerticalContentAlignment = VerticalAlignment.Center;
105 btnPrevious.Cursor = Cursors.Hand;
106 Canvas.SetLeft(btnPrevious, 151);
107 Canvas.SetTop(btnPrevious, 605);
108 this.Children.Add(btnPrevious);
109 //页码文本的设置
110 PageNum = new TextBlock();
111 PageNum.Width = 100;
112 PageNum.Height = 20;
113 PageNum.Text = "00 / 00";
114 PageNum.TextAlignment = TextAlignment.Left;
115 PageNum.VerticalAlignment = VerticalAlignment.Center;
116 PageNum.FontFamily = new FontFamily("Comic sans MS");
117 Canvas.SetLeft(PageNum, 10);
118 Canvas.SetTop(PageNum, 607);
119 this.Children.Add(PageNum);
120 }
121 //设置图片路径
122 public void setterimgPhoto(string path)
123 {
124 BitmapImage btm = new BitmapImage();
125 btm.UriSource = new Uri(path, UriKind.Relative);
126 imgPhoto.Source = btm;
127 }
128 //设置按钮是否可见
129 public void setterDisplayBtnPrevious(bool YesNo)
130 {
131 if (YesNo)
132 {
133 btnPrevious.Visibility = Visibility.Visible;
134 }
135 else {
136 btnPrevious.Visibility = Visibility.Collapsed;
137 }
138 }
139 //设置页码
140 public void setterPageNumber(string currentPageNum, string TotalPageNum) {
141 PageNum.Text = currentPageNum + " / " + TotalPageNum;
142 }
143 //返回按钮单击事件关联
144 public Button getbtnPrevious()
145 {
146 return btnPrevious;
147 }
148
149 }
150}
151
152
153RightPage.cs文件代码:
154
155
156Code System;
157using System.Net;
158using System.Windows;
159using System.Windows.Controls;
160using System.Windows.Documents;
161using System.Windows.Ink;
162using System.Windows.Input;
163using System.Windows.Media;
164using System.Windows.Media.Animation;
165using System.Windows.Media.Imaging;
166using System.Windows.Shapes;
167
168namespace SilverlightClient.TypePage
169{
170 public class RightPage : Canvas
171 {
172 //定义将在页面上显示的元素
173 private Image imgPhoto;
174 private Button btnNext;
175 private Rectangle RecBorder;
176 private TextBlock PageNum;
177
178 //构造函数
179 public RightPage()
180 {
181 //页面的设置
182 this.Width = 452;
183 this.Height = 630;
184 this.Background = new SolidColorBrush(Colors.White);
185 Canvas.SetLeft(this, 0);//设置页面边框在Canvas中的位置,下同。
186 Canvas.SetTop(this, 0);
187 //页面边框的设置
188 RecBorder = new Rectangle();
189 RecBorder.Width = 452;
190 RecBorder.Height = 630;
191 Canvas.SetLeft(RecBorder, 0);
192 Canvas.SetTop(RecBorder, 0);
193 RecBorder.Stroke = new SolidColorBrush(Colors.Black);
194 RecBorder.StrokeThickness = 0;
195 this.Children.Add(RecBorder);
196 //照片的设置
197 imgPhoto = new Image();
198 imgPhoto.Width = 450;
199 imgPhoto.Height = 600;
200 Canvas.SetLeft(imgPhoto, 1);
201 Canvas.SetTop(imgPhoto, 1);
202 this.Children.Add(imgPhoto);
203 //“后一页”按钮的设置
204 btnNext = new Button();
205 btnNext.Width = 150;
206 btnNext.Height = 20;
207 btnNext.Content = "后一页 >>";
208 btnNext.HorizontalContentAlignment = HorizontalAlignment.Center;
209 btnNext.VerticalContentAlignment = VerticalAlignment.Center;
210 btnNext.Cursor = Cursors.Hand;
211 Canvas.SetLeft(btnNext, 151);
212 Canvas.SetTop(btnNext, 605);
213 this.Children.Add(btnNext);
214 //页码文本的设置
215 PageNum = new TextBlock();
216 PageNum.Width = 100;
217 PageNum.Height = 20;
218 PageNum.Text = "00 / 00";
219 PageNum.TextAlignment = TextAlignment.Right;
220 PageNum.VerticalAlignment = VerticalAlignment.Center;
221 PageNum.FontFamily = new FontFamily("Comic sans MS");
222 Canvas.SetLeft(PageNum, 340);
223 Canvas.SetTop(PageNum, 607);
224 this.Children.Add(PageNum);
225 }
226 //设置图片路径
227 public void setterimgPhoto(string path)
228 {
229 BitmapImage btm = new BitmapImage();
230 btm.UriSource = new Uri(path, UriKind.Relative);
231 imgPhoto.Source = btm;
232 }
233 //设置按钮是否可见
234 public void setterDisplayBtnNext(bool YesNo)
235 {
236 if (YesNo)
237 {
238 btnNext.Visibility = Visibility.Visible;
239 }
240 else
241 {
242 btnNext.Visibility = Visibility.Collapsed;
243 }
244 }
245 //设置页码
246 public void setterPageNumber(string currentPageNum, string TotalPageNum)
247 {
248 PageNum.Text = currentPageNum + " / " + TotalPageNum;
249 }
250 //返回按钮单击事件关联
251 public Button getbtnNext()
252 {
253 return btnNext;
254 }
255
256 }
257}
258
2593、构建应用程序界面
260详细的说明请见代码注释。
261MainPage.xaml文件代码:
262
263CodeUserControl x:Class="SilverlightClient.MainPage"
264 xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
265 xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
266 xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
267 xmlns:local="clr-namespace:SLMitsuControls;assembly=SLMitsuControls"
268 mc:Ignorable="d" d:DesignWidth="640" d:DesignHeight="480" Loaded="UserControl_Loaded">
269 <Grid x:Name="LayoutRoot">
270 <Canvas x:Name="layout" Background="White" Width="906" Height="630" Canvas.Left="0" Canvas.Top="0">
271 <!--显示层-->
272 <Canvas x:Name="canvasBook" Background="White" Width="906" Height="630" Canvas.Left="0" Canvas.Top="0" Visibility="Collapsed">
273 <local:UCBook x:Name="book" Width="906" Height="630" Canvas.Left="0" Canvas.Top="0" /><!--BookControl-->
274 </Canvas>
275 <!--加载层-->
276 <Canvas x:Name="canvChanging" Width="500" Height="75" Canvas.Left="200" Canvas.Top="250" Visibility="Collapsed" Background="Transparent">
277 <TextBlock x:Name="changingText" Text="页面加载中
278
279" Width="200" Height="30" Canvas.Left="0" Canvas.Top="0" FontFamily="comic sans ms" FontSize="14"></TextBlock>
280 <ProgressBar x:Name="changingProgressBar" Width="500" Height="30" Canvas.Left="0" Canvas.Top="30"></ProgressBar>
281 </Canvas>
282 </Canvas>
283 </Grid>
284</UserControl>
285
286
2874、设置应用程序控制逻辑
288
289详细的说明请见代码注释。
2901)MainPage.xaml.cs文件代码:
291
292Code System;
293using System.Collections.Generic;
294using System.Linq;
295using System.Net;
296using System.Windows;
297using System.Windows.Controls;
298using System.Windows.Documents;
299using System.Windows.Input;
300using System.Windows.Media;
301using System.Windows.Media.Animation;
302using System.Windows.Media.Imaging;
303using System.Windows.Shapes;
304using System.Threading;
305using SLMitsuControls;
306
307namespace SilverlightClient
308{
309 public partial class MainPage : UserControl, IDataProvider
310 {
311 //定义全局变量
312 private List<object> PageObjectList;//页面对象列表
313 public enum PageType { right, left };//页面类型
314 public string fileMedia = "";//文件媒体
315 public string headerPage = "";//首页
316 public int maxiPageNum = 0;//最大页数
317 public enum Location { local, web };//枚举应用程序所在
318 public Location modeLocation;
319 private int pageDownload = 0;//下载的页面数
320 private string uriResources = "";//Uri地址
321
322 //构造函数
323 public MainPage()
324 {
325 InitializeComponent();
326 PageObjectList = new List<object>();
327 }
328
329 //UserControl事件触发处理
330 private void UserControl_Loaded(object sender, RoutedEventArgs e)
331 {
332 if (modeLocation == Location.local)
333 {
334 this.canvChanging.Visibility = Visibility.Collapsed;
335 this.canvasBook.Visibility = Visibility.Visible;
336 //填充页面列表
337 FillPagesList();
338 }
339 if (modeLocation == Location.web)
340 {
341 this.canvChanging.Visibility = Visibility.Visible;
342 this.canvasBook.Visibility = Visibility.Collapsed;
343 //开始下载页面
344 DownloadPages();
345 }
346 }
347
348 //开始将页面填充至List中
349 private void FillPagesList()
350 {
351 //用页面填充列表
352 for (int xx = 1; xx <= maxiPageNum; xx++)
353 {
354 if (xx % 2 != 0)
355 {
356 //前一页即奇数页
357 AddPageToList(PageType.right, fileMedia + "/" + headerPage + xx.ToString("00") + ".jpg", xx.ToString(),
358 maxiPageNum.ToString(), true);
359 }
360 else
361 {
362 //后一页即偶数页
363 AddPageToList(PageType.left, fileMedia + "/" + headerPage + xx.ToString("00") + ".jpg", xx.ToString(),
364 maxiPageNum.ToString(), true);
365 }
366 }
367
368 //移除最后一页的按钮
369 TypePage.RightPage page = PageObjectList[maxiPageNum - 1] as TypePage.RightPage;
370 page.setterDisplayBtnNext(false);
371
372 //为翻页按钮指派事件触发处理
373 for (int xx = 1; xx < maxiPageNum; xx++)
374 {
375 if (xx % 2 != 0)
376 {
377 //前一页即奇数页
378 TypePage.RightPage pp = PageObjectList[xx - 1] as TypePage.RightPage;
379 Button btnNext = pp.getbtnNext();
380 btnNext.Click += new RoutedEventHandler(btnNext_Click);
381 }
382 else
383 {
384 //后一页即偶数页
385 TypePage.LeftPage pp = PageObjectList[xx - 1] as TypePage.LeftPage;
386 Button btnPrevious = pp.getbtnPrevious();
387 btnPrevious.Click += new RoutedEventHandler(btnPrevious_Click);
388 }
389 }
390
391 //为Book设置数据内容
392 book.SetData(this);
393 }
394
395 //向页面列表中添加具体页面
396 private void AddPageToList(PageType pageType, string pathImage, string numPage, string numMaxiPage,
397 bool showBtnYesNo)
398 {
399 switch (pageType)
400 {
401 case PageType.right:
402 TypePage.RightPage pcd = new SilverlightClient.TypePage.RightPage();
403 pcd.setterimgPhoto(pathImage);
404 pcd.setterPageNumber(numPage, numMaxiPage);
405 pcd.setterDisplayBtnNext(showBtnYesNo);
406 PageObjectList.Add(pcd);
407 break;
408 case PageType.left:
409 TypePage.LeftPage pcg = new SilverlightClient.TypePage.LeftPage();
410 pcg.setterimgPhoto(pathImage);
411 pcg.setterPageNumber(numPage, numMaxiPage);
412 pcg.setterDisplayBtnPrevious(showBtnYesNo);
413 PageObjectList.Add(pcg);
414 break;
415 }
416 }
417
418 //“下一页”按钮事件触发处理
419 private void btnNext_Click(object sender, RoutedEventArgs e)
420 {
421 book.AnimateToNextPage(500);
422 }
423
424 //“上一页”按钮事件触发处理
425 private void btnPrevious_Click(object sender, RoutedEventArgs e)
426 {
427 book.AnimateToPreviousPage(500);
428 }
429
430 //从网络上下载页面
431 private void DownloadPages()
432 {
433 this.canvChanging.Visibility = Visibility.Visible;
434 this.uriResources = Application.Current.Host.Source.AbsoluteUri;
435 int index = uriResources.IndexOf("SilverlightClient.xap");
436 uriResources = uriResources.Substring(0, index);
437 this.changingProgressBar.Minimum = 0;
438 this.changingProgressBar.Maximum = maxiPageNum - 1;
439 string theResources = uriResources + fileMedia + "/" + headerPage + (pageDownload + 1).ToString("00") + ".jpg";
440 string theResourcesNum = headerPage + (pageDownload + 1).ToString("00") + ".jpg";
441 AsynchronouslyDownloadPage(theResources, theResourcesNum);
442 }
443
444 //异步下载页面
445 private void AsynchronouslyDownloadPage(string path, string num)
446 {
447 WebClient unWeb = new WebClient();
448 unWeb.DownloadStringCompleted += new DownloadStringCompletedEventHandler(unWeb_DownloadStringCompleted);
449 unWeb.DownloadStringAsync(new Uri(path));
450 this.changingText.Text = "正在下载 : " + num;
451 this.changingProgressBar.Value = this.pageDownload;
452 }
453
454 //异步下载页面完成事件触发处理
455 private void unWeb_DownloadStringCompleted(object sender, DownloadStringCompletedEventArgs e)
456 {
457 this.pageDownload++;
458 if (this.pageDownload < this.maxiPageNum)//持续不断下载页面直到所有页面都下完
459 {
460 string theResources = uriResources + fileMedia + "/" + headerPage + (pageDownload + 1).ToString("00") + ".jpg";
461 string theResourcesNum = headerPage + (pageDownload + 1).ToString("00") + ".jpg";
462 AsynchronouslyDownloadPage(theResources, theResourcesNum);
463 }
464 else
465 {
466 FillPagesList();
467 this.canvChanging.Visibility = Visibility.Collapsed;
468 this.canvasBook.Visibility = Visibility.Visible;
469 }
470 }
471
472 //强制声明接口
473 #region IDataProvider Members
474 public object GetItem(int index)
475 {
476 return PageObjectList[index];
477 }
478 public int GetCount()
479 {
480 return PageObjectList.Count;
481 }
482 #endregion
483
484 }
485}
486
4872)App.xaml.cs文件代码:
488
489Code System;
490using System.Collections.Generic;
491using System.Linq;
492using System.Net;
493using System.Windows;
494using System.Windows.Controls;
495using System.Windows.Documents;
496using System.Windows.Input;
497using System.Windows.Media;
498using System.Windows.Media.Animation;
499using System.Windows.Shapes;
500
501namespace SilverlightClient
502{
503 public partial class App : Application
504 {
505 public string gFileMedia = "";
506 public string gHeaderPage = "";
507 public int gPageNumber = 0;
508 public string gModeLocation = "";
509
510 public App()
511 {
512 this.Startup += this.Application_Startup;
513 this.Exit += this.Application_Exit;
514 this.UnhandledException += this.Application_UnhandledException;
515
516 InitializeComponent();
517 }
518
519 private void Application_Startup(object sender, StartupEventArgs e)
520 {
521 int paramOk = 0;
522 //从HTML中取出初始化数据
523 if (e.InitParams.ContainsKey("gFile"))
524 {
525 gFileMedia = e.InitParams["gFile"];
526 paramOk++;
527 }
528 if (e.InitParams.ContainsKey("gHeaderPage"))
529 {
530 gHeaderPage = e.InitParams["gHeaderPage"];
531 paramOk++;
532 }
533 if (e.InitParams.ContainsKey("gNum"))
534 {
535 string recup = e.InitParams["gNum"];
536 gPageNumber = int.Parse(recup);
537 paramOk++;
538 }
539 if (e.InitParams.ContainsKey("gLocation"))
540 {
541 gModeLocation = e.InitParams["gLocation"];
542 paramOk++;
543 }
544 if (paramOk == 4)
545 {
546 //初始化MainPage
547 MainPage maPage = new MainPage();
548 maPage.fileMedia = gFileMedia;
549 maPage.headerPage = gHeaderPage;
550 maPage.maxiPageNum = gPageNumber;
551 if (gModeLocation.CompareTo("local") == 0)
552 {
553 maPage.modeLocation = MainPage.Location.local;
554 }
555 if (gModeLocation.CompareTo("web") == 0)
556 {
557 maPage.modeLocation = MainPage.Location.web;
558 }
559 this.RootVisual = maPage;
560 }
561 }
562
563 private void Application_Exit(object sender, EventArgs e)
564 {
565
566 }
567
568 private void Application_UnhandledException(object sender, ApplicationUnhandledExceptionEventArgs e)
569 {
570 if (!System.Diagnostics.Debugger.IsAttached)
571 {
572 e.Handled = true;
573 Deployment.Current.Dispatcher.BeginInvoke(delegate { ReportErrorToDOM(e); });
574 }
575 }
576 private void ReportErrorToDOM(ApplicationUnhandledExceptionEventArgs e)
577 {
578 try
579 {
580 string errorMsg = e.ExceptionObject.Message + e.ExceptionObject.StackTrace;
581 errorMsg = errorMsg.Replace('"', '\'').Replace("\r\n", @"\n");
582
583 System.Windows.Browser.HtmlPage.Window.Eval("throw new Error(\"Unhandled Error in Silverlight Application " + errorMsg + "\");");
584 }
585 catch (Exception)
586 {
587 }
588 }
589 }
590}
591
592
5933)在SilverlightClientTestPage.aspx文件(位于工程FlipPage文件夹下)中,添加用绿色粗体标明的代码:
594
595<body>
596 <form id="form1" runat="server" style="height:100%">
597 <div id="silverlightControlHost">
598 <object data="data:application/x-silverlight-2," type="application/x-silverlight-2" width="100%" height="100%">
599 <param name="source" value="ClientBin/SilverlightClient.xap"/>
600 <param name="onError" value="onSilverlightError" />
601 <param name="background" value="white" />
602 <param name="minRuntimeVersion" value="3.0.40624.0" />
603 <param name="autoUpgrade" value="true" />
604 <!--设置Book初始化参数-->
605 <param name="initParams" value="gFile=mediaPictures, gHeaderPage=albumPictures, gNum=9, gLocation=web" />
606 <a href="http://go.microsoft.com/fwlink/?LinkID=149156&v=3.0.40624.0" style="text-decoration:none">
607 <img src="http://go.microsoft.com/fwlink/?LinkId=108181" alt="Get Microsoft Silverlight" style="border-style:none"/>
608 </a>
609 </object><iframe id="_sl_historyFrame" style="visibility:hidden;height:0px;width:0px;border:0px"></iframe></div>
610 </form>
611</body>
612
6135、最终效果图
614
615[项目源文件下载]
616
617
618
View Code
代理IP的高匿名,匿名和透明的区别
如果从隐藏使用代理用户的级别上划分,代理可以分为三种,即高度匿名代理、普通匿名代理和透明代理。
(1)高度匿名代理不改变客户机的请求,这样在服务器看来就像有个真正的客户浏览器在访问它,这时客户的真实IP是隐藏的,服务器端不会认为我们使用了代理。
(2)普通匿名代理能隐藏客户机的真实IP,但会改变我们的请求信息,服务器端有可能会认为我们使用了代理。不过使用此种代理时,虽然被访问的网站不能知道你的ip地址,但仍然可以知道你在使用代理,当然某些能够侦测ip的网页仍然可以查到你的ip。
(3)透明代理,它不但改变了我们的请求信息,还会传送真实的IP地址。
三者隐藏使用代理者身份的级别依次为高度匿名代理最隐蔽,其次是普通匿名代理,最差的是透明代理。
对winform中tabContorl隐藏tabPage的补充
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35 1前几天说到winfom中tabContorl隐藏tabPage的问题,总的来说达到了目的,但效果一般。
2今天在看msdn时候发现了一个tabPage的属性其实也可以实现这个效果。
3
4微软对tabContorl中的tabPage隐藏的实现方法也是在集合中删除,似乎只有这一个方法,所以我的方法也跟这个差不多。
5就是设置tabPage的parent属性为null
6原理很简单,如果tabPage的parent控件不存在,则tabPage也不存在。
7如果想让它显示就设置tabPage的parent为tabContorl控件就可以了。
8下面是主要代码
9
10
11 /// <summary>
12 /// 隐藏tabPage1
13 /// </summary>
14 /// <param name="sender"></param>
15 /// <param name="e"></param>
16 private void Form1_Load(object sender, EventArgs e)
17 {
18 this.tabPage1.Parent = null;
19 }
20 /// <summary>
21 /// 显示tabPage1
22 /// </summary>
23 /// <param name="sender"></param>
24 /// <param name="e"></param>
25 private void button1_Click(object sender, EventArgs e)
26 {
27 this.tabPage1.Parent = this.tabControl1;
28 }
29
30
31很简单吧?
32恩,不过问题跟上一次一样,顺序又不对了。
33但这个问题只存在于隐藏了前一个tabPage的情况。
34
35
View Code
分解Gif图像
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37 1对于一个Gif进行拆分,其实Image对象本身就支持,例如对于一个Gif文件拆分成Jpeg文件方式,可以按照如下的方式进行处理。
2
3 using System.Drawing.Drawing2D;
4
5 using System.Drawing.Imaging;
6
7
8 Image imgGif = Image.FromFile(@"d:\test.gif");
9
10 //Create a new FrameDimension object from this image
11
12 FrameDimension ImgFrmDim = new FrameDimension( imgGif.FrameDimensionsList[0] );
13
14
15
16 //Determine the number of frames in the image
17
18 //Note that all images contain at least 1 frame,
19
20 //but an animated GIF will contain more than 1 frame.
21
22 int nFrameCount = imgGif.GetFrameCount( ImgFrmDim );
23
24
25 // Save every frame into jpeg format
26
27 for( int i = 0; i < nFrameCount; i++ )
28
29 {
30
31 imgGif.SelectActiveFrame( ImgFrmDim, i );
32
33 imgGif.Save( string.Format( @"d:\Frame{0}.jpg", i ), ImageFormat.Jpeg );
34
35 }
36
37
View Code