在此之前,此系统是结合DICOM的WADO标准,在浏览器里通过javascript操作返回的JPG图片。这种服务器端解析,客户端展现的方式,对实现图像的移动、缩放、旋转、测量等图像操作能够实现实时的交互。但这种方式存在着几个弊端:

1.获取图像上的CT值(钙化值)信息的时候,要频繁的和服务器进行交互。

2.调整图像的窗宽窗位或者对图像进行反色,也要和服务器进行频繁的交互。

3.对图像进行测量(长方形测量,椭圆测量等)只能获取到面值和周长的简单的信息,这对于医生的诊断没多大的用处,实际运用中需要知道所测量的区域的最大值、最小值、方差值、均值等测量信息。

以上的缺点归结为一点:即本地没有处理像素信息的操作。但是HTML5对于像素级处理的能力已经支持得很好,完成可以实现客户端对像素信息的操作。所以为了解决以上问题最近对系统做了一次比较大的升级。即客户端端直接操作DICOM的像素数据进行JS端图像的生成以及JS端实现窗宽窗位的调整。

获取dicom中的像素数据,可考虑以下两种方式:

A:服务器端直接以字节流的方式返回DICOM文件,客户端用JS来接收字节流,并负责解析DICOM中的图像数据,这种方式不仅要根据DICOM 的传输语法(0002,0010)Transfer Syntax UID,还要根据  (0028,0002)Samples per pixel、(0028,0004)Photometric Interpretation,(0028,0010)Rows,(0028,0011)Columns,(0028,0100)Bits Allocated,(0028,0103)Pixel Representation等标签来确定像素数据的结构,复杂点的可能还会用到查找表来查找((0028,0004)Photometric Interpretation的值等于==PALETTE COLOR)。对于非压缩的显示VR或者是隐形VR, (0028,0004)Photometric Interpretation等于MONOCHROME1或者MONOCHROME2来说JS解析出像素数据确实很方便,但是DICOM文件各式各样,要 写出包罗给种传输语法以及各种像素结构的JS文件确实很费劲。还要考虑到多帧动态图像,如果多针图像很大整个文件下载下来解析估计浏览器会彻底奔溃。所以 觉得这种方式不太可行。(虽然这过程中实现了显示VR的DICOM文件的JS解析,但是中途考虑到复杂性和难度还是放弃了)。

B:从服务器端获取DICOM文件的像素数组,既然目前基于C/S模式的PACS已经相当成熟,各式各样的第三方开源的dicom解析工具如 DCMTK,DCM4CHE,MDCM,OPENDICOM等也相当的多,用开源的DICOM解析工具获取到像素数据也相当的方便。所以在服务器获取到像 素数据返回给JS端,让JS端直接操作像素数据来生成要显示的图像。对于多帧图像也可以按需按帧的从服务器下载像素数据。

言归正传,目前此系统是基于第二种方式来实现。需要特别注意的是:做窗宽窗位调整的时候要先做Hounsfield 值的转换。

HU[i] = pixel_val[i]*rescaleSlope+ rescaleIntercept。窗宽窗位的调整使用了线性的window-leveling 算法针对CT/MR等图像,或者是非线性的gamma算法针对DX图像(即当windowWidth比较大的时候要考虑非线性的gamma算法,因为线性 算法中每windowWidth/255个原始密度会压缩成一个显示灰度,windowWidth很大的时候损失可能会很大)

//线性的window-leveling算法

min = (2*windowCenter - windowWidth)/2.0 - 0.5;

max = (2*windowCenter + windowWidth)/2.0 - 0.5;

for (var i = 0; i != nNumPixels; i++){

showPixelValue = (pixelHuValue[i] - min)*255.0/(double)(max - min);

}

//非线性的gamma算法

min = (2*windowCenter - windowWidth)/2.0 - 0.5;

max = (2*windowCenter + windowWidth)/2.0 - 0.5;

for (var i = 0; i != nNumPixels; i++){

showPixelValue = 255.0 * Math.pow(pixelHuValue/(max-min), 1.0/gamma);

}

如下代码展示JS端如何用后台获取到的像素数据生成图像。其中用到了查找表的概念。

/**

* @author http://www.cnblogs.com/poxiao

* pixelBuffer代表是从后台获取到的像素信息数组,代码只列出了单色灰度图像的情况,

* 如果是三色的RGB图像自己稍微改动下代码即可。篇幅有限不在叙述。

**/

var pixelBuffer;

//width 代表图像的宽度,即DICOM中的标签(0028,0011)Columns

var width;

//height 代表图像的高度,即DICOM中的标签(0028,0010)Rows

var height;

/**

* @windowCenter 代表当前要显示的窗位

* @windowWidth 代表当前要显示的窗宽

* @bitsStored (0028,0101) 根据每个像素的存储位数生成查找表大小

* @rescaleSlope (0028,1053)用于计算HU值

* @rescaleIntercept  (0028,1052)用于计算HU值

* **/

function createImageCanvas(windowCenter,windowWidth,bitsStored,rescaleSlope,rescaleIntercept){

var lookupObject=new LookupTable();

lookupObject.setData(windowCenter,windowWidth,bitsStored,rescaleSlope,rescaleIntercept);

lookupObject.calculateHULookup();

lookupObject.calculateLookup();

var imageCanvas=document.createElement("canvas");

imageCanvas.width = width;

imageCanvas.height =height;

imageCanvas.style.width = width;

imageCanvas.style.height = height;

var tmpCxt = imageCanvas.getContext("2d");

var imageData = tmpCxt.getImageData(0,0,width,height);

var n=0;

for(var yPix=0; yPix

{

for(var xPix=0; xPix

{

var offset = (yPix * width + xPix) * 4;

var pixelValue=lookupObject.lookup[pixelBuffer[n]];

imageData.data[offset]=    pixelValue;

imageData.data[offset+1]=pixelValue;

imageData.data[offset+2]=pixelValue;

imageData.data[offset+3]=255;

n++;

}

}

tmpCxt.putImageData(imageData, 0,0);

return imageCanvas;

};

/**

* 像素查找表,主要要先根据rescaleSlope和rescaleIntercept进行Hounsfield值的转换

* HU[i] = pixel_val[i]*rescaleSlope+ rescaleIntercept

*/

function LookupTable()

{

this.bitsStored;

this.rescaleSlope;

this.rescaleIntercept;

this.windowCenter;

this.windowWidth;

this.huLookup;

this.lookup;

}

LookupTable.prototype.setData=function(wc,ww,bs,rs,ri)

{

this.windowCenter=wc;

this.windowWidth=ww;

this.bitsStored=bs;

this.rescaleSlope=rs;

this.rescaleIntercept=ri;

};

LookupTable.prototype.setWindowingdata=function(wc,ww)

{

this.windowCenter=wc;

this.windowWidth=ww;

};

LookupTable.prototype.calculateHULookup=function()

{

var size=1<

this.huLookup = new Array(size);

for(var inputValue=0;inputValue

{

if(this.rescaleSlope == undefined && this.rescaleIntercept == undefined) {

this.huLookup[inputValue] = inputValue;

} else {

this.huLookup[inputValue] = inputValue * this.rescaleSlope + this.rescaleIntercept;

}

}

};

/**

* 窗宽窗位的调整线性的Window-leveling算法

* 非线性的gamma算法,稍微修改下:

*  var y=255.0 * Math.pow(this.huLookup[inputValue]/this.windowWidth, 1.0/gamma);

* **/

LookupTable.prototype.calculateLookup=function()

{

var size=1<

var min=this.windowCenter-0.5-(this.windowWidth-1)/2;

var max=this.windowCenter-0.5+(this.windowWidth-1)/2;

this.lookup=new Array(size);

for(var inputValue=0;inputValue

{

if(this.huLookup[inputValue]<=min){

this.lookup[inputValue]=0 ;

}else if (this.huLookup[inputValue]>max){

this.lookup[inputValue]=255;

}else{

var y=((this.huLookup[inputValue]-(this.windowCenter-0.5))/(this.windowWidth-1)+0.5)*255;

this.lookup[inputValue]= parseInt(y);

}

}

};

鼠标调整窗宽窗位的时候JS端生成图像+绘制图形的速度。

1.512 X 512大小的CT图像调整窗宽窗位速度

2.512 X 512大小的彩色CT图像调整窗宽窗位速度

3.512 x 512大小的MR图像调整窗宽窗位速度

4.2057 X 1347大小的CR图像调整窗宽窗位速度

5.有了像素信息后就可以在客户端实时的获取到CT值了。

6:有了像素信息后测量也可以获取到测量区域的最大值、最小值、方差值、均值等测量信息了

进测试,调整窗宽窗位时HTML5上绘制图形的时间还是很快的,总的绘制时间在10毫秒的数量级,而且发现绘制时间还可以变少,这绘制时间包括了图 像边角上的文字信息,但是HTML5绘制文字的信息效率明显比绘制图像的效率要底,所以不必每次刷新都绘制文本信息,可以加以参数控制在图像切换或者调窗 宽窗位的时候也就是文本信息变化的时候才绘制文字信息。关于图像的生成时间,发现图像的生成时间和图像的宽X高成正比,图像越大所需时间越长,对于 CT/MR等图像时间大概在几十个毫秒级。对于2057X1347的CR图像时间大概在400毫秒级,对于2000X3000多的DX图像生成图像的时间 就有点卡顿了,要1秒-2秒左右。。。这速度还得想办法优化有木有。。。。。还有对于DX图像调整窗宽窗位虽然使用了gamma算法,但是出来的图像,我 总感觉得没有用第三方工具比如RadiAnt上看见的光滑,噪声有点大。所以在没得到更好的解决方案前,目前DX的图像只能特殊化即保留原来的方式在服务 器端直接生成JPG让客户端直接绘制,希望会DICOM图像算法的大神们看到此文章后能给小弟我一点关于DX调窗宽窗位的意见,是不是还要用到别的算法啥的?。先谢谢了。

html5 pacs浏览,基于HTML5的PACS--HTML5图像处理相关推荐

  1. html5 职工入职后台管理系统_ChemCMS是一款基于GO+PHP+MYSQL+HTML5构建的化学内容管理系统

    ChemCMS是一款基于GO+PHP+MYSQL+HTML5构建的化学内容管理系统,旨在提高化学类企业信息化管理水平,ChemCMS提供了行业所需的库存管理.订单管理.产品管理.客户管理.权限管理全部 ...

  2. 基于HTML5实现的超酷摄像头(HTML5 webcam)拍照功能 - photobooth.js

    在线演示  下载 WebRTC可能是明年最受关注的HTML5标准了,Mozilla为此开发了一套帮助你控制硬件的API,例如,摄像头,麦克风,或者是加速表.你可以不依赖其它的插件来调用你需要的本机硬件 ...

  3. html5 canvas图表,Chart.js基于Canvas画布的HTML5统计图表库 - 资源分享

    Chart.js 是一个简单.面向对象.为设计者和开发者准备的图表绘制工具库.可以绘制柱状图.热点图.曲线图等,使用HTML5中的Canvas画布,支持原生的和jQuery的调用方法. 特点 6种图表 ...

  4. html5桌面系统,基于HTML5的IVI桌面系统及本地功能扩展研究实现

    摘要: 随着汽车技术以及互联网技术的发展,智能化车载信息娱乐系统(IVI:In-Vehicle Infotainment)已经成为汽车工业未来发展的新方向.目前,在用于开发智能化车载信息娱乐系统的大量 ...

  5. 再议HTML5离线浏览

    作者简介:Malcolm Sherida是Microsoft在ASP.NET方面的awarded MVP,精通ASP和Telerik,经常在澳大利亚和新西兰的会议以及用户组中做报告.作为一个长期使用A ...

  6. HTML5游戏_基于DOM平台跳跃小游戏开发_9.按键监听

    HTML5游戏_基于DOM平台跳跃小游戏开发 按键监听 视频讲解 HTML5游戏 效果图 本章知识点: 对象自定义名称属性,可以用变量来命名属性名称 //这段代码把多个属性(品牌, 型号, 排量)赋给 ...

  7. 基于html5的矢量图绘制方法研究,基于HTML5Canvas技术的在线图像处理方法的研究...

    摘要: 本文主要对基于HTML5Canvas技术的在线图像处理方法进行探讨和研究. 随着网页技术的飞速发展,在线的应用程序越来越受到用户的欢迎,很多业余摄影爱好者开始采用在线的图像处理软件来对照片进行 ...

  8. 图片动画效果html5,8个实用炫酷的HTML5图片动画应用

    原标题:8个实用炫酷的HTML5图片动画应用 近期我们发布了不少关于HTML5和jQuery的图片动画应用,很多都比较实用,也有一些效果非常炫酷,比如一些HTML5 3D图片动画特效.本文精选了8个实 ...

  9. html5作品分析报告,性能报告之HTML5 性能测试报告

    引言 1.1. 编写目的 HTML5 作为当前"最火"的跨平台.跨终端(硬件)开发语言,越来越受到前端开发者 的重视,无论是 PC 端还是当前"火热"的移动端, ...

  10. 安卓使用html5动画,精妙无比!8款HTML5动画实例

    1.jQuery垂直带小图标菜单导航插件 今天我们要来分享一款jQuery菜单插件,这款jQuery菜单是垂直的样式,鼠标滑过菜单项时会出现一个背景,菜单项的右侧也会出现一个小箭头.另外值得注意的是, ...

最新文章

  1. 【Zookeeper】Zookeeper集群“脑裂”问题处理大全
  2. android handler的机制和原理_一文搞懂handler:彻底明白Android消息机制的原理及源码
  3. 微信小程序设置启动图时出现滚动条
  4. Count Color poj2777 线段树
  5. js call(),apply(),对象冒充,改变变量作用域
  6. JavaScript一个简易枚举类型实现扑克牌
  7. Eclipse 添加 JD-eclipse 反编译插件
  8. 计算机控制技术第二版答案于微波,微波技术习题答案 2.doc
  9. buuctf|ciscn_2019_en_2 1
  10. centos7 yum 配置阿里云镜像
  11. 【深度学习】使用tensorflow实现VGG19网络
  12. GFP-GAN学习笔记
  13. iperf详细使用图文教程
  14. C语言公制长度转英制长度,英制换算(英制长度转换公制长度换算)
  15. 从今天开始,请叫我,新生代农民工
  16. 【面试】蜻蜓FM2020秋季校园招聘
  17. jvax.net.ssl.SSLException: 异常解决
  18. JavaScript学习记录-正则表达式(2)
  19. 批量从IP列表中提取C段
  20. PC-DMIS 2019 校验测针注意事项

热门文章

  1. JVM-深入理解JVM内存模型、类加载机制、内存分配机制
  2. 小程序发布成功后搜索不到怎么办?
  3. 当我开始学微信公众号开发时,我要学什么?
  4. 十月百度,阿里巴巴,迅雷搜狗最新面试十一题
  5. 赢在中国 - 史玉柱经典语录(转载)
  6. php启动后no input file specified.,php网站出现no input file specified 三种解决方法
  7. 广播风暴和环路是什么
  8. reCAPTCHA打不开的解决方法
  9. 安装dhcp服务器虚拟2012,windows server 2012 dhcp服务器安装
  10. HTTPs SSL OV、DV和EV证书的区别