制作簡易圖像瀏覽器
先發點牢騷放松下心情, 最近完全沒有做項目的動力,每天感覺腦子昏昏沉沉的沒有一點狀態。
一來可能快春節了,自己離家比較遠也在擔心何時回家何時購票,
二來公司程序員就我一個人在單干,軟件 項目什么的做好了,卻不能接受一次又一次的添加功能和修改數據庫,(我真的很想罵某個人的娘)
三來也老早計劃好了11年4月份一年合同到期后就離職,現在好像一點都靜不下心來
如果有各位同僚給我開解開解我也好恢復下心境。
好了,下面來說這個簡易的圖像瀏覽器吧。 其實這也不是無中生有我要去做的一個東西, 我們公司的軟件 項目都是我一個人在做的, 在做之前我已經構思好了所有的東西,也盡自己最大努力去實現了。 但是一個人兼顧設計 開發 測試,。所有東西幾個月下來, 有時候就會有其他新的想法。
這個圖像瀏覽器就算是其中一個小的部分吧, 先來看一下預覽效果吧,
就是Demo有縮略圖的這個東西了, 我把它封裝成了一個控件 命名為 ImageViewBox .其實這個東西很簡單,但是就是簡單我們有時候一下又不知道如何下手,
再加上我本身最近心情就比較煩躁,所以實現的時候太多細節也沒注意, 只是簡單實現一個縮略圖瀏覽這樣一個效果!
不過就具體的實現方法我還是簡單說下,也方便有需要的朋友可以借鑒!
先簡單描述下我可能要應用的場景:
至于上面這張圖怎么實現大家一眼也都看出來了,也不是本文要討論的! 只是為了說明這個圖片瀏覽器所要應用的一個場景,以便大家不用看到代碼后太鄙視我!好了,現在說這個圖像瀏覽器吧,
: 控件主體 ImageViewBox:UserControl
:縮略圖顯示主體 ImageViewItem:Control 這里為什么也設計為一個控件呢, 實際上是為了在 ImageViewBox中方便的直接用Dock布局,而不用復雜的繪制
主要的東西就這2個, ImageViewItem 作為一個小控件,主要顯示圖像縮略圖和圖像標題 , 當然為了我的特定應用場景,代碼簡單就OK了,有了ImageViewItem 只需要它添加到ImageViewBox中 并Dock =Left 就能規規矩矩的排成一行的。
為了規矩的排成一個橫行, 我們還需要限制ImageViewBox 以及 ImageViewItem 的大小, 另外ImageViewBox 的AutoScroll 也要設置為true,剩下的工作就是ImageViewItem 的呈現了,主要的效果就是 圓角邊框、鼠標經過時的變色, 鼠標選中時的變色以及事件。原本我的應用場景中是需要定義一個對象 如: class 截面
public Bitmap 截面背景圖
{
get;
set;
}
public string 截面名稱
{
get;
set;
}
public 傳感器 傳感器數組
{
get;
set;
}
}
這樣的話,我在ImageViewItem 的構造函數傳入 截面 這個對象就可以了, 但是后來想想還是算了, 實際用到的時候用它的tag屬性來綁定,現在為了演示方便就直接 public ImageViewItem(Bitmap bmp,string title) 好了。
然后就是定義三種狀態下,對不同狀態下 ImageViewItem的繪制了, 限定縮略圖大小為 96*96 , 具體的繪制部分代碼如下:
/// 重寫控件繪制
/// </summary>
/// <param name="e"></param>
protected override void OnPaint(PaintEventArgs e)
{
using(Graphics g=e.Graphics)
{
//處理背景
g.SetClip(this.ClientRectangle);
g.Clear(SystemColors.Window);
//繪制邊框與背景色
using(Pen borderPen=new Pen(NONE_BORDER_COLOR))
{
if (BackStyle == DrawBackStyle.FOCUSED)
{
borderPen.Color = FOCUSED_BORDER_COLOR;
using (LinearGradientBrush backBrush = new LinearGradientBrush(this.ClientRectangle,FOCUSED_LIGHT_COLOR,FOCUSED_DEEP_COLOR, LinearGradientMode.Vertical))
{
g.FillPath(backBrush, Utility.GetRoundedRectanglePath(2, 2, this.Width - 4, this.Height - 4, 5));
}
}
else if (BackStyle == DrawBackStyle.SELECTED)
{
borderPen.Color = SELECTED_BORDER_COLOR;
using (LinearGradientBrush backBrush = new LinearGradientBrush(this.ClientRectangle, SELECTED_LIGHT_COLOR, SELECTED_DEEP_COLOR, LinearGradientMode.Vertical))
{
g.FillPath(backBrush, Utility.GetRoundedRectanglePath(2, 2, this.Width - 4, this.Height - 4, 5));
}
}
g.DrawPath(borderPen, Utility.GetRoundedRectanglePath(2, 2, this.Width - 4, this.Height - 4, 5));
}
//繪制縮略圖與標題
if (this.ThumbnailImage != null)
{
g.DrawImage(this.ThumbnailImage, new Rectangle(IMAGE_POINT, IMAGE_SIZE));
}
Color foreColor = this.ImageViewBox.ForeColor;
Rectangle rt = new Rectangle(3, 103, 98, TextRenderer.MeasureText(this.Title, ImageViewBox.Font).Height);
TextRenderer.DrawText(g, this.Title, ImageViewBox.Font, rt, foreColor,
TextFormatFlags.EndEllipsis | TextFormatFlags.HorizontalCenter | TextFormatFlags.VerticalCenter | TextFormatFlags.SingleLine);
}
}
有一些細節方面的東西我就不多解釋了,主要是為了方便我的應用, 不如 ImageViewItem中的 ImageViewBox 屬性等! 以及用ImageViewBox屬性來設置標題字體顏色等。這一部分對于有過制作自定義控件的朋友就很熟悉了, 那關于三種狀態的的變化呢 也很簡單,就是重寫下 OnMouse 相關的函數,代碼如下
/// <summary>
/// 鼠標進入控件區域
/// </summary>
/// <param name="e"></param>
protected override void OnMouseEnter(EventArgs e)
{
if (!BackStyle.Equals(DrawBackStyle.SELECTED))
{
this.BackStyle = DrawBackStyle.FOCUSED;
this.Refresh();
}
base.OnMouseEnter(e);
}
/// <summary>
/// 鼠標移出控件區域
/// </summary>
/// <param name="e"></param>
protected override void OnMouseLeave(EventArgs e)
{
if (!BackStyle.Equals(DrawBackStyle.SELECTED))
{
this.BackStyle = DrawBackStyle.NONE;
this.Refresh();
}
base.OnMouseLeave(e);
}
/// <summary>
/// 控件被點擊
/// </summary>
/// <param name="e"></param>
protected override void OnClick(EventArgs e)
{
//取消其他ImageViewItem 選中狀態
foreach (ImageViewItem item in this.ImageViewItemCollection)
{
if (item.BackStyle != DrawBackStyle.NONE)
{
item.BackStyle = DrawBackStyle.NONE;
item.Refresh();
}
}
this.BackStyle = DrawBackStyle.SELECTED;
this.Refresh();
base.OnClick(e);
}
有了上面這些東西,其實就已經能簡單的實現本文標題的這個東西了,不過我們還需要加點東西 ,需要加一個類ImageViewItemCollection.cs 。呵呵,這樣大家就知道該怎么做了吧,那我就不廢話了! 請不要拍我,我也知道簡單,我也想封裝好一點發出來,但是真的心煩意亂,就當是給也在找這方面實現資料的朋友一個示例吧,雖然不怎么好!
我就直接上代碼了:代碼下載
留言列表