PropertyGrid是一個特別的大元件,[Category][Description][DisplayName]這些都是配合的特殊語法,他有一些限制條件,就是必須放在Member的上一行。搭配.NET3.5的封裝寫法,可以很簡單的撰寫,如下例
[Category( "Font" ), Description( "Font Size" )]
public int FontSize { get; set; }
但是,如果你需要在 set 或 get 函式做一些判斷,那就不能用.NET3.5的簡易寫法了,你必須定義一個 Private 的 Member,然後透過封裝的 get, set 將 Member給外面使用,但,這時候就要注意,[Category][Description][DisplayName]這一行,必須要寫在 private 跟 public 的中間囉,否則你會得到這樣的訊息:
屬性 'xxxxxxxx' 在此宣告型別上無效。它只在 'class, method, property, indexer, event' 宣告上有效
---錯誤寫法---
[Category( "Font" ), Description( "Size of the font" ), DisplayName( "Font Size" ]
[Editor( typeof( System.Windows.Forms.Design.FolderNameEditor ), typeof( System.Drawing.Design.UITypeEditor ) )]
private int _FontSize;
public int FontSize
{
get
{
return _FontSize ;
}
set
{
if ( 0 < _FontSize )
{
_FontSize = value
}
}
}
---正確寫法---
private int _FontSize;
[Category( "Font" ), Description( "Size of the font" ), DisplayName( "Font Size" ]
[Editor( typeof( System.Windows.Forms.Design.FolderNameEditor ), typeof( System.Drawing.Design.UITypeEditor ) )]
public int FontSize
{
get
{
return _FontSize ;
}
set
{
if ( 0 < _FontSize )
{
_FontSize = value
}
}
}
我喜歡設計,我喜歡創造,我喜歡美 不論軟體設計,不論介面設計,不論產品規劃設計,我都很有興趣 一直希望能能用這份專長,好好發揮在職場上。讓我做的快樂。 不論寫程式,或是做美工,我都很喜歡,希望我可以有機會雙線。兩種都很擅長。
2012年1月31日 星期二
2012年1月12日 星期四
C# Dictionary的用法,以及查字典的用途
什麼是Dictionary?他是個很簡單的東西,概念跟字典有點類似沒錯,如果我有10組鑰匙,跟10組物品,且滿足兩個條件,一、每個鑰匙不重複,二、每個鑰匙配一個物品。(物品可以長的一樣,比方第一個物品跟第六個物品都是一樣的杯子,只要能夠不會讓鑰匙沒有搭配的物品,或兩把鑰匙搭配到同一個物品就行了。)那接下來,你問Dictionary,某一把鑰匙,他就會告訴你對應的物品是什麼。我們看一下範例程式片段:
Dictionary<string, string> MyDic = new Dictionary<string, string>( );
// 建立字典
private void CreateDictionary( )
{
MyDic.Add( "Name", "Jack" );
MyDic.Add( "Blog", "Jack’s Blog" );
MyDic.Add( "Group", "KTV Group" );
}
// 查字典
private String FindInDictionary( String FindMe )
{
if ( true == ( MyDic.ContainsKey( FindMe ) ) )
{
return MyDic[ FindMe ];
}
else
{
return "Not Found";
}
}
// 巡整個字典
private void ShowAllInDictionary( )
{
foreach ( var OneItem in MyDic )
{
Console.WriteLine( "Key = " + OneItem.Key + ", Value = " + OneItem.Value );
}
}
除了上面那種先宣告再Add的方式之外,也可以用底下的方式來直接宣告並產生內容
Dictionary<string, string> dctNewWay =
new Dictionary<string, string>()
{
{"Key1", "AAAA"}, {"Key2", "BBBB"},
{"Key3", "CCCC"}, {"Key4", "DDDD"}
};
另外,值得一提的是,Key跟Value並不限定只能用String,什麼型別都可以,所以你也可以把Class塞到Value,然後其中一個屬性拿出來當作Key,就可以方便的確認有沒有重複的Key,不用塞到SQL才知道。
2012年1月11日 星期三
WPF的BitmapImage佔用資源的處理方式
我們經常使用Image控制項來載入圖片,簡單的作法,直接在IDE開發環境中,在Image的屬性頁面設定Source屬性即可。但,我們有時候會需要將圖檔動態的讀入,怎麼寫?可想到程式碼如下:
// 開檔
String FilePath = @"C:\temp\001 (1).jpg";
FileStream FStream = new FileStream( FilePath, FileMode.Open );
// 將資料讀入 BitmapImage 變成圖檔資源
BitmapImage BitMap = new BitmapImage( );
BitMap.BeginInit( );
BitMap.StreamSource = FStream ;
BitMap.EndInit( );
// 放到 Image 元件中,顯示圖片
ImageControl.BeginInit( );
ImageControl.Source = BitMap;
ImageControl.EndInit( );
// FStream.Close( ); 不可Close,不然圖片不會出來
可是這樣會遇到一個問題,載入圖檔之後,原本的圖檔會無法刪除,或被別人使用,因為資源被Stream鎖住了,如果你在程式中把FStream給Close了,那麼,執行的時候就看不到圖了(什麼機制嘛!)所以要改成底下的作法,把檔案讀到記憶體裡面
// 開檔
String FilePath = @"C:\temp\001 (1).jpg";
FileStream FStream = new FileStream( FilePath, FileMode.Open );
// 轉成 Binary
BinaryReader BinReader = new BinaryReader( FStream );
byte[] BinaBytes = BinReader.ReadBytes( (int)FStream.Length );
// 資料變成 MemoryStream (如此檔案就跟此程式無關連了,可關閉、刪除)
MemoryStream MStream = new MemoryStream( BinaBytes );
BinReader.Close( );
FStream.Close( );
// 將資料讀入 BitmapImage 變成圖檔資源
BitmapImage BitMap = new BitmapImage( );
BitMap.BeginInit( );
BitMap.StreamSource = MStream ;
BitMap.EndInit( );
// 放到 Image 元件中,顯示圖片
ImageControl.BeginInit( );
ImageControl.Source = BitMap;
ImageControl.EndInit( );
//MStream.Close( ); 不可Close,不然圖片不會出來
這樣,檔案可以更動了(因為FileStream關閉啦),可是,MemoryStream一樣無法關閉,不然圖片不會出來,這樣還是沒有解決問題,根本的作法,是預先載入,設定BitmapCacheOption,這樣,就可以回到第一個作法,簡單作出來。
// 開檔
String FilePath = @"C:\temp\001 (1).jpg";
FileStream FStream = new FileStream( FilePath, FileMode.Open );
// 將資料讀入 BitmapImage 變成圖檔資源
BitmapImage BitMap = new BitmapImage( );
BitMap.BeginInit( );
BitMap.StreamSource = FStream ;
BitMap .CacheOption = BitmapCacheOption.OnLoad;
BitMap.EndInit( );
FStream.Close();
// 放到 Image 元件中,顯示圖片
ImageControl.BeginInit( );
ImageControl.Source = BitMap;
ImageControl.EndInit( );
// 開檔
String FilePath = @"C:\temp\001 (1).jpg";
FileStream FStream = new FileStream( FilePath, FileMode.Open );
// 將資料讀入 BitmapImage 變成圖檔資源
BitmapImage BitMap = new BitmapImage( );
BitMap.BeginInit( );
BitMap.StreamSource = FStream ;
BitMap.EndInit( );
// 放到 Image 元件中,顯示圖片
ImageControl.BeginInit( );
ImageControl.Source = BitMap;
ImageControl.EndInit( );
// FStream.Close( ); 不可Close,不然圖片不會出來
可是這樣會遇到一個問題,載入圖檔之後,原本的圖檔會無法刪除,或被別人使用,因為資源被Stream鎖住了,如果你在程式中把FStream給Close了,那麼,執行的時候就看不到圖了(什麼機制嘛!)所以要改成底下的作法,把檔案讀到記憶體裡面
// 開檔
String FilePath = @"C:\temp\001 (1).jpg";
FileStream FStream = new FileStream( FilePath, FileMode.Open );
// 轉成 Binary
BinaryReader BinReader = new BinaryReader( FStream );
byte[] BinaBytes = BinReader.ReadBytes( (int)FStream.Length );
// 資料變成 MemoryStream (如此檔案就跟此程式無關連了,可關閉、刪除)
MemoryStream MStream = new MemoryStream( BinaBytes );
BinReader.Close( );
FStream.Close( );
// 將資料讀入 BitmapImage 變成圖檔資源
BitmapImage BitMap = new BitmapImage( );
BitMap.BeginInit( );
BitMap.StreamSource = MStream ;
BitMap.EndInit( );
// 放到 Image 元件中,顯示圖片
ImageControl.BeginInit( );
ImageControl.Source = BitMap;
ImageControl.EndInit( );
//MStream.Close( ); 不可Close,不然圖片不會出來
這樣,檔案可以更動了(因為FileStream關閉啦),可是,MemoryStream一樣無法關閉,不然圖片不會出來,這樣還是沒有解決問題,根本的作法,是預先載入,設定BitmapCacheOption,這樣,就可以回到第一個作法,簡單作出來。
// 開檔
String FilePath = @"C:\temp\001 (1).jpg";
FileStream FStream = new FileStream( FilePath, FileMode.Open );
// 將資料讀入 BitmapImage 變成圖檔資源
BitmapImage BitMap = new BitmapImage( );
BitMap.BeginInit( );
BitMap.StreamSource = FStream ;
BitMap .CacheOption = BitmapCacheOption.OnLoad;
BitMap.EndInit( );
FStream.Close();
// 放到 Image 元件中,顯示圖片
ImageControl.BeginInit( );
ImageControl.Source = BitMap;
ImageControl.EndInit( );
2012年1月10日 星期二
WPF的Main去哪裡了?我怎麼取得執行參數?
由於WPF把main()藏了起來,包裝起來,在編譯過程才會產生,所以原本透過main(string[] args)來取得參數的方法變得無法使用了(或說我不知道該怎麼用),怎麼辦呢?可以透過以下的變通方式來用,雖然麻煩點,但是知道方法之後,也沒有多難。
首先,要在App.xaml.cs動手腳,增加以下程式碼,就可以取得
// override 的目的是為了取得傳入的參數
protected override void OnStartup( StartupEventArgs e )
{
public static String Args0;
if ( e.Args != null && e.Args.Count( ) > 0 )
{
Args0 = e.Args[ 0 ].ToString( );
}
base.OnStartup( e );
}
然後在啟動的視窗(可以在App.xmal當中看到呼叫了哪個視窗,他就會是啟動視窗,比方如果是 StartupUri="WinProgress.xaml" 那WinProgress 就是啟動視窗 )
在該視窗程式碼(.cs)當中就可以用App.Args0取得傳入的參數了。
那參數如果有兩個呢?很簡單,就這樣子做:
// override 的目的是為了取得傳入的參數
protected override void OnStartup( StartupEventArgs e )
{
public static String Args0;
public static String Args1;
if ( e.Args != null && e.Args.Count( ) > 1 )
{
Args0 = e.Args[ 0 ].ToString( );
Args1 = e.Args[ 1 ].ToString( );
}
base.OnStartup( e );
}
反而比較要注意的是,如果你透過程式要呼叫上面那個程式,想把參數傳進去,要怎麼透過Process()來傳多個參數呢?,要用個小技巧,Process.Start( "Filename", "Arg1 Arg2" );在Start()這個函式的第二個參數,傳入的自串中間用空格隔開,就會變成兩個參數了XD
首先,要在App.xaml.cs動手腳,增加以下程式碼,就可以取得
// override 的目的是為了取得傳入的參數
protected override void OnStartup( StartupEventArgs e )
{
public static String Args0;
if ( e.Args != null && e.Args.Count( ) > 0 )
{
Args0 = e.Args[ 0 ].ToString( );
}
base.OnStartup( e );
}
然後在啟動的視窗(可以在App.xmal當中看到呼叫了哪個視窗,他就會是啟動視窗,比方如果是 StartupUri="WinProgress.xaml" 那WinProgress 就是啟動視窗 )
在該視窗程式碼(.cs)當中就可以用App.Args0取得傳入的參數了。
那參數如果有兩個呢?很簡單,就這樣子做:
// override 的目的是為了取得傳入的參數
protected override void OnStartup( StartupEventArgs e )
{
public static String Args0;
public static String Args1;
if ( e.Args != null && e.Args.Count( ) > 1 )
{
Args0 = e.Args[ 0 ].ToString( );
Args1 = e.Args[ 1 ].ToString( );
}
base.OnStartup( e );
}
反而比較要注意的是,如果你透過程式要呼叫上面那個程式,想把參數傳進去,要怎麼透過Process()來傳多個參數呢?,要用個小技巧,Process.Start( "Filename", "Arg1 Arg2" );在Start()這個函式的第二個參數,傳入的自串中間用空格隔開,就會變成兩個參數了XD
C# 嵌入檔案,包在EXE裡
圖檔可以透過加入Resource的方式來使用,那其他檔案呢?有一種方便的嵌入方式可以把想要的檔案夾在你產生的EXE中,從專案中選擇「加入」、「現有項目」、然後從檔案對話框當中更改檔案類型為*.*,點選你想要的檔案,可加入專案中。
接下來,在方案總管中選擇該檔案,在屬性視窗將「建置動作」改為「內嵌資源」,這樣就可以讓程式碼引用,程式碼如下。
// 從專案組件讀入檔案到磁碟
Assembly Asmb = Assembly.GetExecutingAssembly( );
Stream ManifestStream = Asmb.GetManifestResourceStream( Asmb.GetName( ).Name + ".Update_Downloader.exe" );
// 讀入檔案
byte[] StreamData = new byte[ ManifestStream.Length ];
ManifestStream.Read( StreamData, 0, (int)ManifestStream.Length );
// 存到磁碟
FileStream FileStm = new FileStream( ExeFileName, FileMode.Create );
FileStm.Write( StreamData, 0, (int)ManifestStream.Length );
FileStm.Close( );
2012年1月9日 星期一
C#角度看XML格式讀取
XML以程式語言的角度來看的目的是什麼?就是為了知道怎麼讀寫,怎麼解析內容
讀寫的方式有很多種,XmlReader, XmlDocument......能控制的角度,能使用的函式也有不同
在此先介紹 XmlDocument
先將 XmlDocument 產生物件之後,可呼叫 Load() 來載入 XML 檔,如果用 LoadXml() 則可以由字串來讀入,也就是一個傳入路徑,一個傳入String,之後便透過節點的方式,指定要讀取哪一個階層的節點們,然後用迴圈逐一的將內容讀取出來,以下為簡單的範例程式
XmlDocument XmlDoc = new XmlDocument( );
XmlDoc.Load( @"C:\XmlFileName.XML" );
XmlNodeList NodeLists = XmlDoc.SelectNodes( "Root/MyLevel1" );
foreach ( XmlNode OneNode in NodeLists )
{
String StrAttrName = OneNode.Attributes.Name;
String StrAttrValue = OneNode.Attributes[ " MyAttr1 " ].Value;
String StrAttrValue = OneNode.InnerText;
}
如此便可將 <MyLevel1> 這一層的節點都抓出來,下面這個XML範例來抓應該會抓到五個,然後讀取每一個的 MyAttr1 屬性的內容以及Node的InnerText。(備註:但是這樣的作法,是固定的沒有彈性的,必須每個<MyLevel1>節點都要具備MyAttr1,否則就會有Exception,而某個Node如果有多個Attribute則不會讀取到)。同樣的,如果用XmlNodeList NodeLists = XmlDoc.SelectNodes( "Root/MyLevel1/MyLevel2" );就可以讀取這層的四個節點了。 接下來,我們看看XML的格式
<?xml version="1.0" encoding="utf-8"?>
<Root>
<MyLevel1 MyAttr1 = "aaaaa" > WXYZ
<MyLevel2 MyAttr10 = "UUUUUUUUU" />
<MyLevel2 MyAttr10 = "KKKKKKKKK" >QWER</MyLevel2>
</MyLevel1>
<MyLevel1 MyAttr1 = "aaaaa" > WXYZ
<MyLevel2 MyAttr10 = "VVVVVVVVV" />
<MyLevel2 MyAttr10 = "PPPPPPPPP" >QWER</MyLevel2>
</MyLevel1>
<MyLevel1 MyAttr1 = "bbbbb" MyAttr2 = "bbbbb"/>
<MyLevel1 MyAttr1 = "UUUUUUUUU" />
</Root>
Root是根節點,一個檔案只能有一個,接下來,每個<>所括住的都是一個節點,並且分層次存在,層次的分法,是相同的標記如果用<>與</>來分兩行來包住其他的<>節點,那這些被包起來的,就會是下一層。而每個節點可以有Attributes,每個屬性可以存放一個數值(或字串),而如果節點的表示法用 用<>與</>來表示,且中間夾了數值(或字串),則這個稱為InnerText。(備註:另外還有InnerXml,這個是包含子節點都算進去,有點複雜,也可先不理會),所以用程式來讀取其Attributes的Value,或是讀取InnerText,在轉成需要的格式,就是XML的讀取應用方式了,
接下來,挑戰一下有難度的格式吧!!
<?xml version="1.0" encoding="utf-8"?>
<Root>
<MyLevel1 MyAttr1 = "aaaaa" > WXYZ
<MyLevel2 MyAttr100 = "第二層01" />
<MyLevel2>IN_002</MyLevel2>
</MyLevel1>
<MyLevel1 MyAttr1 = "bbbbb" > WXYZ
<MyLevel2 MyAttr100 = "第二層02" MyAttr101 = "第二層002" />
<MyLevel2>IN_003</MyLevel2>
</MyLevel1>
<MyLevel1 MyAttr1 = "ccccc" > WXYZ
<MyLevel3 MyAttr100 = "第二層03" />
<MyLevel3>IN_004</MyLevel3>
</MyLevel1>
<MyLevel1 MyAttr1 = "ddddd" > WXYZ
<MyLevel2 MyAttr100 = "第二層04" />
<MyLevel2>IN_005</MyLevel2>
</MyLevel1>
<YouLevel1 MyAttr1 = "ddddd" > WXYZ
<MyLevel2 MyAttr100 = "第二層05" />
<MyLevel2>IN_006</MyLevel2>
</YouLevel1>
<MyLevel1 MyAttr1 = "bbbbb" MyAttr2 = "bbbbb"/>
<MyLevel1 MyAttr10 = "UUUUUUUUU" />
<MyLevel1>IN_007</MyLevel1>
</Root>
不管他格式多複雜,用以下的方式,就可以讀取節點的每個Attribute,以及InnerText了,且,不會去嘗試讀取不存在的Attribute,所以不會發生Exception。
foreach ( XmlNode OneNode in NodeLists )
{
String StrNodeName = OneNode.Name.ToString();
foreach ( XmlAttribute Attr in OneNode.Attributes )
{
String StrAttr = Attr.Name.ToString( );
String StrValue = OneNode.Attributes[ Attr.Name.ToString( ) ].Value;
String StrInnerText = OneNode.InnerText;
}
}
再來,就是怎麼選擇要讀取哪一層,如果用以下的方式會讀取在Root底下的MyLevel1底下的MyLevel2,對,MyLevel3就不會被讀取了。還有YouLevel1底下的MyLevel2也不會被讀取,
所以會讀取到6個節點。
XmlNodeList NodeLists = XmlDoc.SelectNodes( "Root/MyLevel1/MyLevel2" );
如果用以下的方式會讀取在Root底下的MyLevel1 ,則會讀取到7個節點
XmlNodeList NodeLists = XmlDoc.SelectNodes( "Root/MyLevel1" );
讀寫的方式有很多種,XmlReader, XmlDocument......能控制的角度,能使用的函式也有不同
在此先介紹 XmlDocument
先將 XmlDocument 產生物件之後,可呼叫 Load() 來載入 XML 檔,如果用 LoadXml() 則可以由字串來讀入,也就是一個傳入路徑,一個傳入String,之後便透過節點的方式,指定要讀取哪一個階層的節點們,然後用迴圈逐一的將內容讀取出來,以下為簡單的範例程式
XmlDocument XmlDoc = new XmlDocument( );
XmlDoc.Load( @"C:\XmlFileName.XML" );
XmlNodeList NodeLists = XmlDoc.SelectNodes( "Root/MyLevel1" );
foreach ( XmlNode OneNode in NodeLists )
{
String StrAttrName = OneNode.Attributes.Name;
String StrAttrValue = OneNode.Attributes[ " MyAttr1 " ].Value;
String StrAttrValue = OneNode.InnerText;
}
如此便可將 <MyLevel1> 這一層的節點都抓出來,下面這個XML範例來抓應該會抓到五個,然後讀取每一個的 MyAttr1 屬性的內容以及Node的InnerText。(備註:但是這樣的作法,是固定的沒有彈性的,必須每個<MyLevel1>節點都要具備MyAttr1,否則就會有Exception,而某個Node如果有多個Attribute則不會讀取到)。同樣的,如果用XmlNodeList NodeLists = XmlDoc.SelectNodes( "Root/MyLevel1/MyLevel2" );就可以讀取這層的四個節點了。 接下來,我們看看XML的格式
<?xml version="1.0" encoding="utf-8"?>
<Root>
<MyLevel1 MyAttr1 = "aaaaa" > WXYZ
<MyLevel2 MyAttr10 = "UUUUUUUUU" />
<MyLevel2 MyAttr10 = "KKKKKKKKK" >QWER</MyLevel2>
</MyLevel1>
<MyLevel1 MyAttr1 = "aaaaa" > WXYZ
<MyLevel2 MyAttr10 = "VVVVVVVVV" />
<MyLevel2 MyAttr10 = "PPPPPPPPP" >QWER</MyLevel2>
</MyLevel1>
<MyLevel1 MyAttr1 = "bbbbb" MyAttr2 = "bbbbb"/>
<MyLevel1 MyAttr1 = "UUUUUUUUU" />
</Root>
Root是根節點,一個檔案只能有一個,接下來,每個<>所括住的都是一個節點,並且分層次存在,層次的分法,是相同的標記如果用<>與</>來分兩行來包住其他的<>節點,那這些被包起來的,就會是下一層。而每個節點可以有Attributes,每個屬性可以存放一個數值(或字串),而如果節點的表示法用 用<>與</>來表示,且中間夾了數值(或字串),則這個稱為InnerText。(備註:另外還有InnerXml,這個是包含子節點都算進去,有點複雜,也可先不理會),所以用程式來讀取其Attributes的Value,或是讀取InnerText,在轉成需要的格式,就是XML的讀取應用方式了,
接下來,挑戰一下有難度的格式吧!!
<?xml version="1.0" encoding="utf-8"?>
<Root>
<MyLevel1 MyAttr1 = "aaaaa" > WXYZ
<MyLevel2 MyAttr100 = "第二層01" />
<MyLevel2>IN_002</MyLevel2>
</MyLevel1>
<MyLevel1 MyAttr1 = "bbbbb" > WXYZ
<MyLevel2 MyAttr100 = "第二層02" MyAttr101 = "第二層002" />
<MyLevel2>IN_003</MyLevel2>
</MyLevel1>
<MyLevel1 MyAttr1 = "ccccc" > WXYZ
<MyLevel3 MyAttr100 = "第二層03" />
<MyLevel3>IN_004</MyLevel3>
</MyLevel1>
<MyLevel1 MyAttr1 = "ddddd" > WXYZ
<MyLevel2 MyAttr100 = "第二層04" />
<MyLevel2>IN_005</MyLevel2>
</MyLevel1>
<YouLevel1 MyAttr1 = "ddddd" > WXYZ
<MyLevel2 MyAttr100 = "第二層05" />
<MyLevel2>IN_006</MyLevel2>
</YouLevel1>
<MyLevel1 MyAttr1 = "bbbbb" MyAttr2 = "bbbbb"/>
<MyLevel1 MyAttr10 = "UUUUUUUUU" />
<MyLevel1>IN_007</MyLevel1>
</Root>
不管他格式多複雜,用以下的方式,就可以讀取節點的每個Attribute,以及InnerText了,且,不會去嘗試讀取不存在的Attribute,所以不會發生Exception。
foreach ( XmlNode OneNode in NodeLists )
{
String StrNodeName = OneNode.Name.ToString();
foreach ( XmlAttribute Attr in OneNode.Attributes )
{
String StrAttr = Attr.Name.ToString( );
String StrValue = OneNode.Attributes[ Attr.Name.ToString( ) ].Value;
String StrInnerText = OneNode.InnerText;
}
}
再來,就是怎麼選擇要讀取哪一層,如果用以下的方式會讀取在Root底下的MyLevel1底下的MyLevel2,對,MyLevel3就不會被讀取了。還有YouLevel1底下的MyLevel2也不會被讀取,
所以會讀取到6個節點。
XmlNodeList NodeLists = XmlDoc.SelectNodes( "Root/MyLevel1/MyLevel2" );
如果用以下的方式會讀取在Root底下的MyLevel1 ,則會讀取到7個節點
XmlNodeList NodeLists = XmlDoc.SelectNodes( "Root/MyLevel1" );
2012年1月6日 星期五
C# 透過HTTP抓檔案回來
在Window視窗上放一個Button,一個ProgressBar,一個TextBlock(用來顯示ProgressBar的數值)
利用以下的函式,可以完成
private void Btn_http_Click( object sender, RoutedEventArgs e )
{
// 非同步
WebClient MyWebClient = new WebClient( );
MyWebClient.DownloadFileCompleted += new AsyncCompletedEventHandler( Http_Completed );
MyWebClient.DownloadProgressChanged += new DownloadProgressChangedEventHandler( Http_ProgressChanged );
MyWebClient.DownloadFileAsync( new Uri( "http://www.joyplux.net/xplayer/download/JoyeDM/JoyeDMDownload_Setup.exe" ), @"c:\temp\JoyeDM.exe" );
}
private void Http_ProgressChanged( object sender, DownloadProgressChangedEventArgs e )
{
PgBar_Http.Value = e.ProgressPercentage; //控制ProcessBar顯示進度
TxtBk_Percent.Text = e.ProgressPercentage + "%";
}
private void Http_Completed( object sender, AsyncCompletedEventArgs e )
{
MessageBox.Show( "Download completed!" );
}
利用以下的函式,可以完成
private void Btn_http_Click( object sender, RoutedEventArgs e )
{
// 非同步
WebClient MyWebClient = new WebClient( );
MyWebClient.DownloadFileCompleted += new AsyncCompletedEventHandler( Http_Completed );
MyWebClient.DownloadProgressChanged += new DownloadProgressChangedEventHandler( Http_ProgressChanged );
MyWebClient.DownloadFileAsync( new Uri( "http://www.joyplux.net/xplayer/download/JoyeDM/JoyeDMDownload_Setup.exe" ), @"c:\temp\JoyeDM.exe" );
}
private void Http_ProgressChanged( object sender, DownloadProgressChangedEventArgs e )
{
PgBar_Http.Value = e.ProgressPercentage; //控制ProcessBar顯示進度
TxtBk_Percent.Text = e.ProgressPercentage + "%";
}
private void Http_Completed( object sender, AsyncCompletedEventArgs e )
{
MessageBox.Show( "Download completed!" );
}
訂閱:
文章 (Atom)