当前位置: 首页 > news >正文

avalonia、WPF使用ScottPlot动态显示ECG心电图

文章目录

    • avalonia、WPF使用ScottPlot动态显示ECG心电图
    • 实现效果,动态效果懒得录视频了
    • 安装
    • 代码部分
    • UpdateData方法就是用来更新心电图表的方法, 根据消息队列数据去更新是视图中的ScottPlot 图表

avalonia、WPF使用ScottPlot动态显示ECG心电图

avalonia、WPF使用ScottPlot动态显示ECG心电图

实现效果,动态效果懒得录视频了

请添加图片描述

安装

1.安装ScottPlot.Avalonia NuGet包

注意:
如果开发环境是macos、linux,需要按照官网步骤配置环境
此处是官网配置链接

代码部分

view部分 注意安装包之后引入
xmlns:ScottPlot="clr-namespace:ScottPlot.Avalonia;assembly=ScottPlot.Avalonia"

<Window xmlns="https://github.com/avaloniaui"xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"xmlns:d="http://schemas.microsoft.com/expression/blend/2008"xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"mc:Ignorable="d" d:DesignWidth="1920" d:DesignHeight="600"xmlns:vm="using:AvaloniaMedical.ViewModels"x:Class="AvaloniaMedical.Views.xx"xmlns:ScottPlot="clr-namespace:ScottPlot.Avalonia;assembly=ScottPlot.Avalonia"x:DataType="vm:xx"xmlns:views="clr-namespace:AvaloniaMedical.Views"xmlns:i="clr-namespace:Avalonia.Xaml.Interactivity;assembly=Avalonia.Xaml.Interactivity"xmlns:controls1="clr-namespace:Material.Styles.Controls;assembly=Material.Styles"Background="#31363A">此处只显示三导心电<ScottPlot:AvaPlot Height="200"  Name="AvaPlotName1" Grid.Row="1" Grid.Column="0" ></ScottPlot:AvaPlot><ScottPlot:AvaPlot Height="200"  Name="AvaPlotName2" Grid.Row="2" Grid.Column="0" ></ScottPlot:AvaPlot><ScottPlot:AvaPlot Height="200" Name="AvaPlotName3" Grid.Row="3" Grid.Column="0" ></ScottPlot:AvaPlot>
</Window>
using System;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Diagnostics;
using System.Drawing;
using System.Threading;
using Avalonia;
using Avalonia.Controls;
using Avalonia.Data;
using Avalonia.Markup.Xaml;
using Avalonia.Threading;
using AvaloniaMedical.ViewModels;
using Npoi.Mapper;
using ScottPlot;
using ScottPlot.Avalonia;
using ScottPlot.Plottable;namespace AvaloniaMedical.Views;public partial class xx : Window
{private readonly double[] liveData = new double[4000];private readonly double[] liveData2 = new double[4000];private readonly double[] liveData3 = new double[4000];private readonly Timer _updateDataTimer;private readonly DispatcherTimer _renderTimer;private readonly VLine vline;private readonly VLine vline2;private readonly VLine vline3;int nextValueIndex = -1;int nextValueIndex2 = -1;int nextValueIndex3= -1;AvaPlot AvaPlot1;AvaPlot AvaPlot2;AvaPlot AvaPlot3;public xx(){InitializeComponent();#if DEBUGthis.AttachDevTools();
#endifAvaPlot1 = this.Find<AvaPlot>("AvaPlotName1");AvaPlot2 = this.Find<AvaPlot>("AvaPlotName2");AvaPlot3 = this.Find<AvaPlot>("AvaPlotName3");AvaPlot1.Plot.AddSignal(liveData, 1, color: Color.LightGreen);AvaPlot1.Plot.AxisAutoX(margin: 0);AvaPlot1.Plot.SetAxisLimits(yMin: 2, yMax:7);AvaPlot2.Plot.AddSignal(liveData2, 1, color: Color.LightGreen);AvaPlot2.Plot.AxisAutoX(margin: 0);AvaPlot2.Plot.SetAxisLimits(yMin: 2, yMax: 7);AvaPlot3.Plot.AddSignal(liveData3, 1, color: Color.LightGreen);AvaPlot3.Plot.AxisAutoX(margin: 0);AvaPlot3.Plot.SetAxisLimits(yMin: 2, yMax: 7);vline = AvaPlot1.Plot.AddVerticalLine(0, Color.LightGreen, 1);vline2 = AvaPlot2.Plot.AddVerticalLine(0, Color.LightGreen, 1);vline3 = AvaPlot3.Plot.AddVerticalLine(0, Color.LightGreen, 1);///Binding binding = new Binding();binding.Source = AvaPlot1;binding.Path = new ropertyPath();AvaPlot1.SetValue(TagProperty, 0);AvaPlot1.Plot.Style(Style.Gray1); AvaPlot2.Plot.Style(Style.Gray1); AvaPlot3.Plot.Style(Style.Gray1); customize styling//AvaPlot1.Plot.Title("Electrocardiogram Strip Chart");AvaPlot1.Plot.Grid(true);AvaPlot2.Plot.Grid(true);AvaPlot3.Plot.Grid(true);// create a traditional timer to update the data//_updateDataTimer = new Timer(_ => UpdateData(), null, 0, 1); create a separate timer to update the GUI_renderTimer = new DispatcherTimer{Interval = TimeSpan.FromMilliseconds(1)};_renderTimer.Tick += Render;_renderTimer.Start();Closed += (sender, args) =>{_updateDataTimer?.Dispose();_renderTimer?.Stop();};}public void UpdateChart(double dto){UpdateData(dto);}public void UpdateChart2(double dto){UpdateData2(dto);}public void UpdateChart3(double dto){UpdateData3(dto);}void UpdateData(double dto){// "scroll" the whole chart to the left// Array.Copy(liveData, 1, liveData, 0, liveData.Length - 1);// place the newest data point at the enddouble nextValue = dto;nextValueIndex = (nextValueIndex < liveData.Length - 1) ? nextValueIndex + 1 : 0;liveData[nextValueIndex] = nextValue;vline.IsVisible = true;vline.X = nextValueIndex;}void UpdateData2(double dto){// "scroll" the whole chart to the left// Array.Copy(liveData, 1, liveData, 0, liveData.Length - 1);// place the newest data point at the enddouble nextValue = dto;nextValueIndex2 = (nextValueIndex2 < liveData2.Length - 1) ? nextValueIndex2 + 1 : 0;liveData2[nextValueIndex2] = nextValue;vline2.IsVisible = true;vline2.X = nextValueIndex2;}void UpdateData3(double dto){// "scroll" the whole chart to the left// Array.Copy(liveData, 1, liveData, 0, liveData.Length - 1);// place the newest data point at the enddouble nextValue = dto;nextValueIndex3 = (nextValueIndex3 < liveData3.Length - 1) ? nextValueIndex3 + 1 : 0;liveData3[nextValueIndex3] = nextValue;vline3.IsVisible = true;vline3.X = nextValueIndex3;}void Render(object sender, EventArgs e){AvaPlot1.Refresh();AvaPlot2.Refresh();AvaPlot3.Refresh();}private void InitializeComponent(){AvaloniaXamlLoader.Load(this);}protected override void OnClosing(CancelEventArgs e){this.Hide();base.OnClosing(e);}}

UpdateData方法就是用来更新心电图表的方法, 根据消息队列数据去更新是视图中的ScottPlot 图表

相关文章:

avalonia、WPF使用ScottPlot动态显示ECG心电图

文章目录 avalonia、WPF使用ScottPlot动态显示ECG心电图实现效果&#xff0c;动态效果懒得录视频了安装代码部分UpdateData方法就是用来更新心电图表的方法&#xff0c; 根据消息队列数据去更新是视图中的ScottPlot 图表 avalonia、WPF使用ScottPlot动态显示ECG心电图 avalonia…...

国内数学公式识别软件对比

1. 超级公式 官网 https://www.ocrmath.com/ 目前超级公式最好用 2. 极度公式 官网 https://jidugs.wrste.com/ 季度公式也还可以&#xff0c;之前提了一些改进用户建议&#xff0c;很久都不改&#xff0c;遂改用超级公式 3. SimpleTex 官网 https://simpletex.cn/ 最近才…...

SCOPE_IDENTITY什么意思

在关系型数据库中&#xff0c;SCOPE_IDENTITY()是一个用于获取最近插入的行的自增标识列值的函数。当向数据库表中插入一行数据时&#xff0c;如果表中的某列被配置为自增标识列&#xff08;通常是主键列&#xff09;&#xff0c;数据库会自动为每个插入的行分配一个唯一的值&a…...

构建现代应用:Java中的热门架构概览

文章目录 1. 三层架构2. Spring框架3. 微服务架构4. Java EE&#xff08;Enterprise Edition&#xff09;5. 响应式架构6. 大数据架构7. 领域驱动设计&#xff08;Domain-Driven Design&#xff0c;DDD&#xff09;8. 安卓开发架构结论 &#x1f389;欢迎来到Java学习路线专栏~…...

Axure RP软件安装包分享(附安装教程)

目录 一、软件简介 二、软件下载 一、软件简介 Axure RP是一款专业的原型设计工具&#xff0c;它能够帮助用户创建高保真度的交互式原型。 Axure RP具有以下特点&#xff1a; 强大的交互设计功能&#xff1a;Axure RP提供了丰富的交互设计工具&#xff0c;用户可以通过拖拽和…...

关于微信小程序的生命周期

关于微信小程序的生命周期 onLaunch 官网App.vue/App.uvue | uni-app官网 问题描述&#xff1a;我现在有个小程序 取名为a 有个用户b 从来没有打开过小程序 那么他第一次打开小程序的时候会触发onLaunch 然后用户b退出了小程序 那么用户 b重新打开小程序的时候会触发 onL…...

【数据结构】带头双向循环链表及其实现

目录 1.带头双向循环链表 2.带头双向循环链表实现 2.1初始化 2.2销毁 2.3头插 2.4链表打印 2.5头删数据 2.6尾插数据 2.7尾删数据 2.8链表判空 2.9查找一个数据 2.10在pos位置前插入数据 2.11删除pos位置 2.12求链表的长度 2.顺序表和链表的比较 1.带头双向循环…...

问道管理:日换手率达20是好是坏?

关于股票商场的出资者而言&#xff0c;日换手率是一个非常重要的目标。日换手率是指股票当日买卖量与该股总股本之比。假如一只股票的日换手率过高&#xff0c;那么就意味着该股票的流动性较强&#xff0c;而假如日换手率过低&#xff0c;那么就意味着该股票的流动性较弱。 那…...

勃艮第葡萄酒是如何分级的?

勃艮第葡萄酒来自一个同名的地区:勃艮第&#xff0c;它位于法国中东部&#xff0c;在西部的卢瓦尔河和东部的索恩河之间。该地区最大的城市是欧塞尔、第戎、马孔和内韦尔。由于地处国家中心&#xff0c;勃艮第属于大陆性气候&#xff0c;夏季炎热&#xff0c;冬季寒冷。这种气候…...

使用awvs进行web安全扫描

1、安装 docker pull secfa/docker-awvs docker run -it -d -name awvs -p 13443:3443 --cap-add LINUX_IMMUTABLE secfa/docker-awvs2、账号密码 # https://ip:13443/ # 用户名:adminadmin.com # 密码:Admin1233、使用 ps:需要征得甲方的同意...

抖音小程序开发教学系列(1)- 抖音小程序简介

章节一&#xff1a;抖音小程序简介 1.1 抖音小程序的背景和概述 抖音小程序的发展背景和市场趋势&#xff1a; 抖音作为一款热门的短视频社交平台&#xff0c;用户群体庞大&#xff0c;社交共享的特性也为小程序的发展提供了广阔的空间。抖音小程序作为抖音在社交和用户粘性…...

【4.Vue兄弟组件之间传值-Bus总线】

1.概述 通过创建一个新的vm对象,专门统一注册事件,供所有组件共同操作,达到所有组件随意隔代传值的效果 也就是:各个组件内部要传输的数据或者要执行的命令信息,靠bus来通信。 2. 代码实现 2.1 全局引入 全局引入的话,就直接在main.js里面引入即可: // 创建 bus总线 V…...

element中Notification组件(this.$notify)自定义样式

1、自定义样式效果 2、vue代码 this.notifications this.$notify({title: ,dangerouslyUseHTMLString: true,duration: obj.remindMethod3 ? 0:4500,customClass: notify-warning,offset: 50,showClose: false,message: this.$createElement("div",null,[this.$…...

Manjaro安装使用

Manjaro安装使用 1.先更改镜像源&#xff1a;sudo pacman-mirrors -c China -g 2.安装第三方软件管理工具 &#xff1a;sudo pacman -Sy yay 导入GPG Key sudo pacman -Syy && sudo pacman -S archlinuxcn-keyring安装输入法 sudo pacman -S fcitx-im (#默认全部安装…...

【iOS】折叠cell

文章目录 前言一、实现效果二、折叠cell的实现原理三、实现折叠cell的高度变化四、实现选中点击的单元格总结 前言 在暑假的3GShare中用到了折叠cell控件&#xff0c;特此总结博客记录 一、实现效果 二、折叠cell的实现原理 首先我们需要知道ScrollView的是TableView的父类&a…...

无涯教程-Android - DatePicker函数

Android Date Picker允许您在自定义用户界面中选择由日,月和年组成的日期。为此功能,android提供了DatePicker和DatePickerDialog组件。 在本教程中,我们将通过DatePickerDialog演示日期选择器的用法, DatePickerDialog是一个包含DatePicker的简单对话框。 为了显示DatePicker…...

经纬恒润荣获吉利汽车“最佳价值贡献”奖

8月18日&#xff0c;以“全面向新 共创共赢”为主题&#xff0c;吉利汽车在宁波成功举行2023年电子电器核心供应商恳谈会。经纬恒润凭借在项目合作上持续创新、高效协同等优异表现&#xff0c;获得“最佳价值贡献”奖项。 作为国产汽车代表性品牌之一&#xff0c;吉利汽车积极推…...

【多线程】lock与synchronized的区别

相同点&#xff1a; 1、他们都是Java中用于解决线程安全的工具&#xff0c;两者的性能相差不大 不同点&#xff1a; 1、在实现上synchronized引入了偏向锁、轻量级锁、重量级锁、锁升级来优化加锁的性能&#xff0c;而lock则使用自旋锁来实现性能的优化 2、synchronized是J…...

什么是RTC

参考&#xff1a; https://zhuanlan.zhihu.com/p/377100294 RTC&#xff08;Real time communication&#xff09;实时通信&#xff0c;是实时音视频的一个简称&#xff0c;我们常说的RTC技术一般指的是WebRTC技术&#xff0c;已经被 W3C 和 IETF 发布为正式标准。由于几乎所…...

BW 源/目标模型主键不一样,增量的作用

最近项目上&#xff0c;做了一个复杂的需求逻辑&#xff0c;源模型到目标模型&#xff0c;主键完全发生了变化。用转换的传统功能&#xff0c;我担心处理起来不方便就使用了专家历程&#xff08;这个说明在之前有说过&#xff09;。 项目上线后&#xff0c;发生很多异常事件。但…...

UE5 学习系列(二)用户操作界面及介绍

这篇博客是 UE5 学习系列博客的第二篇&#xff0c;在第一篇的基础上展开这篇内容。博客参考的 B 站视频资料和第一篇的链接如下&#xff1a; 【Note】&#xff1a;如果你已经完成安装等操作&#xff0c;可以只执行第一篇博客中 2. 新建一个空白游戏项目 章节操作&#xff0c;重…...

【根据当天日期输出明天的日期(需对闰年做判定)。】2022-5-15

缘由根据当天日期输出明天的日期(需对闰年做判定)。日期类型结构体如下&#xff1a; struct data{ int year; int month; int day;};-编程语言-CSDN问答 struct mdata{ int year; int month; int day; }mdata; int 天数(int year, int month) {switch (month){case 1: case 3:…...

iOS 26 携众系统重磅更新,但“苹果智能”仍与国行无缘

美国西海岸的夏天&#xff0c;再次被苹果点燃。一年一度的全球开发者大会 WWDC25 如期而至&#xff0c;这不仅是开发者的盛宴&#xff0c;更是全球数亿苹果用户翘首以盼的科技春晚。今年&#xff0c;苹果依旧为我们带来了全家桶式的系统更新&#xff0c;包括 iOS 26、iPadOS 26…...

CentOS下的分布式内存计算Spark环境部署

一、Spark 核心架构与应用场景 1.1 分布式计算引擎的核心优势 Spark 是基于内存的分布式计算框架&#xff0c;相比 MapReduce 具有以下核心优势&#xff1a; 内存计算&#xff1a;数据可常驻内存&#xff0c;迭代计算性能提升 10-100 倍&#xff08;文档段落&#xff1a;3-79…...

OkHttp 中实现断点续传 demo

在 OkHttp 中实现断点续传主要通过以下步骤完成&#xff0c;核心是利用 HTTP 协议的 Range 请求头指定下载范围&#xff1a; 实现原理 Range 请求头&#xff1a;向服务器请求文件的特定字节范围&#xff08;如 Range: bytes1024-&#xff09; 本地文件记录&#xff1a;保存已…...

PL0语法,分析器实现!

简介 PL/0 是一种简单的编程语言,通常用于教学编译原理。它的语法结构清晰,功能包括常量定义、变量声明、过程(子程序)定义以及基本的控制结构(如条件语句和循环语句)。 PL/0 语法规范 PL/0 是一种教学用的小型编程语言,由 Niklaus Wirth 设计,用于展示编译原理的核…...

云原生玩法三问:构建自定义开发环境

云原生玩法三问&#xff1a;构建自定义开发环境 引言 临时运维一个古董项目&#xff0c;无文档&#xff0c;无环境&#xff0c;无交接人&#xff0c;俗称三无。 运行设备的环境老&#xff0c;本地环境版本高&#xff0c;ssh不过去。正好最近对 腾讯出品的云原生 cnb 感兴趣&…...

LeetCode - 199. 二叉树的右视图

题目 199. 二叉树的右视图 - 力扣&#xff08;LeetCode&#xff09; 思路 右视图是指从树的右侧看&#xff0c;对于每一层&#xff0c;只能看到该层最右边的节点。实现思路是&#xff1a; 使用深度优先搜索(DFS)按照"根-右-左"的顺序遍历树记录每个节点的深度对于…...

基于 TAPD 进行项目管理

起因 自己写了个小工具&#xff0c;仓库用的Github。之前在用markdown进行需求管理&#xff0c;现在随着功能的增加&#xff0c;感觉有点难以管理了&#xff0c;所以用TAPD这个工具进行需求、Bug管理。 操作流程 注册 TAPD&#xff0c;需要提供一个企业名新建一个项目&#…...

Mysql8 忘记密码重置,以及问题解决

1.使用免密登录 找到配置MySQL文件&#xff0c;我的文件路径是/etc/mysql/my.cnf&#xff0c;有的人的是/etc/mysql/mysql.cnf 在里最后加入 skip-grant-tables重启MySQL服务 service mysql restartShutting down MySQL… SUCCESS! Starting MySQL… SUCCESS! 重启成功 2.登…...