- 博客(27)
- 收藏
- 关注
原创 C#处理医学影像(四):基于Stitcher算法拼接人体全景脊柱骨骼影像
在拍摄脊柱或胸片时,经常会遇到因设备高度不够需要分段拍摄的情况,对于影像科诊断查阅影像时希望将分段影像合并成一张影像,有助于更直观的观察病灶,以下图为例的两个分段影像:我们使用OpenCVSharp中的Stitcher类的Stitch方法,导入两张图像并拼接:但结果却失败了,返回错误结果:ERR_NEED_MORE_IMGS,是由于医学影像的特征点匹配不够,导致无法确定对接点。一幅图中总存在着一些独特的像素点,这些点我们可以认为就是这幅图的特征,即为特征点。
2023-05-05 15:21:17 1042
原创 C#开发PACS医学影像三维重建(十四):基于能量模型算法将曲面牙床展开至二维平面
在医学影像领域中,将三维重建中的人体组织展开平铺至二维,用来研判病灶和制定治疗方案的重要手段之一,众所周知,人体牙床正常情况下是有弧度的,无论是从俯视位还是冠状位观察都是不能直观的了解牙齿状况,同理,还可以应用到血管和骨骼的平铺展开,更好的观察血管阻塞和破裂、骨折骨裂等情况。牙床全景图、平铺血管、骨骼二维化展开(肋骨平铺)。③迭代应变能量释放法。
2023-05-05 01:49:01 933 1
原创 C#开发PACS医学影像三维重建(十三):基于人体CT值从皮肤渐变到骨骼的梯度透明思路
然而,当病灶介于两个CT值范围中间或重合时,要观察病灶这将是一个非常困难的工作,需要手动旋转、切割等一系列操作,当我们对三维体使用鼠标操作时,将CT值从最小值到最大值映射到三维体上面,并将透明度从0到100渐变,当我们将CT切片重建为三维体之后,通常会消除一些不必要的外部组织来观察内部病灶,当梯度大小在20-30之间时,不透明度乘子通过线性映射至0.5-1.0之间;梯度大小在10-20时,不透明度乘子通过线性映射至0-0.5之间的数值;但这是非黑即白的,即,要么显示皮肤,要么显示神经,要么显示骨骼…
2023-05-05 01:47:43 1187
原创 C#处理医学影像(三):基于漫水边界自动选取病灶范围的实现思路
通过给定指定的中心坐标,和指定染色的颜色值,向四周扩撒,遇到一样或近似值将其包含在范围内,网上源码很多,很容易实现。其中直观区别是canny算子计算的结果清晰,但不连续,容易受噪点影响,而sobel算子线条相对柔和,连续性强。医生在实际使用PACS软件观察病灶时,经常会测量不规则病灶的周长和面积,使用画笔工具勾勒比较耗时且准度欠佳,这些点是不连续的,不首尾相连的,我们需要将非边缘坐标删除,并将边缘坐标按顺时针或逆时针排序;将漫水填充范围的最大外接矩形裁剪出来,提高后续计算效率。
2023-05-05 01:45:15 444
原创 C#开发医学影像胶片打印系统(一):万能花式布局的实现思路
本篇文章将介绍开发医学影像胶片打印系统(printscu模式)遇到不规则排版时的一种思路,一般来讲,医院打印胶片时都是整张胶片打印,但有时需要将多个病人或一个病人的多个检查打印在同一张胶片上,这时候就需要不规则排版来满足打印需求,使胶片利用率最大化。
2023-05-05 01:43:46 914
原创 C#处理医学图像(二):基于Hessian矩阵的医学图像增强与窗宽窗位
在Slider控件鼠标抬起的事件中,先将目标单元格内WPF图像转为base64,发送给我们生成的C++接口,再将返回的base64转为WPF图像。乳腺影像由原始dcm显示的絮状腺体在图像增强下变成丝状,对于乳腺中存在肿瘤或其他病症的显示更为明显,亦可自由调整参数达到自己想要的效果。考虑到性能问题,因为是base64转码和解码,所以不推荐用ValueChanged,它的触发频率要高得多,由原理中得知,求得特征值和特征向量反应出的变化上的各向异性
2023-05-05 01:40:57 829
原创 C#处理医学图像(一):基于Hessian矩阵的血管肺纹理骨骼增强对比
如果不想用C++,直接用C#里面的opencv库也可以,直接用nuget搜索EmguCV,需要自己将MatLab代码或C++代码翻译成C#导出32位dll,复制到C#debug目录下,C#调用:将目标图像转为base64,发送给C++,返回处理后的base64,在转为图像。将其原理翻译写成C++类库,在C++中使用Opencv对于矩阵操作比较方便,导出dll后再由C#调用,在医院实际环境中,经常遇到有问题的患者,对于一些特殊的场景,比如骨折,肺结节,心脑血管问题。
2023-05-05 01:38:57 701
原创 C#开发PACS医学影像三维重建(一):使用VTK重建3D影像
VTK是一个开源的免费软件系统,主要用于三维计算机图形学、图像处理和可视化。Vtk是在面向对象原理的基础上设计和实现的,它的内核是用C++构建的。//血管CT值为200-300左右。因为使用C#语言开发,而VTK是C++的,所以推荐使用VTK的.Net开发库:ActiViz。//建立算法对象,从CT切片数据中提取出皮肤。最大密度投影(MIP)表面阴影遮盖(SSD)多层面重建(MPR)容积漫游技术(VR)虚拟内镜技术(VE)
2023-05-05 01:34:49 5138 1
原创 C#开发PACS医学影像处理系统(十九):Dicom影像放大镜
在XAML代码设计器中,添加canvas画布与圆形几何对象,利用VisualBrush笔刷来复制画面内容到指定容器
2023-05-05 01:29:56 708
原创 C#开发PACS医学影像处理系统(十八):Dicom使用LUT色彩增强和反色
在医生阅片确诊的过程中,当发线疑似病灶时在灰度显示下有时并不清晰,这时候就需要色彩增强效果来使灰度图像变为彩色图像。在有些类型的影像中,例如牙片(PX),胸片等,需要黑白反色的情况下观察病灶。//实例化文件处理对象并打开文件。//获取dicom图像对象。或者使用LUT逆灰度编码也能达到同样的效果。
2023-05-05 01:27:53 969
原创 C#开发PACS医学影像处理系统(十七):2D处理之影像旋转和翻转
根据鼠标按下时的位置和图片中心位置,利用WPF中Vector类计算向量夹角,得到角度,再设置元素的RotateTransform旋转属性变换。在XAML设计器中,设置RotateTransform属性。)文中提到的ScaleTransform属性中,当 st.ScaleX的值为-1时则水平翻转,当 st.ScaleY的值为-1时则垂直翻转。同样还是先获取变换对象。
2023-05-05 01:21:55 634
原创 C#开发PACS医学影像处理系统(十五):Dicom影像交叉定位线算法
而左边图像是从左手到右手的扫描切片,那么右边图像的位置就恰好在左边图像的眼睛的位置,用红线标出的位置则为定位线,一般用于医生参考病灶在矢状面、冠状面和横断面的具体方位。举个例子:右边的是MR(核磁共振)的某一帧切片,这是从头开始扫描,扫描到眼睛这个位置,得到坐标之后就可以利用绘图操作类(参考本系列教程之图形标记)来自己绘制定位线。在笛卡尔空间直角坐标系中,Y 右肩膀到左肩膀,X 后背到前胸,Z 足到头。
2023-05-05 01:17:47 1003
原创 C#开发PACS医学影像处理系统(十四):处理Dicom影像窗宽窗位
反之,如果使用宽的窗宽,则显示的CT值范围大,每一灰阶代表的CT 值幅度大,则图像对比度差,但密度均匀,适于观察密度差别大的结构。则以窗位为中心(0Hu),向上包括+50Hu,向下包括-50Hu,凡是在这个100Hu 范围内的组织均可显示出来并为人眼所识别。纵隔内淋巴结的大小,纵隔内肿块及这些结构的比邻关系,设定纵隔窗可用窗宽300 Hu~500 Hu,窗位30 Hu~50 Hu。喉颈部、鼻咽、咽喉部的窗宽和窗位常设在300 Hu~350 Hu和30 Hu~50 Hu,能满足该部位的解剖和病灶显示,
2023-05-05 01:15:46 2863
原创 C#开发PACS医学影像处理系统(十三):绘图处理之病灶测量
接上一篇文章,当我们可以绘制图形标记后,就可以在此操作类上面进行扩展,一些角度类型的测量计算相对复杂一点,需要计算角度大小和绘制弧线。计算两点之间的距离:其中dpi是缩放比例。
2023-05-05 01:12:38 687
原创 C#开发PACS医学影像处理系统(十二):绘图处理之图形标记
那么以此类推,通过命名空间System.Windows.Shapes,我们可以继续绘制其他图形了。在医生实际使用过程中,对于有病灶的影像需要一些2D绘图操作,例如对于病灶的标记和测量,最后,关于撤销上个标记和清除所有标记,只需要将图形对象保存在LIst集合中,绘制控制点:一个白色的圆形内嵌一个黑色的圆形,作为绘图完成之后的控制点。需要删除或撤销的时候从集合中移除,并在画布中移除即可。在WPF中, 推荐使用InkCanvas控件。在此类中创建绘制方法。
2023-05-05 01:08:30 859 1
原创 C#开发PACS医学影像处理系统(十一):Dicom影像挂片协议
通俗点说,挂片协议可以看作整个系统的一个相对复杂一点的配置文件,可以用JSON或XML格式来读取与保存,另外,可以制作一个独立的exe配置程序来管理这些挂片协议。
2023-05-05 01:03:55 1020
原创 C#开发PACS医学影像处理系统(十):Dicom影像下载策略与算法
1.传输协议当我们PACS客户端接收到下载命令时需要根据dcm文件的url来下载,这里推荐使用http协议,支持大文件的断点续传。2.下载策略假设有10个序列,每个序列有100张图像,①广度优先:将任务池中的下载任务平均分配到10个序列,每个序列都同时下载,优点:是每个序列都能分布加载,当用户切换序列到单元格时不需要等待。缺点:当图像特别多的时候,比如CT薄层,序列切换图像滚动时显示不完整。②深度优先:将任务池中的下载任务根据先进先出原则分配到排序在前的序列,下载完一个后再开始下
2020-09-15 18:42:48 1484
原创 C#开发PACS医学影像处理系统(九):序列控件与拖拽
1.先看结构:创建WPF用户控件:YourTab创建WPF用户控件:YourItem创建选项卡时循环添加item,并设置序列缩略图到控件和异步下载的进度条,1个病人1个或多个Study检查,1个Study检查1个选项卡,并为每个选项卡添加自定义关闭按钮Tab自定义关闭按钮的XAML样式如下:<Style TargetType="{x:Type TabItem}"> <Setter Property="Templat...
2020-09-15 18:40:49 935
原创 C#开发PACS医学影像处理系统(八):单元格变换
再看结构,Viewer(影像控件)分为N个Cell(单元格),每个单元格分为N个Box(影像容器),当默认情况为2x2的行列时,结构如下图:其中,我们在WPF设计器中创建一个用户控件叫Viewer,使用Grid容器,默认2x2,再根据自己的业务需要创建用户控件Cell和用户控件Box,在Viewer中声明变量集合来记录Cell,同理,在Cell中声明变量集合来记录Box:
2020-09-15 18:39:18 1093
原创 C#开发PACS医学影像处理系统(七):读取影像Dicom信息
Dicom的文件信息一般是由设备信息、图像信息、病人信息等Tag标记组成的,用字节长度和偏移量来区分,具体数据结构可以自行去参考Dicom文件解析,内容比较多,这里不赘述。对于常用的Tag,可以简单的理解为两层结构,第一层是组,第二层是组包含的元素,每个组号和元素号用2个字节表示(Uint16),例如常用的组有 0002组描述设备通讯,0008组描述特征参数,0010组描述患者信息,0028组描述图像信息参数,例如 0010组里面又包含病人姓名、年龄、性别等。同样的,按照上一..
2020-09-14 17:11:05 3737 2
原创 C#开发PACS医学影像处理系统(六):加载Dicom影像
对于一款软件的扩展性和维护性来说,上层业务逻辑和UI表现一定要自己开发才有控制权,否则项目上线之后容易被掣肘,而底层图像处理,我们不需要重复造轮子,这里推荐使用fo-dicom,同样基于Dicom3.0协议。根据以上原则,后台影像处理完成之后,即可使用自己开发的控件来呈现。1.先准备好自己的dcm文件,可以是单个文件或序列文件或DicomDir文件。2.在VS编辑器里打开NUGET搜索fo-dicoman安装即可。3.使用fo-dicom读取影像。 //...
2020-09-14 17:08:25 3781 2
原创 C#开发PACS医学影像处理系统(五):查询病人信息列表
一般情况下,PACS的影像加载是由外部命令发起的,如RIS客户端或网页参数等,但为保证系统完整性和健壮性,也需要在PACS客户端给用户一个查询界面来加载Dicom影像。界面分为两部分,上半部是各种查询条件,使用常见控件即可,不赘述。下半部分是一个WPF中的DataGrid表格控件,通过服务端返回的JSON或XML数据生成列表,双击某一行时进行下载和装载影像操作,后续操作请参考本系列文章关于下载策略和Dicom影像加载。需要注意的是,在DataGird中需要添加自定义列来生..
2020-09-14 17:03:47 1426
原创 C#开发PACS医学影像处理系统(四):界面布局之状态栏
状态栏一般用于显示系统状态,例如影像数量统计、CPU和内存使用情况、全屏时显示日期等,同样也是采用WPF控件的Grid作为容器,布局使用 VerticalAlignment="Bottom"普通配置的Win7和Win10一般内存使用不超过200M,CPU不超过5,除了一些老医院还在用XP系统,实在太烂可以放宽要求,但要保证软件的运行速度和控制资源占用。其中CPU、内存、系统时间监控代码如下:/// <summary> /// 获取程序运行...
2020-09-14 17:02:42 788
原创 C#开发PACS医学影像处理系统(三):界面布局之工具栏
工具栏布局采用WPF中Grid作为容器,按钮采用自定义样式和图标,并采用Separator分割线:XAML设计器代码:其中Style="{StaticResource ButtonStyle}" 按钮样式可以根据自身UI风格来使用自定义样式<Button x:Name="BtnRotate" Margin="5,0,0,0" Style="{StaticResource ButtonStyle}" HorizontalAlignment="Left" Vertic...
2020-09-14 17:00:35 1244
原创 C#开发PACS医学影像处理系统(二):界面布局之菜单栏
在菜单栏布局上,为了使用自定义窗体样式和按钮,我们需要先将窗体设置为无边框,然后添加一个Grid作为菜单栏并置顶,VerticalAlignment="Top"logo图片和标题是Image和TextBlock控件,菜单是Menu控件,系统按钮是Button控件。其中需要注意的是,一般医院影像科或放射科阅片采用的是双屏,横屏+竖屏,而PACS一般是在竖屏上显示,当最大化窗体时,如果不进行特殊处理,则会在横屏上最大化,而我们的要求是在竖屏上最大化,所以需要监听最大化按钮的点击事件,并.
2020-09-14 16:58:04 1776
原创 C#开发PACS医学影像处理系统(一):开发背景和功能预览
本系列文章将从以下模块和大家分享和讨论使用C#开发医学软件PACS和RIS系统,国内相关资料比较少,也借此机会丰富一下医学软件开发生态,讨论技术难点,希望大家互相帮助共同进步。
2020-09-10 17:30:32 4034 4
空空如也
空空如也
TA创建的收藏夹 TA关注的收藏夹
TA关注的人