C#上位機開發(二)
上一篇大致了解了一下單片機實際項目開發中上位機開發部分的內容已經VS下載與安裝,按照編程慣例,接下來就是“Hello,World!”
1、新建C#項目工程
首先選擇新建Windows窗體應用(.NET Framework),然後選擇項目保存位置,填寫項目名稱,這裏因為我們不需要用git進行進行版本管理,所以不用新建GIT存儲庫;
框架是指.net框架,4以及4以下的.NET框架可以在xp上運行,4以上可以在win7/8/10上運行,鑒於當前大多數操作系統都是win7或win10,選擇4.5版本。
2、窗體介紹及代碼分析
這裏我們雙擊窗體界面,這也是VS的特性,雙擊一個控件,就會進入對應代碼文件部分,這些代碼全由VS在生成項目時自動生成,下面進行詳細的解釋:
1 /*filename:Form1.cs*/ 2 //使用命名空間 3 using System; 4 using System.Collections.Generic; 5 using System.ComponentModel; 6 using System.Data; 7 using System.Drawing; 8 using System.Linq; 9 using System.Text; 10 using System.Windows.Forms; 11 12 //用戶項目工程自定義命名空間HelloWorld 13 namespace HelloWorld 14{ 15 //定義了一個名稱為Form1的公共類,並且在定義類的同時創建了一個這個類的對象,名為Form 16 //partial關鍵字 17 public partial class Form1 : Form 18 { 19 //與類同名的構造方法 20 public Form1() 21 { 22 InitializeComponent(); 23 } 24 //用戶自定義方法,窗體加載時由Form對象調用 25 private void Form1_Load(objectsender, EventArgs e) 26 { 27 } 28 } 29 }
命名空間(namespace):在C#中用命名空間將很多類的屬性及其方法進行封裝供調用,類似C語言中將變量和函數封裝成一個個.h文件,調用的時候只需要#include "filepath + filename"就可以使用,比如剛開始時用關鍵字using聲明了一些所需要的系統命名空間(line1-10);然後采用關鍵字namespace來自定義一個用戶工程所需的命名空間HelloWorld,在我們定義的這個命名空間裏就可以定義一些類和方法來進行下一步的實現;
類(class):C#是一門面向對象的編程語言,所以最基本的就是類和對象,對象的特征是具有屬性(C語言中稱為變量)和方法(C語言中稱為函數),然後我們定義一個類來描述這個對象的特征,註意:這個時候定義的類不是真實存在的,所以不會分配內存空間,當我們用所定義的這個類去創建一個類的對象,這個對象是真實存在的,它會占用內存空間,比如在這個工程中定義了一個名稱為Form1的公共類,並且在定義類的同時創建了一個這個類的對象,名為Form;
方法:前面已經說過,在面向對象編程中是沒有變量和函數的,所有的函數都被封裝在類中,屬於對象的方法,最基本的是類的構造方法,該方法與類名同名,在用類創建一個具體對象時自動調用,不可缺少,比如Form1( );另外一種是自己定義的用戶方法,比如該類中的Form1_Load()方法,就是在初始化窗口時,通過具體對象Form調用:Form.Form1_Load( );
訪問修飾符:用來控制類、屬性、方法的訪問權限,常用有5個,默認私有,不能被外部訪問;
私有的private,公共的public,受保護的protected,內部的internal,受保護內部的protect internal;
這裏有一個重點,在定義Form1類的時候含有一個關鍵字partial,這裏就不得不說C#語言設計一個重要的特性了,能作為大多數人開發上位機的首選,C#有一個特性就是設計的時候界面與後臺分離,但是類名相同,首先看一下工程文件結構:
可以看到,Form1.cs文件下面包含了另一個Form1.Designer.cs文件,再打開Form1.Designer.cs這個文件,是不是很驚奇,和前面一模一樣,再次定義了一個命名空間HelloWorld和Form1類,這個部分類中定義了我們使用的控件、事件委托以及如Dispose方法等。因為這裏面的代碼都是自動生成的,因此設計成了一個部分類。最關鍵的一點,這裏類也是用partial關鍵字修飾的,可以看到,Partial是局部類型的意思,允許我們將一個類、結構或接口分成幾個部分,分別實現在幾個不同的.cs文件中,用partial定義的類可以在多個地方被定義,最後C#編譯器編譯時會將這些類當作一個類來處理;
1 /*@filename:Form1.Designer.cs */ 2 3 namespace HelloWorld 4 { 5 partial class Form1 6 { 7 /// <summary> 8 /// 必需的設計器變量。 9 /// </summary> 10 private System.ComponentModel.IContainer components = null; 11 12 /// <summary> 13 /// 清理所有正在使用的資源。 14 /// </summary> 15 /// <param name="disposing">如果應釋放托管資源,為 true;否則為 false。</param> 16 protected override void Dispose(bool disposing) 17 { 18 if (disposing && (components != null)) 19 { 20 components.Dispose(); 21 } 22 base.Dispose(disposing); 23 } 24 25 #region Windows 窗體設計器生成的代碼 26 27 /// <summary> 28 /// 設計器支持所需的方法 - 不要修改 29 /// 使用代碼編輯器修改此方法的內容。 30 /// </summary> 31 private void InitializeComponent() 32 { 33 this.SuspendLayout(); 34 // 35 // Form1 36 // 37 this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 12F); 38 this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font; 39 this.ClientSize = new System.Drawing.Size(418, 331); 40 this.Name = "Form1"; 41 this.Text = "Form1"; 42 this.Load += new System.EventHandler(this.Form1_Load); 43 this.ResumeLayout(false); 44 45 } 46 #endregion 47 } 48 }
Main: 一切程序都有入口主函數main,C#也是如此,在Program.cs文件中定義了Program類,該類中擁有主函數main( ), 在main函數中,第三行代碼是一切的開始,調用Form1類的構造函數,創建一個Form對象,一切由此開始,代碼如下:
1 /* @filename: Program.cs */ 2 using System; 3 using System.Collections.Generic; 4 using System.Linq; 5 using System.Windows.Forms; 6 7 namespace HelloWorld 8 { 9 static class Program 10 { 11 /// <summary> 12 /// 應用程序的主入口點。 13 /// </summary> 14 [STAThread] 15 static void Main() 16 { 17 Application.EnableVisualStyles(); 18 Application.SetCompatibleTextRenderingDefault(false); 19 Application.Run(new Form1()); //調用Form1類的構造函數,創建一個Form對象,一切由此開始 20 } 21 } 22 }
再來解釋一下最後三個文件:第一個文件主要是應用程序發布時的一些屬性設置,版本號,屬性,版權之類的,其余兩個文件是工具自動生成的一些設置文件,不再過多贅述;
/* @filename:Assemblylnfo.cs*/ using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; // 有關程序集的一般信息由以下 // 控制。更改這些特性值可修改 // 與程序集關聯的信息。 [assembly: AssemblyTitle("HelloWorld")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] [assembly: AssemblyCompany("")] [assembly: AssemblyProduct("HelloWorld")] [assembly: AssemblyCopyright("Copyright ? 2018")] [assembly: AssemblyTrademark("")] [assembly: AssemblyCulture("")] // 將 ComVisible 設置為 false 會使此程序集中的類型 //對 COM 組件不可見。如果需要從 COM 訪問此程序集中的類型 //請將此類型的 ComVisible 特性設置為 true。 [assembly: ComVisible(false)] // 如果此項目向 COM 公開,則下列 GUID 用於類型庫的 ID [assembly: Guid("094ac56a-7a59-4f32-a2eb-857135be4d2c")] // 程序集的版本信息由下列四個值組成: // // 主版本 // 次版本 // 生成號 // 修訂號 // // 可以指定所有值,也可以使用以下所示的 "*" 預置版本號和修訂號 // 方法是按如下所示使用“*”: : // [assembly: AssemblyVersion("1.0.*")] [assembly: AssemblyVersion("1.0.0.0")] [assembly: AssemblyFileVersion("1.0.0.0")]
3、Hello,World
下面就正式開始C#程序的設計,首先是界面的實現,可以隨意從控件工具箱中拖放控件到窗體中,這裏我拖動兩個Button和一個TextBox,並在右邊設置框中修改每個控價的屬性,界面如圖:
這個時候如果查看Form1.cs文件,會發現和之前一樣,這裏就需要介紹另外幾個開發GUI界面的知識點了,首先,我們想要實現的功能是:當按下Send按鈕時,文本框顯示^_^Hello,World^_^字樣,當按下Clear按鈕時,文本框清空;這屬於人機交互,一般人機交互的處理方式有兩種,第一種是查詢處理方式,比如在DOS系統下、Linux系統等命令行下的程序設計,第二種是事件處理機制,有了很多的優越性,由傳統的查詢法耗費CPU一直在檢測,變成了事件處理機制下的主動提醒告知,大幅度減輕CPU資源浪費,在事件處理機制中有以下幾個概念:
事件源(EventSource):描述人機交互中事件的來源,通常是一些控件;
事件(ActionEvent):事件源產生的交互內容,比如按下按鈕;
事件處理:這部分也在C++中被叫做回調函數,放事件發生時用來處理事件;
註:這部分在單片機中也是如此,中斷源產生中斷,然後進入中斷服務函數進行響應;
清楚了這幾個概念後,就來實現我們想要的功能,按下按鈕是一個事件,那麽,如何編寫或者在哪編寫這個事件的事件處理函數呢?在VS中很方便,只需要雙擊這個控件,VS就會自動將該控件的事件處理函數添加進Form1.cs文件,此處我先雙擊“Send”按鈕,可以看到VS自動添加進了 private void button1_Click(object sender, EventArgs e) 這個方法,然後在裏面編寫代碼,讓文本框顯示:這裏所有的控件都是一個具體的對象,我們要通過這些對象設置其屬性或者調用其方法;同樣的道理,雙擊Clear按鈕,添加文本框清空代碼,完整代碼如下:
//用戶項目工程自定義命名空間HelloWorld namespace HelloWorld { //定義了一個名稱為Form1的公共類,並且在定義類的同時創建了一個這個類的對象,名為Form //partial關鍵字 public partial class Form1 : Form { //與類同名的構造方法 public Form1() { InitializeComponent(); } private void Form1_Load(object sender, EventArgs e) { } private void button1_Click(object sender, EventArgs e) { //按下Send按鈕 textBox1.Text = "^_^Hello,World^_^"; //文本框顯示 } private void button2_Click(object sender, EventArgs e) { //按下Clear按鈕 textBox1.Text = ""; //文本框清空 } } }
至此,大功告成,第一個應用程序創建成功,點擊啟動按鈕看下效果:
C#上位機開發(二)