一个 WPF TileView 控件






4.58/5 (11投票s)
一个简单的 WPF TileView 控件。
TileView 控件
TileView
控件允许你以平铺的方式排列一组项目 (Tile
),并且其中一个 Tile
会被激活,并在相对较大的区域中显示。 Tile
的激活和取消激活是动画的。 它的行为或多或少类似于 Carousel
控件,但它们是不同的。
选择基类
TileView
展示一组平铺项,并以不同的方式排列它们。 当涉及到展示一组项目时,ItemsControl
是最佳选择,并且我们经常使用的大多数控件都派生自 ItemsControl
,ListView
、TreeView
或 Menu,并且它们每个都有自己的 Item
。 TileView
只是展示一组项目,所以它派生自 ItemsControl
,并且每个 Tile
展示内容。 显然,我们可以选择 ContentControl
,这样我们就可以展示任何内容,但为了将来可能出现的需求,Tile
派生自 HeaderedContentControl
。 我所说的“未来需求”是指,可能有人想要显示标题,或者用于激活/取消激活平铺项的按钮。
主要(简单)需求
该控件的行为是众所周知的,并在其介绍部分中定义。 这是实现此行为的需求列表。
- 平铺项需要以统一的方式排列,并且活动项获得更多空间。
- 其中一个
Tile
在加载时变为活动状态,并且可以使用鼠标激活任何其他Tile
。 - 激活和取消激活应该是动画的和平滑的。
ActiveTile
相对较大,因此非活动Tile
需要两个变换:ScallingTransform
- 使其更大,TranslateTransform
- 将其移动到活动位置。
鉴于需要一个字段来跟踪活动平铺项,我们有 ActiveTile
。
需要一种布局机制来按比例划分 ActiveTile
和其他项之间的空间,所有其他平铺项平均分享剩余空间。
平铺项必须知道鼠标事件,并在激活时通知 TileView
,为此,我们需要 Activated
事件。
将文字付诸行动
让我们看看这些需求是如何以相反的顺序实现的。
动画平铺项
如前所述,激活平铺项涉及两个变换,它们作用于 Tile
的四个不同属性。 要将 Tile
移动到活动位置,使用 TranslateTransform
并且它作用于它的 X 和 Y 值,并且为了使 Tile
更大,使用 ScaleTransform
并且它作用于宽度和高度值。 以下代码演示了如何完成此操作。 这仅用于表示这些值,实际实现与表示形式不同。
tile.RenderTransform = new TranslateTransform();
/* defining StoryBoard and animations */
Storyboard tileActivator = new Storyboard();
DoubleAnimation translateX =
new DoubleAnimation { From = 0, To = 10, Duration = TimeSpan.FromSeconds(1) };
/* Sets the target and the target property for the animation to operate */
Storyboard.SetTarget(translateX, tile);
Storyboard.SetTargetProperty(translateX,
new PropertyPath("(UIElement.RenderTransform).(TranslateTransform.X)"));
/* Adds the animation to the StoryBorad and initiate the activation */
tileActivator.Children.Add(translateX);
tileActivator.Begin();
在 Tile
的所有四个属性中使用相同的方法,使其从非活动状态变为活动状态。
平铺项激活通知
当用户通过鼠标单击激活它时,必须通知 TileView
,此实现定义了一个事件 Activated
,并且只是重写了鼠标按下事件以引发 Activated
事件。 TileView
监听此 Activated
事件并将发送者设置为新的 ActiveTile
。
public event RoutedEventHandler Activated;
protected override void OnMouseDown(System.Windows.Input.MouseButtonEventArgs e)
{
base.OnMouseDown(e);
if (Activated != null)
Activated(this, new RoutedEventgArgs());
}
TileView
监听此事件,将 sender
强制转换为 Tile
,并激活它。
tile.Activated += new RoutedEventHandler(OnTileActivated);
void OnTileActivated(object sender, RoutedEventArgs e)
{
ActivateTile(sender as Tile);
}
排列平铺项
WPF 中的布局过程分两个阶段进行:MeasureOverride
和 ArrageOverride
,这些都在很多文章中得到了很好的解释。 前者让子项知道可用的空间并询问子项将占用的空间。 后者给出它可以占用的空间。
protected override Size MeasureOverride(Size constraint)
{
var sz = base.MeasureOverride(constraint);
foreach (Tile tile in Items)
{
/* size is the value TileView gives to each tiles */
tile.Measure(size)
}
return sz;
}
protected override Size ArrangeOverride(Size arrangeBounds)
{
foreach (Tile tile in OrderedItems)
{
/* rect is the value TileView layout
mechanism gives to each Tile */
tile.Arrange(rect);
}
return arrangeBounds;
}
历史
- 2011/11/16 - 首次发布。
- 2011/11/30 - 添加了
TileState
API,源代码和演示文件已更新。
希望这有帮助!!! 祝您编码愉快!!!