Windows Store apps开发[52]Button控件的自定义——模仿开始屏幕中磁贴的按上、移动效果
Windows Store apps开发[52]Button控件的自定义——模仿开始屏幕中磁贴的按下、移动效果
![Windows Store apps开发[52]Button控件的自定义——模仿开始屏幕中磁贴的按上、移动效果 Windows Store apps开发[52]Button控件的自定义——模仿开始屏幕中磁贴的按上、移动效果](/default/index/img?u=aHR0cDovL3d3dy5teWV4Y2VwdGlvbnMubmV0L2ltZy8yMDEyLzExLzIwLzEwMTUwNDEzNzQuanBn)
代码有详细注释,在此不过多讲解。
![Windows Store apps开发[52]Button控件的自定义——模仿开始屏幕中磁贴的按上、移动效果 Windows Store apps开发[52]Button控件的自定义——模仿开始屏幕中磁贴的按上、移动效果](/default/index/img?u=aHR0cDovL3d3dy5teWV4Y2VwdGlvbnMubmV0L2ltZy8yMDEyLzExLzIwLzEwMTUwNDEzNzcuanBn)
注:本文由BeyondVincent(破船)原创首发
转载请注明出处:BeyondVincent(破船)@DevDiv.com
更多内容请查看下面的帖子
[DevDiv原创]Windows 8 开发Step by Step
小引
在Windows 8的开始屏幕上全是一些方块,当我们用鼠标或者手去触摸时,会有不同的按下倾斜效果,移动的时候也会有放大+半透明的效果。这效果非常的cool。那么这篇博文,我就在自定义一下Button,让其具有类似的效果(Tile内容更新的效果不在此范围,或许在以后的文章中我会写,此文只讨论按下、移动效果)。
注:我在这里称这样的按钮为TileButton
自定义TileButton的关键技术
A、继承自Button,这样会方便很多,只需要做极少部分的处理
B、截获按下事件,首先分析按下位置,然后根据位置做不同的效果
C、移动过程中,对按钮做放大和半透明处理,增加用户体验
制作步骤
1、新建空白工程,名称为BV_TileButton
2、在项目工程上单击右键,选择添加->选择类->输入BV_TileButton,然后确定
3、打开BV_TileButton.cs文件:
里面的内容如下:
/* * ============================================================================== * Filename: BV_TileButton.cs * * Description: * TileButton实现了按下、拖动等效果,有点类似开始屏幕那些磁贴的按下、拖动效果、还支持缩放、旋转等。 * 还存在的问题:在边界按下时,进行拖动没有效果,暂时不知道如何处理 * * Version: 1.0 * Created: 2012/11/15 21:32:23 * * Author: BeyondVincent(破船) * http://weibo.com/beyondvincent * qq:77973689 * ============================================================================== */ using System; using System.Collections.Generic; using System.Diagnostics; using System.Linq; using System.Text; using System.Threading.Tasks; using Windows.Foundation; using Windows.UI.Xaml; using Windows.UI.Xaml.Controls; using Windows.UI.Xaml.Input; using Windows.UI.Xaml.Media; namespace BV_TileButton { class BV_TileButton : Button { // 翻转效果 PlaneProjection projection; // 移动、缩放、旋转等转换 CompositeTransform transform; // 按下时,倾斜的角度 int angle = 10; // 拖动多远时,开始移动空间 double dragoffx = 5; double dragoffy = 5; // 构造函数 做一些初始化工作 public BV_TileButton() { projection = new PlaneProjection(); Projection = projection; transform = new CompositeTransform(); RenderTransform = transform; ManipulationMode = ManipulationModes.Rotate | ManipulationModes.Scale | ManipulationModes.TranslateX | ManipulationModes.TranslateY; } /* * 按下时的事件处理,两个步骤 * 1、首先判断当前按下去的位置在控件的那个区域(控件共分为9个区域,详见PressPointLocation定义) * 2、根据按下去的位置,对控件做不同的效果 */ protected override void OnPointerPressed(Windows.UI.Xaml.Input.PointerRoutedEventArgs e) { // 获得当前区域位置 PressPointLocation location = GetPointLocation(e.GetCurrentPoint(this).Position); // 开始对控件做效果处理 if (location == (PressPointLocation.Left | PressPointLocation.YCenter)) {// 左中 projection.RotationY = angle; projection.CenterOfRotationX = 1; } else if (location == (PressPointLocation.Left | PressPointLocation.Top)) {// 左上 projection.RotationX = -angle; projection.RotationY = angle; projection.CenterOfRotationX = 1; projection.CenterOfRotationY = 1; } else if (location == (PressPointLocation.Top | PressPointLocation.XCenter)) {// 上中 projection.RotationX = -angle * 2; projection.CenterOfRotationY = 1; } else if (location == (PressPointLocation.Right | PressPointLocation.Top)) {// 右上 projection.RotationY = projection.RotationX = -angle; projection.CenterOfRotationX = 0; projection.CenterOfRotationY = 1; } else if (location == (PressPointLocation.Right | PressPointLocation.YCenter)) {// 右中 projection.RotationY = -angle; projection.CenterOfRotationX = 0; } else if (location == (PressPointLocation.Right | PressPointLocation.Bottom)) {// 右下 projection.RotationX = angle; projection.RotationY = -angle; projection.CenterOfRotationX = 0; projection.CenterOfRotationY = 0; } else if (location == (PressPointLocation.Bottom | PressPointLocation.XCenter)) {// 下中 projection.RotationX = angle * 2; projection.CenterOfRotationY = 0; } else if (location == (PressPointLocation.Left | PressPointLocation.Bottom)) {// 左下 projection.RotationY = projection.RotationX = angle; projection.CenterOfRotationX = 1; projection.CenterOfRotationY = 1; } else if (location == (PressPointLocation.XCenter | PressPointLocation.YCenter)) {// 正中 CompositeTransform transform = RenderTransform as CompositeTransform; transform.CenterX = ActualWidth/2; transform.CenterY = ActualHeight/2; transform.ScaleX = 0.9; transform.ScaleY = 0.9; } } /* * 按下放开时的事件处理 * 主要是做一些还原处理(旋转角度归零、缩放还原、透明度设置等) */ protected override void OnPointerReleased(Windows.UI.Xaml.Input.PointerRoutedEventArgs e) { projection.RotationX = 0; projection.RotationY = 0; CompositeTransform transform = RenderTransform as CompositeTransform; transform.CenterX = ActualWidth / 2; transform.CenterY = ActualHeight / 2; transform.ScaleX = 1; transform.ScaleY = 1; Opacity = 1; dragoffx = 0; dragoffy = 0; } /* * 有移动等操作时的事件处理 * 主要包括移动、放大、透明等 */ protected override void OnManipulationDelta(ManipulationDeltaRoutedEventArgs e) { dragoffx += e.Delta.Translation.X; dragoffy += e.Delta.Translation.Y; if (-10 <= dragoffx && dragoffx <= 10 && -10 <= dragoffy && dragoffy <= 10) return; transform.CenterX = ActualWidth / 2; transform.CenterY = ActualHeight / 2; transform.ScaleX = 1.1; transform.ScaleY = 1.1; Opacity = 0.5; projection.RotationX = 0; projection.RotationY = 0; transform.TranslateX += e.Delta.Translation.X; transform.TranslateY += e.Delta.Translation.Y; transform.ScaleX *= e.Delta.Scale; transform.ScaleY *= e.Delta.Scale; transform.Rotation += e.Delta.Rotation; base.OnManipulationDelta(e); } /* * 获取控件所在的区域算法 */ PressPointLocation GetPointLocation(Point point) { PressPointLocation location = PressPointLocation.None; double tempwidth = ActualWidth / 3; if (point.X < tempwidth) { location |= PressPointLocation.Left; } else if (point.X > tempwidth * 2) { location |= PressPointLocation.Right; } else { location |= PressPointLocation.XCenter; } double tempheight = ActualHeight / 3; if (point.Y < tempheight) { location |= PressPointLocation.Top; } else if (point.Y > tempheight * 2) { location |= PressPointLocation.Bottom; } else { location |= PressPointLocation.YCenter; } Debug.WriteLine(location.ToString()); return location; } } public enum PressPointLocation { None = 0, Left = 1, Top = 2, Right = 4, Bottom = 8, XCenter = 16, YCenter = 32 } /* * 获取指定控件的Rect */ public static class BV_ToolAPI { public static Rect GetElementRect(this FrameworkElement element) { GeneralTransform buttonTransform = element.TransformToVisual(null); Point point = buttonTransform.TransformPoint(new Point()); return new Rect(point, new Size(element.ActualWidth, element.ActualHeight)); } } }
代码有详细注释,在此不过多讲解。
4、在MainPage.xaml文件中,添加如下代码:
注意:其中3行3列的girid控件是为了演示效果,为控件划分不同的区域。在实际开发中,不需要。
<Page x:Class="BV_TileButton.MainPage" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:BV_TileButton" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"> <Grid Background="Green"> <local:BV_TileButton HorizontalAlignment="Center" Height="150" VerticalAlignment="Center" Width="310" > <local:BV_TileButton.Content> <Grid Margin="0 0 0 0"> <Image Source="Assets/widelogo.png" Margin="-15,-9,-16,-10"/> <Image Source="Assets/logo.png" Margin="-19,94,234,-6"/> <TextBlock Text="5" FontSize="30" Foreground="Red" Margin="244,90,0,0"/> <TextBlock Text="读书的女孩子,很好噢" FontSize="25" FontFamily="宋体" Foreground="Magenta" Margin="7,20,10,72"/> <Grid Margin="-15,-9,-16,-10" Visibility="Visible"> <Grid.ColumnDefinitions> <ColumnDefinition/> <ColumnDefinition/> <ColumnDefinition/> </Grid.ColumnDefinitions> <Grid.RowDefinitions> <RowDefinition/> <RowDefinition/> <RowDefinition/> </Grid.RowDefinitions> <Border BorderThickness="1" BorderBrush="Red" Grid.Column="0" Grid.Row="0"/> <Border BorderThickness="1" BorderBrush="Red" Grid.Column="0" Grid.Row="1"/> <Border BorderThickness="1" BorderBrush="Red" Grid.Column="0" Grid.Row="2"/> <Border BorderThickness="1" BorderBrush="Red" Grid.Column="1" Grid.Row="0"/> <Border BorderThickness="1" BorderBrush="Red" Grid.Column="1" Grid.Row="1"/> <Border BorderThickness="1" BorderBrush="Red" Grid.Column="1" Grid.Row="2"/> <Border BorderThickness="1" BorderBrush="Red" Grid.Column="2" Grid.Row="0"/> <Border BorderThickness="1" BorderBrush="Red" Grid.Column="2" Grid.Row="1"/> <Border BorderThickness="1" BorderBrush="Red" Grid.Column="2" Grid.Row="2"/> </Grid> </Grid> </local:BV_TileButton.Content> </local:BV_TileButton> </Grid> </Page>
5、运行效果展示:
6、代码下载:
http://www.devdiv.com/thread-169767-1-1.html