[UWP]使用GetAlphaMask和ContainerVisual制作长阴影(Long Shadow)
1. 什么是长阴影2. 使用GetAlphaMask和ContainerVisual制作长阴影#
要在UWP中制作长阴影的话,可以用GetAlphaMask拿到轮廓,做成灰色,然后复制一百几十个摆在后面。不过当然并不是直接创建这么多个UIElement,而是使用ContainerVisual类实现这个功能。ContainerVisual
用于组合子级的Visual,只需简单地调用VisualCollection.InsertAtBottom即可。
下面是具体的实现例子,和上篇文章介绍的一样,首先在需要阴影的元素(TitleElement)后面放一个用于显示阴影的UIElement(ShadowElement),布局如下:
<Grid Background="#FFE87A69" Padding="40" Margin="50" x:Name="ShadowRoot"> <Rectangle x:Name="ShadowElement" /> <TextBlock Text="One Pomodoro" Foreground="#FFfee8da" FontSize="64" x:Name="TitleElement"/> </Grid>
然后在代码里创建一个ContainerVisual并使用ElementCompositionPreview.SetElementChildVisual
将这个ContainerVisual设置到ShadowElement的可视化层:
var textVisual = ElementCompositionPreview.GetElementVisual(TitleElement); compositor = textVisual.Compositor; containerVisual = compositor.CreateContainerVisual(); ElementCompositionPreview.SetElementChildVisual(ShadowElement, containerVisual);
之后调用TitleElement的GetAlphaMask获取轮廓,然后将这个轮廓作为Mask设置到CompositionMaskBrush
的Mask属性,重复一百次:
var mask = TitleElement.GetAlphaMask(); var shadowColor = Color.FromArgb(255, 160, 59, 49); int depth = 100; for (int i = 0; i < depth; i++) { //创建Brush var maskBrush = compositor.CreateMaskBrush(); maskBrush.Mask = mask; maskBrush.Source = compositor.CreateColorBrush(shadowColor); //创建Visual var visual = compositor.CreateSpriteVisual(); visual.Brush = maskBrush; visual.Offset = new Vector3(i + 1, i + 1, 0); //将Visual添加到ContainerVisual containerVisual.Children.InsertAtBottom(visual); //同步Visual和TextVisual的尺寸 var bindSizeAnimation = compositor.CreateExpressionAnimation("textVisual.Size"); bindSizeAnimation.SetReferenceParameter("textVisual", textVisual); visual.StartAnimation("Size", bindSizeAnimation); }
然后终于……
……还是没完成,还需要为ContainerVisual设置Clip以免阴影越界。看起来需要写很多代码去实现,但其实有个简单的方法,将外面那层的ShadowRoot的