Viewbox的控制在Silverlight工具包
介绍
Viewbox的Silverlight工具包是一个非常方便的控制,可以扩展其子UIElement,根据其弹力和StretchDirection属性。 它最初是由泰德Glaza书面,然后我接手和修改它的释放。 你可以阅读的概述,或玩样品 Silverlight工具包CodePlex上页。 条例草案“赖斯的博客文章Viewbox的Silverlight工具包是一个很好的文章读得。 因为它是写在WPF尽可能兼容Viewbox的控制,因此可以被引用过MSDN WPF的Viewbox的帮助 ,但与WPF和Silverlight工具包实现,我将在稍后讨论后之间的一些分歧。
实施
Viewbox的是一个简单的控制,或者应该
过度简化,实施定义两个DependencyProperty的弹力和StretchDirection,一个UIElement的类型ContentProperty儿童。 它覆盖MeasureOverride和ArrangeOverride,这两个调用ComputeScaleFactor,计算的适当规模的因素,根据孩子的DesiredSize,Viewbox的的可用/最后在测量尺寸/安排阶段,和的弹力和StrechDirection属性,和然后设置的计算ScaleTransform作为孩子的RenderTransform。
只有当世界就是这么简单
下面是Viewbox的WPF实现的:
如上所示,在WPF中,Viewbox的装饰类,Silverlight中不存在继承。 因此,我们可以移动的继承链Viewbox的继承自FrameworkElement,或侧身像从控制面板继承。 从FrameworkElement继承的是一个非首发,是因为没有AddVisualChild / RemoveVisualChild / AddLogicalChild / RemoveLogicChild Silverlight中的方法,所以我们是没有的方式来呈现Viewbox的子元素。 因此,唯一可行的办法是侧身移动,并找到一个类,它可以添加到可视树子元素。 我们选择了控制,它允许一个默认的模板,在这里我们可以坚持一个ContentPresenter呈现/缩放子元素。 因此,下面是在Silverlight工具包Viewbox的实施:
但也有破解的缺点:
- 这是不是100%用在WPF的Viewbox的兼容。 鉴于在Silverlight上的限制,这个目标是不可能实现的任何方式。 最好的,我们可以做的是要尽可能接近。
- Viewbox的继承通过继承控制,所有的控制特性,像背景,BorderBrush的,的BorderThickness的FontFamily,字号,FontStretch,FontStyle设置,FontWeight,前景,HorizontalContentAlignment,VerticalContentAlighment。 我们决定忽略这些属性,以避免人越来越习惯在Viewbox的接口部分期待这些属性。 如果你想设置这些属性,您可以设置他们的子元素。 IsEnabled属性,从Control继承,仍然为Viewbox的工作。
- 因为我们使用下面的默认模板,使儿童,创建了几个问题:
私人常量字符串 DefaultTemplateMarkup =的“<ControlTemplate xmlns="http://schemas.microsoft.com/client/2007" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"> <ContentPresenter的X:名称= “儿童”HorizontalAlignment =“{TemplateBinding来HorizontalAlignment}”VerticalAlignment =“{TemplateBinding来VerticalAlignment}”/> </ ControlTemplate中>“;
- 用户不能设置Template属性。 Viewbox的,因为在默认的模板(或者更确切地说,在默认模板的ContentPresenter),它抛出异常,如果用户试图设置模板属性。 这是一个特别糟糕的用户体验,如果你在混合上面的截图,里面混合。 我不知道如何在Blend中禁用“编辑控件部件(模板)”菜单。 另一种方法是添加一个TemplatePart,但模板,因为不应该是Viewbox的接口开始,我们没有去这条路线。
- 因为儿童是通过在默认模板的ContentPresenter呈现,X:名字并不为子元素。 例如,如果你有像一个以上混合截图所示的XAML:<controls:Viewbox x:Name="vbx"> <Button x:Name="btn"> </控制:Viewbox的,你不能引用通过变量BTN按钮。 这是因为X:名称由InitializeComponent的实施产生* g.cs文件,像这样的代码:this.btn =((System.Windows.Controls.Button)(this.FindName(“BTN”))), FindName并不总是整个XAML名称COPES工作,所以BTN将永远是空的。
- 一个有趣的发现是子元素返回,有时像零DesiredSize,<图像源=“ http://silverlight.net/Themes/silverlight/images/logo.jpg “/>,所以Viewbox的计算零ScaleTransform,你赢了“T看到的图像。 并不总是重现,不知道为什么。
结论
无论如何,希望这有助于你使用Viewbox的,更重要的是,了解其执行情况,设计权衡和问题,因为已经有Silverlight工具包论坛的若干意见,要求有关上述副作用。 意见,反馈,建议,欢迎! 谢谢!
更新
- Silverlight的工具包 三月二零零九年推出 :要解决的XAML名称范围问题(x:名称并没有工作Viewbox的的子元素),我改变了Viewbox的ContentControl的,而不是控制的子类,因为ContentControl的是,其中Silverlight的XAML几个控件之一分析器允许名称范围和FindName工程,流动所以x:Viewbox的子元素的名称工程。 我也躲到从ContentControl的控制,并在设计时继承了额外的属性,这样的人不小心使用,并没有引起他们的代码移植到WPF或兼容未来Viewbox的实施。
- 在Silverlight 4工具包和运行时将Silverlight 4的测试版工具包2009年11月发行版 :Viewbox的动议,所以现在固定其实现(子类或ContentControl的控制)引起的所有问题。 Viewbox的Silverlight 3的实施保持不变。 下面是Viewbox的Silverlight 4中的实现:
)] [ContentProperty(“儿童”,TRUE)]
公共密封类 Viewbox的:FrameworkElement的
{
/ /字段
私有静态只读的DependencyProperty ChildProperty;
公共静态只读的DependencyProperty StretchDirectionProperty;
公共静态只读的DependencyProperty StretchProperty;
/ /方法
Viewbox的静态 ();
公共 Viewbox的();
/ /属性
公共 UIElement的儿童{;}
公共畦一畦{;}
的公共 StretchDirection StretchDirection {;设置;}
}








最新评论