前言
随着国产化和跨平台开发需求的不断增长,越来越多的工业上位机应用开始从传统的 WinForm/WPF 向跨平台框架迁移。Avalonia 作为一款功能强大、兼容 WPF 语法的跨平台 UI 框架,正逐渐成为 .NET 开发的首选。
本文将带你使用 Avalonia 开发一个模拟水泵运行状态的自定义控件,重点讲解如何实现旋转动画、使用伪类控制状态,并分享开发过程中遇到的"坑"与解决方案,为工业可视化控件开发提供实用参考。
效果图
正文
在工业监控系统中,水泵、电机、风机等设备的动态状态展示是上位机界面的重要组成部分。通过动画直观地反映设备运行状态,不仅能提升用户体验,还能帮助操作人员快速判断系统工况。
本文以"水泵控件"为例,展示如何在 Avalonia 中实现一个具有旋转动画的可复用控件。
1、控件的构成
水泵控件的核心是一个中间可旋转的圆形部分,用于模拟水泵叶轮的运转。为了简化动画实现,我们使用一个 Canvas 容器将需要旋转的 Path 图形包裹起来。
这样,动画只需作用于 Canvas,避免了直接旋转 Path 时因坐标系问题难以确定旋转中心的复杂性。
以下是控件的核心 XAML 结构:
<Canvas
Canvas.Left="19.5"
Canvas.Top="39.5"
Height="34.5"
Name="BumpCircle"
UseLayoutRounding="False"
Width="34.2">
<Path
Fill="#ffffffff"
Stroke="#ff6c6c6c"
StrokeJoin="Miter"
StrokeThickness="2.05166">
<Path.Data>
<PathGeometry Figures="M 11.3573 15.4557 C 6.78011 13.3704 4.04416 9.6096 3.14943 4.1733 M 11.3573 19.7314 C 6.82241 21.3797 2.37649 20.6383 -1.98048 17.5071 M 15.4612 22.6354 C 13.3753 27.2112 9.61334 29.9464 4.17541 30.8408 M 19.7381 22.6354 c 1.64889 4.53351 0.907239 8.97809 -2.22494 13.3338 m 5.12991 -17.4365 c 4.57717 2.08531 7.31313 5.84611 8.20786 11.2824 M 22.6431 14.2571 c 4.53487 -1.64839 8.98079 -0.906966 13.3378 2.22428 M 18.5392 11.353 c 2.08594 -4.5758 5.84787 -7.31093 11.2858 -8.20539 m -15.5627 8.20539 c -1.64889 -4.53351 -0.907239 -8.97809 2.22494 -13.3338 m 4.50314 14.9864 c 2.20369 2.20302 2.20369 5.77484 0 7.97786 c -2.20369 2.20302 -5.77658 2.20302 -7.98027 0 c -2.20369 -2.20302 -2.20369 -5.77484 0 -7.97786 c 2.20369 -2.20302 5.77658 -2.20302 7.98027 0 m 9.43124 -9.4284 c 7.41241 7.41018 7.41241 19.4245 0 26.8347 c -7.41241 7.41019 -19.4304 7.41019 -26.8428 0 c -7.41241 -7.41018 -7.41241 -19.4245 0 -26.8347 c 7.41241 -7.41019 19.4304 -7.41019 26.8428 0" />
</Path.Data>
</Path>
</Canvas>
2、动画的创建
Avalonia 支持基于 CSS 样式的动画定义。我们通过伪类 running 来标识水泵的运行状态。动画的 Selector 使用了层级选择语法:
<Style Selector="controls|Pump.running">
<Style Selector="^ /template/ Canvas#BumpCircle">
<Style.Animations>
<Animation Duration="0:0:5" IterationCount="INFINITE">
<KeyFrame Cue="0%">
<Setter Property="RotateTransform.Angle" Value="0" />
</KeyFrame>
<KeyFrame Cue="100%">
<Setter Property="RotateTransform.Angle" Value="360" />
</KeyFrame>
</Animation>
</Style.Animations>
</Style>
</Style>
-
controls|Pump.running:选择Pump控件且处于running伪类状态。 -
^ /template/ Canvas#BumpCircle:继承上层选择器,并进入控件模板内部,选择名为BumpCircle的Canvas。 -
动画从 0° 旋转到 360°,持续 5 秒,无限循环。
3、踩到的坑与解决方案
(1)自定义伪类的 Selector 写法
Avalonia 内置伪类如 :pointerover 使用冒号前缀,但自定义伪类在 Style Selector 中应直接使用点号连接,如 Pump.running,而非 Pump:running。
(2)属性变更时动态更新伪类
最初尝试在 Running 属性的 set 方法中添加/移除伪类,但通过绑定(如 {Binding #CheckBox.IsChecked})更新属性时,set 方法不会被调用。
正确的做法是重写 OnPropertyChanged 方法,监听 RunningProperty 的变化:
protected override void OnPropertyChanged(AvaloniaPropertyChangedEventArgs change)
{
base.OnPropertyChanged(change);
if (change.Property == RunningProperty)
{
if (change.NewValue != null && (bool)change.NewValue)
{
PseudoClasses.Add("running");
}
else
{
PseudoClasses.Remove("running");
}
}
}
这种方式确保了无论属性如何变更(直接赋值或通过绑定),都能正确触发伪类的更新,从而启动或停止动画。
总结
本文通过开发一个 Avalonia 水泵控件,系统性地介绍了跨平台上位机控件开发的关键技术:使用 Canvas 简化动画实现、通过伪类管理控件状态、利用 OnPropertyChanged 响应属性变更。这些技巧不仅适用于水泵控件,也可推广至电机、阀门、传送带等其他动态工业控件的开发。Avalonia 的强大样式系统和跨平台能力,为构建现代化、高性能的工业上位机界面提供了坚实基础。希望本文能为大家的跨平台开发之旅提供有价值的参考。
关键词
Avalonia、跨平台开发、上位机、控件开发、水泵动画、旋转动画、伪类、OnPropertyChanged、Canvas、Selector、工业可视化
最后
如果你觉得这篇文章对你有帮助,不妨点个赞支持一下!你的支持是我继续分享知识的动力。如果有任何疑问或需要进一步的帮助,欢迎随时留言。
也可以加入微信公众号 [DotNet技术匠] 社区,与其他热爱技术的同行一起交流心得,共同成长!
优秀是一种习惯,欢迎大家留言学习!
作者: 智汇IOT
出处:cnblogs.com/Cookies-Tang/p/18522958
声明:网络内容,仅供学习,尊重版权,侵权速删,歉意致谢!