什麼是馬賽克(Mask)
相信許多看電影的朋友都知道什麼是馬賽克,通俗的将就是視訊或者圖檔上方有一層模糊的區域,以使這塊區域不可見。
下面的文字摘自百度百科:
馬賽克(Mosaic),建築專業名詞為錦磚,分為陶瓷錦磚和玻璃錦磚兩種。是一種裝飾藝術,通常使用許多小石塊或有色玻璃碎片拼成圖案,在教堂中的玻璃藝品,又稱為花窗玻璃(stained glass)。在拜占庭帝國時代,馬賽克随着基督教興起而發展為教堂及宮殿中的壁畫形式。現今馬賽克泛指這種類型五彩斑斓的視覺效果。馬賽克也指現行廣為使用的一種圖像(視訊)處理手段,此手段将影像特定區域的色階細節劣化并造成色塊打亂的效果,因為這種模糊看上去有一個個的小格子組成,便形象的稱這種畫面為馬賽克。其目的通常是使之無法辨認。
先來看一下程式的運作結果:
<a target="_blank" href="http://blog.51cto.com/attachment/201105/155255561.jpg"></a>
要實作這個效果,我們是通過圖檔的Clip屬性。
圖檔的Cilp屬性
用于确定剪輯區域大小的幾何圖形。一個典型的例子如下:
在沒有使用Clip屬性之前圖檔是這樣的:
使用的代碼是MSDN上的代碼
<Image
Source="sampleImages\Waterlilies.jpg"
Width="200" Height="150" HorizontalAlignment="Left">
<Image.Clip>
<EllipseGeometry
RadiusX="100"
RadiusY="75"
Center="100,75"/>
</Image.Clip>
</Image>
使用了Clip屬性之後:
<a target="_blank" href="http://blog.51cto.com/attachment/201105/155421717.png"></a>
CompositionTarget.Rendering
CompositionTarget 是一個類,表示正在其上繪制您的應用程式的顯示圖面。 WPF 動畫引擎為建立基于幀的動畫提供了許多功能。 但是,在有些應用程式方案中,您需要根據每個幀控制呈現。 使用 CompositionTarget 對象,可以基于每個幀回調來建立自定義動畫。
我們在程式中使用這個重繪的方法來重繪螢幕,具體的代碼如下:
void CompositionTarget_Rendering(object sender, EventArgs e)
{
double springness = Spring;
double scale = 1;
//周遊每一個圖檔
for (int i = 0; i < images.Length; i++)
{
//目前的圖檔
Image image = images[i];
// 根據目标點重定位圖檔
double offsetX = -(image.Width - ImageWidth) / ImageWidth * targetPoint.X;
double offsetY = -(image.Height - ImageHeight) / ImageHeight * targetPoint.Y;
image.SetValue(Canvas.LeftProperty, offsetX);
image.SetValue(Canvas.TopProperty, offsetY);
// 更新馬賽克
EllipseGeometry ellipseGeometry = (EllipseGeometry)image.Clip;
Point center = ellipseGeometry.Center;
centercenter.X = center.X + (targetPoint.X - offsetX - center.X) * springness;
centercenter.Y = center.Y + (targetPoint.Y - offsetY - center.Y) * springness;
ellipseGeometry.Center = center;
image.Clip = ellipseGeometry;
springness *= SpringDrag;
scale += LayerScale;
}
}
打造馬賽克
我們使用多重圖檔堆疊來打造馬賽克,具體的代碼如下:
/// <summary>
/// 将打過馬賽克的圖檔添加到窗體中
/// </summary>
private void addImage()
double radius = InitialRadius;//初始半徑
ImageSource imageSource = new BitmapImage(new Uri(ImagePath, UriKind.Relative));
//周遊層數
for (int i = 0; i < LayerCount; i++)
// 建立馬賽克
EllipseGeometry ellipseGeometry = new EllipseGeometry();
ellipseGeometry.Center = new Point(0, 0);
ellipseGeometry.RadiusX = radius;
ellipseGeometry.RadiusY = radius;
double offsetX = ImageWidth * (1 - scale) / 2;
double offestY = ImageHeight * (1 - scale) / 2;
// 建立圖檔,并設定圖檔的位置
Image image = new Image();
image.Source = imageSource;
image.Width = ImageWidth * scale;
image.Height = ImageHeight * scale;
image.SetValue(Canvas.TopProperty, offestY);
// 用于确定剪輯區域大小的幾何圖形
// 将馬賽克和圖檔添加到螢幕中
images[i] = image;
LayoutRoot.Children.Insert(0, image);
radius += RadiusIncrement;
// 将圖檔添加到窗體的背景中
Image background = new Image();
background.Source = imageSource;
LayoutRoot.Children.Insert(0, background);
詳細的代碼可以參加源代碼。
WPF版源檔案下載下傳:
<a target="_blank" href="http://blog.51cto.com/attachment/201105/2621421_1306396586.rar"></a>
Silverlight版源檔案下載下傳:
<a target="_blank" href="http://blog.51cto.com/attachment/201105/2621421_1306396615.zip"></a>
<a href="http://down.51cto.com/data/2358229" target="_blank">附件:http://down.51cto.com/data/2358229</a>
本文轉自xshf12345 51CTO部落格,原文連結:http://blog.51cto.com/alexis/574740,如需轉載請自行聯系原作者