.NET 和 Flex 在開發上都使用了許多 Attribute,我也一直對 Attribute 的應用很感興趣,可是實務開發應用的不多。主要還是對 .NET Attribute 的掌握度不夠,今天在網路上發現六篇針對 Attribute 的系列文章
*博客园 – dudu – Attribute在.net编程中的应用(一)
*博客园 – dudu – Attribute在.net编程中的应用(二)
*博客园 – dudu – Attribute在.NET编程中的应用(三)
*博客园 – dudu – Attribute在.NET编程中的应用(四)
*博客园 – dudu – Attribute在.NET编程中的应用(五)
*博客园 – dudu – Attribute在.NET编程中的应用(六)
寫的相當不錯,但可惜被埋沒許久。
其中第四篇提到 Attribute + Reflection 製作 SQL Command 產生器的應用,對我前陣子也是寫重複的 SQL Command 帶來不錯的啟發。
我以下嘗試實作 Flex 的 Embed[下載],首先是 Attribute 部份
public enum EmbedImageSource {
File,
Http
}
public enum EmbedImageType {
Jpeg,
Gif,
Png
}
[AttributeUsage( AttributeTargets.Field )]
public class EmbedImageAttribute : Attribute {
private String m_url;
private EmbedImageSource m_source;
private EmbedImageType m_type;
public EmbedImageAttribute(String url, EmbedImageSource source, EmbedImageType type) {
m_url = url;
m_source = source;
m_type = type;
}
public String URL {
get {
return m_url;
}
}
public EmbedImageType Type {
get {
return m_type;
}
}
public EmbedImageSource Source {
get {
return m_source;
}
}
}
然後是利用 Reflection+ Attribute 產生動載入影像的程式碼,如下:
public class EmbedImageGenerator {
public static void InitEmbedImage(object obj) {
Type t = obj.GetType();
FieldInfo[] fis = t.GetFields();
MemberInfo[] mis = t.GetMembers();
PropertyInfo[] pis = t.GetProperties();
foreach (FieldInfo fi in fis) {
object[] attrs = fi.GetCustomAttributes(false);
foreach (Attribute attr in attrs) {
if (attr is EmbedImageAttribute) {
EmbedImageAttribute ma = attr as EmbedImageAttribute;
if (ma.Source == EmbedImageSource.File) { ;
fi.SetValue(obj, System.Drawing.Image.FromFile(ma.URL));
} else if (ma.Source == EmbedImageSource.Http) {
System.Net.WebClient client = new System.Net.WebClient();
byte[] bs = client.DownloadData(ma.URL);
using (MemoryStream ms = new MemoryStream(bs)) {
fi.SetValue(obj, System.Drawing.Image.FromStream(ms));
}
}
}
}
}
}
}
最後是測試程式碼
using System;
using System.Collections.Generic;
using System.Text;
using System.IO;
using System.Reflection;
using System.Windows.Forms;
namespace ConsoleApplication1 {
class Program {
static void Main(string[] args) {
Tester t = new Tester();
}
}
public class Tester {
[EmbedImage("http://shared.live.com/HjKMzTS-xzcms40!CabizA/emoticons/smile_teeth.gif", EmbedImageSource.Http, EmbedImageType.Gif)]
public System.Drawing.Image imgHttp;
[EmbedImage("d:\logo.jpg", EmbedImageSource.File, EmbedImageType.Jpeg)]
public System.Drawing.Image imgFile;
public Tester() {
//
EmbedImageGenerator.InitEmbedImage(this);
Form f = new Form();
FlowLayoutPanel flp = new FlowLayoutPanel();
PictureBox pic = new PictureBox();
pic.Image = imgFile;
pic.Size = imgFile.Size;
flp.Controls.Add(pic);
pic = new PictureBox();
pic.Image = imgHttp;
pic.Size = imgHttp.Size;
flp.Controls.Add(pic);
f.Controls.Add(flp);
f.ShowDialog();
}
}
}
以下是上述程式的執行結果
雖然依稀可以模擬出 Flex 的 Embed 但是還是很多餘的需要撰寫 EmbedImageGenerator.InitEmbedImage(this); 有點可惜。
另外,如果有用不完的 Attribute,是不是以後寫程式可以像貼標籤一樣簡單就寫完了呢?
發表留言