SkiaSharp 之 WPF 自绘 五环弹动球(案例版)

此案例基于拖曳和弹动球两个技术功能实现,如有不懂的可以参考之前的相关文章,属于递进式教程。

五环弹动球

好吧,名字是我起的,其实,你可以任意个球进行联动弹动,效果还是很不错的,有很多前端都是基于这个特效,可以搞出一些很有科技感的效果出来。

Wpf 和 SkiaSharp

新建一个WPF项目,然后,Nuget包即可 要添加Nuget包

Install-Package SkiaSharp.Views.WPF -Version 2.88.0

其中核心逻辑是这部分,会以我设置的60FPS来刷新当前的画板。

skContainer.PaintSurface += SkContainer_PaintSurface;
_ = Task.Run(() =>
{while (true){try{Dispatcher.Invoke(() =>{skContainer.InvalidateVisual();});_ = SpinWait.SpinUntil(() => false, 1000 / 60);//每秒60帧}catch{break;}}
});

弹球实体代码 (Ball.cs)

public class Ball
{public double X { get; set; }public double Y { get; set; }public double VX { get; set; }public double VY { get; set; }public int Radius { get; set; }public bool Dragged { get; set; } = false;public SKColor sKColor { get; set; } = SKColors.Blue;public bool CheckPoint(SKPoint sKPoint){var d = Math.Sqrt(Math.Pow(sKPoint.X - X, 2) + Math.Pow(sKPoint.Y - Y, 2));return this.Radius >= d;}
}

五环弹动核心类 (FiveRings.cs)

/// <summary>
/// 五环弹球
/// </summary>
public class FiveRings
{public SKPoint centerPoint;public int Radius = 0;public int BallLength = 8;public double TargetX;public double Spring = 0.03;public double SpringLength = 200;public double Friction = 0.95;public List<Ball>? Balls;public Ball? draggedBall;public void init(SKCanvas canvas, SKTypeface Font, int Width, int Height){if (Balls == null){Balls = new List<Ball>();for (int i = 0; i < BallLength; i++){Random random = new Random((int)DateTime.Now.Ticks);Balls.Add(new Ball(){X = random.Next(50, Width - 50),Y = random.Next(50, Height - 50),Radius = this.Radius});}}}/// <summary>/// 渲染/// </summary>public void Render(SKCanvas canvas, SKTypeface Font, int Width, int Height){centerPoint = new SKPoint(Width / 2, Height / 2);this.Radius = 20;this.TargetX = Width / 2;init(canvas, Font, Width, Height);canvas.Clear(SKColors.White);//划线using var LinePaint = new SKPaint{Color = SKColors.Green,Style = SKPaintStyle.Fill,StrokeWidth = 3,IsStroke = true,StrokeCap = SKStrokeCap.Round,IsAntialias = true};SKPath path = null;foreach (var item in Balls){if (path == null){path = new SKPath();path.MoveTo((float)item.X, (float)item.Y);}else{path.LineTo((float)item.X, (float)item.Y);}}path.Close();canvas.DrawPath(path, LinePaint);foreach (var item in Balls){if (!item.Dragged){foreach (var ball in Balls.Where(t => t != item).ToList()){SpringTo(item, ball);}}DrawCircle(canvas, item);}using var paint = new SKPaint{Color = SKColors.Blue,IsAntialias = true,Typeface = Font,TextSize = 24};string by = $"by 蓝创精英团队";canvas.DrawText(by, 600, 400, paint);}/// <summary>/// 画一个圆/// </summary>public void DrawCircle(SKCanvas canvas, Ball ball){using var paint = new SKPaint{Color = SKColors.Blue,Style = SKPaintStyle.Fill,IsAntialias = true,StrokeWidth = 2};canvas.DrawCircle((float)ball.X, (float)ball.Y, ball.Radius, paint);}public void MouseMove(SKPoint sKPoint){if (draggedBall != null){draggedBall.X = sKPoint.X;draggedBall.Y = sKPoint.Y;}}public void MouseDown(SKPoint sKPoint){foreach (var item in Balls){if (item.CheckPoint(sKPoint)){item.Dragged = true;draggedBall = item;}else{item.Dragged = false;}}}public void MouseUp(SKPoint sKPoint){draggedBall = null;foreach (var item in Balls){item.Dragged = false;}}public void SpringTo(Ball b1, Ball b2){var dx = b2.X - b1.X;var dy = b2.Y - b1.Y;var angle = Math.Atan2(dy, dx);var targetX = b2.X - SpringLength * Math.Cos(angle);var targetY = b2.Y - SpringLength * Math.Sin(angle);b1.VX += (targetX - b1.X) * Spring;b1.VY += (targetY - b1.Y) * Spring;b1.VX *= Friction;b1.VY *= Friction;b1.X += b1.VX;b1.Y += b1.VY;}
}

效果如下:

68b87318e5d56d2d9ddc196544bcf5df.gif

这个特效用的好,也能产生一些神奇的效果。

总结

这次是结合拖曳和弹动效果实现的综合案例,效果还是很不错的,之前也没想到原来还可以这样玩,拓展了玩法啊。

代码地址

https://github.com/kesshei/WPFSkiaFiveRingsDemo.git

https://gitee.com/kesshei/WPFSkiaFiveRingsDemo.git

一键三连呦!,感谢大佬的支持,您的支持就是我的动力!

版权

蓝创精英团队(公众号同名,CSDN同名,CNBlogs同名)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/284141.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【GlobalMapper精品教程】032:浏览地理照片及航线信息(航测应用)

本文讲述globalmapper软件在无人机航测了内业处理中的应用之:浏览地理照片及航线信息、相机参数、元数据编辑器。 文章目录 1. 航线信息浏览2. 地理图像浏览2.1 数字化工具2.2 要素信息工具2.3 属性表3. 照片原数据编辑1. 航线信息浏览 打开globalmapper软件,加载无人机航测…

【GlobalMapper精品教程】031:Globalmapper在航测内业数据处理中的应用举例

Globalmapper在航测内业数据处理中的应用举例索引。 文章目录 1. 图像及航线浏览2. 3D重建3. 点云分类4. 创建地形5. 地形分析1. 图像及航线浏览 扩展阅读:【GlobalMapper精品教程】032:浏览地理照片及航线信息(航测应用) 2. 3D重建 从Global Mapper的19版本开始,Pixels-…

移动工具V和选区工具M

移动工具快捷键&#xff1a;V 属性&#xff1a; 自动选择 在默认情况下&#xff0c;移动工具的“自动选择”一项是没有勾选的。表示只能选中图层窗口中选定的固定图层&#xff0c;不能随意的点击选择别的图层。在这里&#xff0c;我们也勾选“自动选择”&#xff0c;可任意选择…

SeleniumWebDriver扩展插件开发

Selenium WebDriver 是一组开源 API&#xff0c;用于自动测试 Web 应用程序&#xff0c;利用它可以通过代码来控制chrome edge等浏览器&#xff01;有时候我们需要mock接口的返回&#xff0c;或者拦截和转发请求&#xff0c;今天就来实现这个功能本插件代码已开源&#xff1a;h…

[转]钱岭:别担心“35岁危机”,要成为“老专家”

从清华大学到贝尔实验室&#xff0c;再到中国移动&#xff0c;作为“IT老人”&#xff0c;钱岭的技术人生几乎覆盖了20世纪90年代至今的信息产业革命。2007年开始&#xff0c;钱岭在中国移动经历了基础科研到产品落地&#xff0c;再到团队孵化&#xff1b;也经历了云计算从无到…

【GIS前沿】周成虎院士:GIS的大数据时代展望(PPT分享)

本文源自微信公众号&#xff1a;宋关福GIS笔记。版权归原作者及刊载媒体所有&#xff0c;如有侵权请立即与我们联系,我们将及时处理。更多GIS前言技术&#xff0c;请关注《GIS前言》专栏。 GIS的大数据时代展望

DataV:可视化大屏展示神器实战分享

由于公司年即将发布新的产品&#xff0c;传统意义上的PPT显得不太生动化&#xff0c;所以想采用具体化&#xff0c;可视化的数据大屏进行业务数据的事实展示&#xff0c;第一时间想到了来自于阿里云旗下的DataV&#xff0c;废话不多说&#xff0c;老司机开始发牌照&#xff01;…

数据库性能系列之索引(中)

GOOD NIGHT前言上一篇中&#xff0c;我们已经了解到了索引的基本概念和一些用法。那索引为什么会提升查询的速度&#xff0c;以及索引究竟是怎么工作的呢&#xff1f;也许大家心里还是有一些迷茫&#xff0c;这一切&#xff0c;还要从索引背后的算法说起。GOOD NIGHT概述大家知…

微服务架构的设计原则和核心话题

目录 一、前言 二、微服务架构的设计原则 1.拆分足够微 2.轻量级通信 3.单一职责原则 4.领域驱动原则 三、微服务架构的核心话题 1.服务拆分 2.服务注册与发现 3.负载均衡 4.API网关 5.服务部署与发布 四、总结 一、前言 毫无疑问&#xff0c;微服务架构的设计原…

Golang GOPATH 包

2019独角兽企业重金招聘Python工程师标准>>> Golang GOPATH & 包的定义 & 包的导入 GOPATH 设置 go 命令依赖一个重要的环境变量&#xff1a;$GOPATH 可以在 .zshrc 配置文件中加上一行这样的配置&#xff0c; export GOPATH/Users/flyme/mygo Go从1.1版本到…

PPK大疆无人机应用教程

文章目录 一、新建项目二、导入数据三、解算过程四、结果导出一、新建项目 新建工程,设置项目名称,保存位置,控制等级,坐标系统(坐标系统选择高斯克吕格,中央子午线根据实际数据所在位置进行选择) 二、导入数据 选择大疆数据,找到对应的文件夹 数据有:图片,EVENT.b…

Eclipse Add generated serial version ID报错解决方案

为什么80%的码农都做不了架构师&#xff1f;>>> 问题&#xff1a; The following problem occurred:Could not find class file.Make sure the file is compilable 解决方案&#xff1a; 1、右键项目 -> Java Build Path -> Source 在Sourcd folders on bui…

C# WPF设备监控软件(经典)-上篇

01—前言应老东家也是老同学的需求&#xff0c;开发了此设备监控软件。主要是为了应对测试设备长时间不上传测试数据未能及时发现的问题&#xff0c;测试数据一般在每台设备都有个固定的临时存放目录&#xff0c;测试数据不更新时&#xff0c;此文件夹便不再更新。需求相对比较…

[转]微服务的4个设计原则和19个解决方案

目录 一、微服务架构演进过程 二、微服务架构的好处 三、微服务应用4个设计原则 1.AKF拆分原则 2.前后端分离 3.无状态服务 4.Restful通信风格 四、微服务架构带来的问题 五、微服务平台的19个落地实践 1.企业IT建设的三大基础环境 2.微服务应用平台总体架构 3.微服…

【GlobalMapper精品教程】033:影像地图羽化方式详解

在Globalmapper中,可以很方便的对影响进行多种羽化值设置。 文章目录 1. 不要羽化此图层2. 沿一个或多个边缘羽化3. 羽化到有效数据的多边形覆盖4. 在当前选定的多边形内羽化5. 裁剪到选定的边界,而不是羽化6. 在多边形外部羽化,而不是内部加载配套案例数据包中的data033.ra…

基于WPF重复造轮子,写一款数据库文档管理工具(一)

项目背景公司业务历史悠久且复杂&#xff0c;数据库的表更是多而繁杂&#xff0c;每次基于老业务做功能开发都需要去翻以前的表和业务代码。需要理解旧的表的用途以及包含的字段的含义&#xff0c;表少还好说&#xff0c;但是表一多这就很浪费时间&#xff0c;而且留下来的文档…

[转]GitBook使用教程收藏

GitBook使用教程 最简单的方式就是使用GitBook编辑器&#xff0c;没有什么难度&#xff0c;后面的教程主要针对命令行的方式 PS&#xff1a;GitBook的book页面默认没有download按钮的 需要到设置中打开&#xff0c;打开后再次publish生效 同步GitHub 更新失败&#xff0c;无法…

二 面向对象三大特性

一 继承与派生 一、继承定义 二、继承与抽象的关系 三、继承与重用性 四、派生 五、组合与重用性 六、接口与归一化设计 七、抽象类 八、继承实现的原理 九、子类中调用父类的方法 二 多态与多态性 一、多态 二、多态性 三 封装 一、封装定义 二、特性(property) 三、封装与扩展…

CSS3新属性

边框&#xff1a; border-radius 用于创建圆角 div { border:2px solid; border-radius:25px; -moz-border-radius:25px; /* Old Firefox */ } box-shadow 用于向方框添加阴影 div { box-shadow: 10px 10px 5px #888888; } border-image 使用图片来创建边框 div { border-image…

Android实用笔记——使用Spinner实现下拉列表

2019独角兽企业重金招聘Python工程师标准>>> 1、编辑activity_main.xml <?xml version"1.0" encoding"utf-8"?> <LinearLayout xmlns:android"http://schemas.android.com/apk/res/android"android:layout_width"mat…