C#版簡易RSS閱讀器。由VB版修改完成,感謝aowind的技術支持! 源代碼: using System; using System.Drawing; using System.Collections; using System.ComponentModel; using System.Windows.Forms; using System.Data; using System.Xml; using System.IO; using System.Threading; namespace YuLRSSReader { /// <summary> /// Form1 的摘要說明。 /// </summary> public class Form1 : System.Windows.Forms.Form { private System.Windows.Forms.Label label1; private System.Windows.Forms.Label label2; private System.Windows.Forms.Label label3; private System.Windows.Forms.TextBox textBox1; private System.Windows.Forms.Button button1; private System.Windows.Forms.Label BlogName; private System.Windows.Forms.Label BlogDescription; private System.Windows.Forms.ListBox listBox1; private System.Windows.Forms.StatusBar statusBar1; private AxSHDocVw.AxWebBrowser axWebBrowser1; /// <summary> /// 必需的設計器變量。 /// </summary> private System.ComponentModel.Container components = null; public Form1() { // // Windows 窗體設計器支持所必需的 // InitializeComponent(); // // TODO: 在 InitializeComponent 調用後添加任何構造函數代碼 // } /// <summary> /// 清理全部正在使用的資源。 /// </summary> protected override void Dispose( bool disposing ) { if( disposing ) { if (components != null) { components.Dispose(); } } base.Dispose( disposing ); } #region Windows 窗體設計器生成的代碼 /// <summary> /// 設計器支持所需的方法 - 不要使用代碼編輯器修改 /// 此方法的內容。 /// </summary> private void InitializeComponent() { System.Resources.ResourceManager resources = new System.Resources.ResourceManager(typeof(Form1)); this.label1 = new System.Windows.Forms.Label(); this.label2 = new System.Windows.Forms.Label(); this.label3 = new System.Windows.Forms.Label(); this.textBox1 = new System.Windows.Forms.TextBox(); this.button1 = new System.Windows.Forms.Button(); this.BlogName = new System.Windows.Forms.Label(); this.BlogDescription = new System.Windows.Forms.Label(); this.listBox1 = new System.Windows.Forms.ListBox(); this.statusBar1 = new System.Windows.Forms.StatusBar(); this.axWebBrowser1 = new AxSHDocVw.AxWebBrowser(); ((System.ComponentModel.ISupportInitialize)(this.axWebBrowser1)).BeginInit(); this.SuspendLayout(); // // label1 // this.label1.Location = new System.Drawing.Point(8, 8); this.label1.Name = "label1"; this.label1.Size = new System.Drawing.Size(64, 23); this.label1.TabIndex = 0; this.label1.Text = "RSS地址:"; // // label2 // this.label2.Location = new System.Drawing.Point(8, 40); this.label2.Name = "label2"; this.label2.Size = new System.Drawing.Size(64, 23); this.label2.TabIndex = 1; this.label2.Text = "BLOG:"; // // label3 // this.label3.Location = new System.Drawing.Point(8, 72); this.label3.Name = "label3"; this.label3.Size = new System.Drawing.Size(64, 23); this.label3.TabIndex = 2; this.label3.Text = "描述:"; // // textBox1 // this.textBox1.Location = new System.Drawing.Point(72, 8); this.textBox1.Name = "textBox1"; this.textBox1.Size = new System.Drawing.Size(392, 21); this.textBox1.TabIndex = 3; this.textBox1.Text = ""; // // button1 // this.button1.Location = new System.Drawing.Point(472, 16); this.button1.Name = "button1"; this.button1.Size = new System.Drawing.Size(80, 64); this.button1.TabIndex = 4; this.button1.Text = "讀取"; this.button1.Click += new System.EventHandler(this.button1_Click); // // BlogName // this.BlogName.Location = new System.Drawing.Point(72, 40); this.BlogName.Name = "BlogName"; this.BlogName.Size = new System.Drawing.Size(392, 23); this.BlogName.TabIndex = 5; // // BlogDescription // this.BlogDescription.Location = new System.Drawing.Point(72, 72); this.BlogDescription.Name = "BlogDescription"; this.BlogDescription.Size = new System.Drawing.Size(392, 23); this.BlogDescription.TabIndex = 6; // // listBox1 // this.listBox1.ItemHeight = 12; this.listBox1.Location = new System.Drawing.Point(0, 104); this.listBox1.Name = "listBox1"; this.listBox1.Size = new System.Drawing.Size(560, 112); this.listBox1.TabIndex = 7; this.listBox1.SelectedIndexChanged += new System.EventHandler(this.listBox1_SelectedIndexChanged); // // statusBar1 // this.statusBar1.Location = new System.Drawing.Point(0, 591); this.statusBar1.Name = "statusBar1"; this.statusBar1.Size = new System.Drawing.Size(562, 22); this.statusBar1.TabIndex = 8; // // axWebBrowser1 // this.axWebBrowser1.Dock = System.Windows.Forms.DockStyle.Bottom; this.axWebBrowser1.Enabled = true; this.axWebBrowser1.Location = new System.Drawing.Point(0, 223); this.axWebBrowser1.OcxState = ((System.Windows.Forms.AxHost.State)(resources.GetObject("axWebBrowser1.OcxState"))); this.axWebBrowser1.Size = new System.Drawing.Size(562, 368); this.axWebBrowser1.TabIndex = 9; // // Form1 // this.AutoScaleBaseSize = new System.Drawing.Size(6, 14); this.ClientSize = new System.Drawing.Size(562, 613); this.Controls.Add(this.axWebBrowser1); this.Controls.Add(this.statusBar1); this.Controls.Add(this.listBox1); this.Controls.Add(this.BlogDescription); this.Controls.Add(this.BlogName); this.Controls.Add(this.button1); this.Controls.Add(this.textBox1); this.Controls.Add(this.label3); this.Controls.Add(this.label2); this.Controls.Add(this.label1); this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedSingle; this.Name = "Form1"; this.StartPosition = System.Windows.Forms.FormStartPosition.CenterScreen; this.Text = "YuL\'s RSS Reader"; this.Load += new System.EventHandler(this.Form1_Load); ((System.ComponentModel.ISupportInitialize)(this.axWebBrowser1)).EndInit(); this.ResumeLayout(false); } #endregion /// <summary> /// 應用程序的主入口點。 /// </summary> [STAThread] static void Main() { Application.Run(new Form1()); } private void Form1_Load(object sender, System.EventArgs e) { this.axWebBrowser1.Width = this.Width; this.statusBar1.Text = "就緒"; } private Thread thread; private string fileFullPath = Application.StartupPath + "~tempdoc.xml"; private void LoadRss() { this.statusBar1.Text = "正在讀取" + this.textBox1.Text + "並校驗…"; this.LoadXml2Coach(this.textBox1.Text); this.statusBar1.Text = "正在讀取BLOG相關信息…"; this.LoadTitle(); this.statusBar1.Text = "正在讀取RSS內容信息…"; this.LoadItem(); this.statusBar1.Text = "完成"; } private void LoadXml2Coach(String url) { XmlDocument doc = new XmlDocument(); doc.Load(url); doc.Save(this.fileFullPath); } private void LoadTitle() { XmlDocument doc = new XmlDocument(); doc.Load(this.fileFullPath); XmlNodeList nodeList; nodeList = doc.SelectNodes("/rss/channel"); this.BlogName.Text = nodeList[0].SelectSingleNode("title").InnerText; this.BlogDescription.Text = nodeList[0].SelectSingleNode("description").InnerText; } private void LoadItem() { XmlDocument doc = new XmlDocument(); doc.Load(this.fileFullPath); XmlNodeList nodeList; nodeList = doc.SelectNodes("/rss/channel/item"); this.listBox1.Items.Clear(); XmlNamespaceManager ns = new XmlNamespaceManager(doc.NameTable); ns.AddNamespace("dc","http://purl.org/dc/elements/1.1/"); try { for(int i = 0; i < nodeList.Count; i++) { this.listBox1.Items.Add("[" + nodeList[i].SelectSingleNode("dc:creator",ns).InnerText + "]" + nodeList[i].SelectSingleNode("title").InnerText); } } catch(Exception ex) { MessageBox.Show(ex.ToString()); } } private void LoadHtml() { XmlDocument doc = new XmlDocument(); doc.Load(this.fileFullPath); XmlNodeList nodeList; nodeList = doc.SelectNodes("/rss/channel/item"); bool flag; string temp = ""; string content = ""; this.statusBar1.Text = "正在讀取文章內容…"; XmlNamespaceManager ns = new XmlNamespaceManager(doc.NameTable); ns.AddNamespace("dc","http://purl.org/dc/elements/1.1/"); for(int i = 0; i < nodeList.Count; i++) { temp = "[" + nodeList[i].SelectSingleNode("dc:creator",ns).InnerText + "]" + nodeList[i].SelectSingleNode("title").InnerText; if(this.listBox1.SelectedItem.ToString().Equals(temp)) { content = content + "<html><head><meta http-equiv='content-type' content='text/html;charset=UTF-8'></head><body>"; content = content + "<table width='100%' height='80' bgcolor='#eeeeee'><tr><td><b>標題:</b><a href='"; content = content + nodeList[i].SelectSingleNode("link").InnerText; content = content + "' target='_blank'>"; content = content + nodeList[i].SelectSingleNode("title").InnerText; content = content + "</a><br><b>做者:</b>"; content = content + nodeList[i].SelectSingleNode("dc:creator",ns).InnerText; content = content + "</tb></tr></table>"; content = content + nodeList[i].SelectSingleNode("description").InnerText; content = content + "</body></html>"; flag = SaveTextFile(Application.StartupPath + "~temp.html", content); object flags = 0; object targetFrame = String.Empty; object postData = String.Empty; object headers = String.Empty; this.axWebBrowser1.Navigate(Application.StartupPath + "~temp.html", ref flags, ref targetFrame, ref postData, ref headers); break; } } this.statusBar1.Text = "完成"; } private bool SaveTextFile(string filePath, string fileContent) { System.IO.StreamWriter sw = null; try { sw = new StreamWriter(filePath,false); sw.Write(fileContent); return true; } catch(Exception ex) { MessageBox.Show(ex.ToString()); return false; } finally { if(sw != null) sw.Close(); } } private void button1_Click(object sender, System.EventArgs e) { try { this.thread = new Thread(new ThreadStart(this.LoadRss)); this.thread.Start(); } catch(Exception ex) { MessageBox.Show(ex.ToString()); } } private void listBox1_SelectedIndexChanged(object sender, System.EventArgs e) { try { this.thread = new Thread(new ThreadStart(this.LoadHtml)); this.thread.Start(); } catch(Exception ex) { MessageBox.Show(ex.ToString()); } } } }
C#實現斷點續傳詳細剖析html
· 摘要:這裏介紹C#實現斷點續傳,在瞭解HTTP斷點續傳的原理以前,讓咱們先來了解一下HTTP協議,HTTP協議是一種基於tcp的簡單協議,分爲請求和回覆兩種。 · C#語言仍是比較常見的東西,這裏咱們主要介紹C#實現斷點續傳,包括介紹HTTP協議是一種基於tcp的簡單協議等方面。 在瞭解HTTP斷點續傳的原理以前,讓咱們先來了解一下HTTP協議,HTTP協議是一種基於tcp的簡單協議,分爲請求和回覆兩種。請求協議是由客戶機(瀏覽器)向服務器(WEB SERVER)提交請求時發送報文的協議。回覆協議是由服務器(web server),向客戶機(瀏覽器)回覆報文時的協議。請求和回覆協議都由頭和體組成。頭和體之間以一行空行爲分隔。 如下是一個請求報文與相應的回覆報文的例子: 1. GET /image/index_r4_c1.jpg HTTP/1.1 2. Accept: */* 3. Referer: http://192.168.3.120:8080 4. Accept-Language: zh-cn 5. Accept-Encoding: gzip, deflate 6. User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0; .NET CLR 1.0.3705) 7. Host: 192.168.3.120:8080 8. Connection: Keep-Alive 9. 10. HTTP/1.1 200 OK 11. Server: Microsoft-IIS/5.0 12. Date: Tue, 24 Jun 2003 05:39:40 GMT 13. Content-Type: image/jpeg 14. Accept-Ranges: bytes 15. Last-Modified: Thu, 23 May 2002 03:05:40 GMT 16. ETag: "bec48eb862c21:934" 17. Content-Length: 2827 下面咱們就來講說C#實現斷點續傳,顧名思義,斷點續傳就是在上一次下載時斷開的位置開始繼續下載。 在HTTP協議中,能夠在請求報文頭中加入Range段,來表示客戶機但願從何處繼續下載。 好比說從第1024字節開始下載,請求報文以下: 1. GET /image/index_r4_c1.jpg HTTP/1.1 2. Accept: */* 3. Referer: http://192.168.3.120:8080 4. Accept-Language: zh-cn 5. Accept-Encoding: gzip, deflate 6. User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0; .NET CLR 1.0.3705) 7. Host: 192.168.3.120:8080 8. Range:bytes=1024- 9. Connection: Keep-Alive .NET中的相關類,明白了上面的原理,那麼,咱們來看看.NET FRAMEWORK中爲咱們提供了哪些類能夠來作這些事。完成HTTP請求System.Net.HttpWebRequest HttpWebRequest 類對 WebRequest 中定義的屬性和方法提供支持,也對使用戶可以直接與使用 HTTP 的服務器交互的附加屬性和方法提供支持。 HttpWebRequest 將發送到 Internet 資源的公共 HTTP 標頭值公開爲屬性,由方法或系統設置。下表包含完整列表。能夠將 Headers 屬性中的其餘標頭設置爲名稱/值對。可是注意,某些公共標頭被視爲受限制的,它們或者直接由 API公開,或者受到系統保護,不能被更改。Range也屬於被保護之列,不過,.NET爲開發者提供了更方便的操做,就是 AddRange方法,向請求添加從請求數據的開始處或結束處的特定範圍的字節範圍標頭,以上介紹C#實現斷點續傳。
C#製做新聞閱讀器node
1、弄清結構再動手 要想輕鬆的抽取RSS信息,天然先要了解它的結構,所謂「知己知彼,百戰不殆」嘛。 1、RSS的結構 咱們先打開百度新聞一個RSS連接,若是你再多打開幾個別的網站的RSS連接,會發現他們都有大體相同的結構。而咱們在揭祕RSS(上)中爲你們講解的其實就是編成實現這樣的一個XML文件。 爲了可以方便地對這樣的XML文檔進行處理,在本文裏,咱們使用C#做爲開發的語言。 分析整個RSS連接後,咱們知道RSS大體的結構入圖1。 2、抽取的原理 知道告終構,咱們還要知道結構中各部分的含義。在圖1中RSS節點表示當前是一個RSS文件,它由一個CHANNEL節點及其子節點組成,其中一些子節點提供關於頻道自己的信息,好比title表示頻道的名稱(「百度互聯網新聞」)。 CHANNEL節點又包含多個ITEM子節點,而ITEM節點就是程序須要處理的部分,由於它對應着每條實際的新聞項信息, 每一個ITEM節點又經過其子節點提供關於這條新聞的詳細信息,好比title表示新聞的標題(「微軟IM稱王」),link對應新聞實際的連接。 RSS具體規範可查看http://blogs.law.harvard.edu/tech/rss 知道了這些後,要編程就不困難啦。咱們只需提取並顯示出CHANNEL和ITEM下的各條信息就能夠了。如今來看看具體的實現方法吧。 二.作個程序讀新聞 對RSS有必定了解後,咱們開始編寫程序。先仍是須要一個最簡單的界面。新建一個Win Form 工程,在Form上放置一個Label,一個文本框txtURL用來輸入RSS連接(就是各網站RSS連接中包含的地址),一個按鈕bnRead用來執行讀取新聞, 一個TreeView樹形控件treeRSS顯示讀出的新聞項。 1、定義裝載結構 根據上面分析的RSS結構,咱們首先來創建一個rss類,用它來裝載RSS連接中CHANNEL和ITEM的各條信息。代碼以下: public class rss { public struct Channel { public string Title; public Hashtable Items; } public struct Item { public string Title; public string Description; public string Link; } } Channel結構將存儲CHANNEL節點包含的全部子節點信息,其中Items成員字段是一個Hashtable集合,程序會將Item結構做爲對象加入集合,用來存儲Channel下的全部Item節點。這裏我只讀取了有限的幾個節點,讀者能夠根據實際須要擴展整個結構定義。 2、從RSS連接中獲取新聞信息 如今咱們就能夠開始編寫讀取函數,將抽取出的RSS信息放入上面設計好的結構中。 C#提供了專門的類來訪問XML, 使咱們可以輕鬆地讀出RSS的內容。代碼以下: XmlTextReader Reader = new XmlTextReader(URL); XmlValidatingReader Valid = new XmlValidatingReader(Reader); Valid.ValidationType = ValidationType.None; XmlDocument xmlDoc= new XmlDocument(); xmlDoc.Load(Reader); 使用XmlDocument類將txtURL中輸入的RSS連接加載後,首先經過FoundChildNode函數,找到Channel節點。 private XmlNode FoundChildNode(XmlNode Node,string Name) { XmlNode childlNode = null; for (int i=0;i < Node.ChildNodes.Count;i++) { if ( Node.ChildNodes[i].Name == Name && Node.ChildNodes[i].ChildNodes.Count > 0 ) { childlNode = Node.ChildNodes[i]; return childlNode; } } return childlNode; } XmlNode rssNode = FoundChildNode(xmlDoc,"rss"); XmlNode channelNode = FoundChildNode(rssNode,"channel"); 而後咱們就能夠遍歷它的子節點,根據子節點的Name屬性,讀取咱們須要的信息。 rss.Channel channel=new rss.Channel(); channel.Items=new Hashtable(); { switch ( channelNode.ChildNodes[i].Name ) { case "title": { channel.Title = channelNode.ChildNodes[i].InnerText; break; } case "item": { rss.Item item=this.getRssItem(channelNode.ChildNodes[i]); channel.Items.Add(channel.Items.Count,item ); break; } } } 若是發現是item子節點,就調用getRssItem函數,一樣經過遍歷子節點的方法,將其子節點內容填入Item結構中,而後再添加到Channel結構的Items集合中。由於本程序並不關心添加到集合的鍵值,只須要它是不重複的值,因此我傳入了Count屬性。 3.將讀出的信息顯示在程序中 將RSS內容讀出後,就須要把信息展現給用戶了。咱們這裏用的是基本的TreeView方法,經過遍歷Channel結構的Items集合,將其標題添加到TreeView中。 private void ViewRss(rss.Channel channel) { treeRss.BeginUpdate(); treeRss.Nodes.Clear(); TreeNode channelNode=treeRss.Nodes.Add(channel.Title ); channelNode.Tag=""; for (int i=0;i <channel.Items.Count ;i++) { rss.Item item=(rss.Item)channel.Items[i]; TreeNode itemNode=channelNode.Nodes.Add(item.Title ); itemNode.Tag=item.Link; } treeRss.ExpandAll(); treeRss.EndUpdate(); } 同時咱們還能夠設置TreeView的每一個子節點的Tag屬性爲它對應的連接。以便當選中子節點時就能夠經過讀取Tag屬性訪問具體的信息。 private void treeRss_AfterSelect(object sender, System.Windows.Forms.TreeViewEventArgs e) { TreeNode itemNode=e.Node ; string URL=itemNode.Tag.ToString(); if (URL.Length!=0) System.Diagnostics.Process.Start( URL); } 程序運行效果如圖2。 三.小結 怎麼樣,一個簡單的RSS新聞閱讀器就按前面所說輕鬆完成了,容易吧。雖然它還有不少不足,但若是你們經過這個例子學會了抽取RSS連接信息的基本方法,那就足夠了!
C#製做源閱讀器web
1 需求分析 這是一個rss源閱讀器,可以讀取xml文件以實現連接網頁的目的。其主要功能是經過添加url來獲取種子並閱讀網頁,使得瀏覽網頁更加輕鬆,項目中主要包含了增長、刪除、修改頻道的功能。其界面以下: 2 概要設計 設計思路:主窗體中分爲節點跟內容顯示兩個窗口(即左邊爲節點,右邊爲文章詳細內容),並從主窗體的.cs文件中鏈接到add.cs跟del.cs窗口以實現整個RSS閱讀器的完整功能(即包括增刪改節點的功能)。 關鍵點:如何將種子讀取並加載上去、如何下載下載.xml文檔並解析種子、如何實現多線程任務管理、如何將添加的頻道添加到txt文檔中並在主窗口顯示、如何修改和刪除節點。 框架設計: 主要類設計: 1、在讀取文章模塊: Article.cs類中:有title跟url的封裝屬性,用來體現文章的標題跟url路徑。 RssFeed.cs類是初始化了title、url跟destination,到網上下載rss源的種子文檔,並解析了已有的.xml文件,以此來獲取每一個節點。 FeedManager.cs類是讀取feeds.txt種子文件並加載文件信息使其顯示在webBrowser中 Form1.cs中實現了多線程任務管理,也將feedList中種子信息傳到設計窗口顯示出來。 2、增長頻道模塊: 添加了一個add.cs窗口,在此窗口中實現了添加文章的title、url跟destination三項並將之保存到feeds.txt文檔中。 3、刪除/修改頻道模塊: 添加了一個del.cs窗口,在此窗口中用了一個richTextBox來顯示打開後的feeds.txt文檔的內容,並在其中進行文檔的編輯(即修改或刪除節點),並用按鈕進行保存。 3 知識點解析 1、封裝一個文件: public string Title { get { return title; } set { title = value; } } 2、加載信息:(讀取種子文件並將文件加載到feedList中去) string filepath = path + "\\feeds.txt"; StreamReader sr = new StreamReader(filepath,Encoding.Default); string line = ""; while ((line = sr.ReadLine()) != null) { RssFeed rf = new RssFeed(); rf.FeedName = line; rf.Url = sr.ReadLine(); rf.Description = sr.ReadLine(); FeedList.Add(rf); } 3、網上下載rss種子文件並解析xml文件 WebClient wc = new WebClient(); wc.DownloadFile(this.url, "temp.xml"); XmlDocument myXml = new XmlDocument(); myXml.Load("temp.xml"); XmlNode root = myXml.DocumentElement; XmlNode channel = root.ChildNodes[0]; 4、獲取節點(先判斷是否存在節點) if (node.Name.Equals("item")) { Article a = new Article(); a.Title = node.ChildNodes[0].InnerText; a.Url = node.ChildNodes[1].InnerText; Articles.Add(a); } 5、讀取種子並在主窗體添加節點 for (int i = 0; i < list.Count; ++i) { TreeNode feedNode = new TreeNode(list[i].FeedName); feedNode.Tag = list[i]; rootNode.Nodes.Add(feedNode); } tvFeeds.Nodes.Add(rootNode); 6、線程的管理: 啓動線程,並將參數傳遞到線程入口函數: Thread thread = new Thread(new ParameterizedThreadStart(RunThread)); thread.Start(node); 事件的處理函數: TreeNode node = e.Node; this.BeginInvoke(uad, new object[] { node }); 7、添加頻道的窗口中觸發「添加」按鈕的事件(將本身添加的title、url、destination添加到已有的feeds.txt文檔中): string filepath = Application.StartupPath + "\\feeds.txt"; //FileStream fs = File.Open("feeds.txt", FileMode.Create, FileAccess.Write); StreamWriter sw = new StreamWriter(filepath,true, Encoding.GetEncoding("gb2312")); sw.WriteLine(textBox1.Text); sw.WriteLine(textBox2.Text); sw.WriteLine(textBox3.Text); sw.Close(); MessageBox.Show("添加成功!"); 8、用流和文件來讀取文檔並進行修改後保存操做: 打開feeds.txt文檔並在richTextBox中顯示文檔內容(觸發「打開」按鈕事件): OpenFileDialog feeds = new OpenFileDialog(); if (feeds.ShowDialog(this) == System.Windows.Forms.DialogResult.OK) { string file = feeds.FileName; richTextBox1.Text = System.IO.File.ReadAllText(file, Encoding.Default); } 將richTextBox中修改過的文件覆蓋保存到feeds.txt中,(「保存」按鈕事件): richTextBox1.SaveFile(Application.StartupPath + "\\feeds.txt", RichTextBoxStreamType.PlainText);