UNPKG

cornerstone-tools-cacalc

Version:

Medical imaging tools for the Cornerstone library with added functionality for computing Agatston calcium scores

431 lines (317 loc) 13.9 kB
<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"> <title>imageTools/wwwcRegion.js - Documentation</title> <script src="scripts/prettify/prettify.js"></script> <script src="scripts/prettify/lang-css.js"></script> <!--[if lt IE 9]> <script src="//html5shiv.googlecode.com/svn/trunk/html5.js"></script> <![endif]--> <link type="text/css" rel="stylesheet" href="styles/prettify.css"> <link type="text/css" rel="stylesheet" href="styles/jsdoc.css"> </head> <body> <input type="checkbox" id="nav-trigger" class="nav-trigger" /> <label for="nav-trigger" class="navicon-button x"> <div class="navicon"></div> </label> <label for="nav-trigger" class="overlay"></label> <nav> <h2><a href="index.html">Home</a></h2><h3>Global</h3><ul><li><a href="global.html#applyWWWCRegion">applyWWWCRegion</a></li><li><a href="global.html#calculateMinMaxMean">calculateMinMaxMean</a></li><li><a href="global.html#createMagnificationCanvas">createMagnificationCanvas</a></li><li><a href="global.html#dragCallback">dragCallback</a></li><li><a href="global.html#drawMagnificationTool">drawMagnificationTool</a></li><li><a href="global.html#getPlayClipTimeouts">getPlayClipTimeouts</a></li><li><a href="global.html#mouseDownCallback">mouseDownCallback</a></li><li><a href="global.html#mouseUpCallback">mouseUpCallback</a></li><li><a href="global.html#onImageRendered">onImageRendered</a></li><li><a href="global.html#performThresholding">performThresholding</a></li><li><a href="global.html#playClip">playClip</a></li><li><a href="global.html#recordStartPoint">recordStartPoint</a></li><li><a href="global.html#removeMagnificationCanvas">removeMagnificationCanvas</a></li><li><a href="global.html#stopClip">stopClip</a></li><li><a href="global.html#stopClipWithData">stopClipWithData</a></li><li><a href="global.html#triggerStopEvent">triggerStopEvent</a></li></ul> </nav> <div id="main"> <h1 class="page-title">imageTools/wwwcRegion.js</h1> <section> <article> <pre class="prettyprint source linenums"><code>import $ from '../jquery.js'; import * as cornerstone from '../cornerstone-core.js'; import toolStyle from '../stateManagement/toolStyle.js'; import toolColors from '../stateManagement/toolColors.js'; import { getToolState, addToolState } from '../stateManagement/toolState.js'; import getLuminance from '../util/getLuminance.js'; import isMouseButtonEnabled from '../util/isMouseButtonEnabled.js'; const toolType = 'wwwcRegion'; let configuration = { minWindowWidth: 10 }; let currentMouseButtonMask; /** Calculates the minimum, maximum, and mean value in the given pixel array */ function calculateMinMaxMean (storedPixelLuminanceData, globalMin, globalMax) { const numPixels = storedPixelLuminanceData.length; if (numPixels &lt; 2) { return { min: globalMin, max: globalMax, mean: (globalMin + globalMax) / 2 }; } let min = globalMax; let max = globalMin; let sum = 0; for (let index = 0; index &lt; numPixels; index++) { const spv = storedPixelLuminanceData[index]; min = Math.min(min, spv); max = Math.max(max, spv); sum += spv; } return { min, max, mean: sum / numPixels }; } /* Erases the toolData and rebinds the handlers when the image changes */ function newImageCallback (e, eventData) { const toolData = getToolState(eventData.element, toolType); if (toolData &amp;&amp; toolData.data) { toolData.data = []; } $(eventData.element).off('CornerstoneToolsMouseMove', dragCallback); $(eventData.element).off('CornerstoneToolsMouseDrag', dragCallback); $(eventData.element).off('CornerstoneToolsMouseUp', dragEndCallback); $(eventData.element).off('CornerstoneToolsMouseClick', dragEndCallback); const mouseData = { mouseButtonMask: currentMouseButtonMask }; $(eventData.element).on('CornerstoneToolsMouseDown', mouseData, mouseDownCallback); } /* Applies the windowing procedure when the mouse drag ends */ function dragEndCallback (e, eventData) { $(eventData.element).off('CornerstoneToolsMouseMove', dragCallback); $(eventData.element).off('CornerstoneToolsMouseDrag', dragCallback); $(eventData.element).off('CornerstoneToolsMouseUp', dragEndCallback); $(eventData.element).off('CornerstoneToolsMouseClick', dragEndCallback); const mouseData = { mouseButtonMask: currentMouseButtonMask }; $(eventData.element).on('CornerstoneToolsMouseDown', mouseData, mouseDownCallback); const toolData = getToolState(eventData.element, toolType); if (!toolData || !toolData.data || !toolData.data.length) { return; } // Update the endpoint as the mouse/touch is dragged toolData.data[0].endPoint = { x: eventData.currentPoints.image.x, y: eventData.currentPoints.image.y }; applyWWWCRegion(eventData); } /** Calculates the minimum and maximum value in the given pixel array */ function applyWWWCRegion (eventData) { const toolData = getToolState(eventData.element, toolType); if (!toolData || !toolData.data || !toolData.data.length) { return; } const startPoint = toolData.data[0].startPoint; const endPoint = toolData.data[0].endPoint; // Get the rectangular region defined by the handles let width = Math.abs(startPoint.x - endPoint.x); let height = Math.abs(startPoint.y - endPoint.y); let left = Math.min(startPoint.x, endPoint.x); let top = Math.min(startPoint.y, endPoint.y); // Bound the rectangle so we don't get undefined pixels left = Math.max(left, 0); left = Math.min(left, eventData.image.width); top = Math.max(top, 0); top = Math.min(top, eventData.image.height); width = Math.floor(Math.min(width, Math.abs(eventData.image.width - left))); height = Math.floor(Math.min(height, Math.abs(eventData.image.height - top))); // Get the pixel data in the rectangular region const pixelLuminanceData = getLuminance(eventData.element, left, top, width, height); // Calculate the minimum and maximum pixel values const minMaxMean = calculateMinMaxMean(pixelLuminanceData, eventData.image.minPixelValue, eventData.image.maxPixelValue); // Adjust the viewport window width and center based on the calculated values const config = wwwcRegion.getConfiguration(); const viewport = cornerstone.getViewport(eventData.element); if (config.minWindowWidth === undefined) { config.minWindowWidth = 10; } viewport.voi.windowWidth = Math.max(Math.abs(minMaxMean.max - minMaxMean.min), config.minWindowWidth); viewport.voi.windowCenter = minMaxMean.mean; cornerstone.setViewport(eventData.element, viewport); // Clear the toolData toolData.data = []; cornerstone.updateImage(eventData.element); } function whichMovement (e, eventData) { const element = eventData.element; $(element).off('CornerstoneToolsMouseMove'); $(element).off('CornerstoneToolsMouseDrag'); $(element).on('CornerstoneToolsMouseMove', dragCallback); $(element).on('CornerstoneToolsMouseDrag', dragCallback); $(element).on('CornerstoneToolsMouseClick', dragEndCallback); if (e.type === 'CornerstoneToolsMouseDrag') { $(element).on('CornerstoneToolsMouseUp', dragEndCallback); } } /** Records the start point and attaches the drag event handler */ function mouseDownCallback (e, eventData) { if (isMouseButtonEnabled(eventData.which, e.data.mouseButtonMask)) { $(eventData.element).on('CornerstoneToolsMouseDrag', eventData, whichMovement); $(eventData.element).on('CornerstoneToolsMouseMove', eventData, whichMovement); $(eventData.element).off('CornerstoneToolsMouseDown', mouseDownCallback); recordStartPoint(eventData); return false; } } /** Records the start point of the click or touch */ function recordStartPoint (eventData) { const toolData = getToolState(eventData.element, toolType); if (toolData &amp;&amp; toolData.data) { toolData.data = []; } const measurementData = { startPoint: { x: eventData.currentPoints.image.x, y: eventData.currentPoints.image.y } }; addToolState(eventData.element, toolType, measurementData); } /** Draws the rectangular region while the touch or mouse event drag occurs */ function dragCallback (e, eventData) { // If we have no toolData for this element, return immediately as there is nothing to do const toolData = getToolState(eventData.element, toolType); if (!toolData || !toolData.data || !toolData.data.length) { return; } // Update the endpoint as the mouse/touch is dragged const endPoint = { x: eventData.currentPoints.image.x, y: eventData.currentPoints.image.y }; toolData.data[0].endPoint = endPoint; cornerstone.updateImage(eventData.element); } function onImageRendered (e, eventData) { const toolData = getToolState(eventData.element, toolType); if (!toolData || !toolData.data || !toolData.data.length) { return; } const startPoint = toolData.data[0].startPoint; const endPoint = toolData.data[0].endPoint; if (!startPoint || !endPoint) { return; } // Get the current element's canvas const canvas = $(eventData.element).find('canvas').get(0); const context = canvas.getContext('2d'); context.setTransform(1, 0, 0, 1, 0, 0); // Set to the active tool color const color = toolColors.getActiveColor(); // Calculate the rectangle parameters const startPointCanvas = cornerstone.pixelToCanvas(eventData.element, startPoint); const endPointCanvas = cornerstone.pixelToCanvas(eventData.element, endPoint); const left = Math.min(startPointCanvas.x, endPointCanvas.x); const top = Math.min(startPointCanvas.y, endPointCanvas.y); const width = Math.abs(startPointCanvas.x - endPointCanvas.x); const height = Math.abs(startPointCanvas.y - endPointCanvas.y); const lineWidth = toolStyle.getToolWidth(); const config = wwwcRegion.getConfiguration(); // Draw the rectangle context.save(); if (config &amp;&amp; config.shadow) { context.shadowColor = config.shadowColor || '#000000'; context.shadowOffsetX = config.shadowOffsetX || 1; context.shadowOffsetY = config.shadowOffsetY || 1; } context.beginPath(); context.strokeStyle = color; context.lineWidth = lineWidth; context.rect(left, top, width, height); context.stroke(); context.restore(); } // --- Mouse tool enable / disable --- /// function disable (element) { $(element).off('CornerstoneToolsMouseDown', mouseDownCallback); $(element).off('CornerstoneToolsMouseUp', dragEndCallback); $(element).off('CornerstoneToolsMouseClick', dragEndCallback); $(element).off('CornerstoneToolsMouseDrag', dragCallback); $(element).off('CornerstoneToolsMouseMove', dragCallback); $(element).off('CornerstoneImageRendered', onImageRendered); $(element).off('CornerstoneNewImage', newImageCallback); cornerstone.updateImage(element); } function activate (element, mouseButtonMask) { const eventData = { mouseButtonMask }; currentMouseButtonMask = mouseButtonMask; const toolData = getToolState(element, toolType); if (!toolData) { const data = []; addToolState(element, toolType, data); } $(element).off('CornerstoneToolsMouseDown', mouseDownCallback); $(element).off('CornerstoneToolsMouseUp', dragEndCallback); $(element).off('CornerstoneToolsMouseClick', dragEndCallback); $(element).off('CornerstoneToolsMouseDrag', dragCallback); $(element).off('CornerstoneToolsMouseMove', dragCallback); $(element).off('CornerstoneImageRendered', onImageRendered); $(element).off('CornerstoneNewImage', newImageCallback); $(element).on('CornerstoneToolsMouseDown', eventData, mouseDownCallback); $(element).on('CornerstoneImageRendered', onImageRendered); // If the displayed image changes after the user has started clicking, we should // Cancel the handlers and prepare for another click $(element).on('CornerstoneNewImage', newImageCallback); cornerstone.updateImage(element); } // --- Touch tool enable / disable --- // function disableTouchDrag (element) { $(element).off('CornerstoneToolsTouchDrag', dragCallback); $(element).off('CornerstoneToolsTouchStart', recordStartPoint); $(element).off('CornerstoneToolsDragEnd', applyWWWCRegion); $(element).off('CornerstoneImageRendered', onImageRendered); } function activateTouchDrag (element) { const toolData = getToolState(element, toolType); if (!toolData) { const data = []; addToolState(element, toolType, data); } $(element).off('CornerstoneToolsTouchDrag', dragCallback); $(element).off('CornerstoneToolsTouchStart', recordStartPoint); $(element).off('CornerstoneToolsDragEnd', applyWWWCRegion); $(element).off('CornerstoneImageRendered', onImageRendered); $(element).on('CornerstoneToolsTouchDrag', dragCallback); $(element).on('CornerstoneToolsTouchStart', recordStartPoint); $(element).on('CornerstoneToolsDragEnd', applyWWWCRegion); $(element).on('CornerstoneImageRendered', onImageRendered); } function getConfiguration () { return configuration; } function setConfiguration (config) { configuration = config; } // Module exports const wwwcRegion = { activate, deactivate: disable, disable, setConfiguration, getConfiguration }; const wwwcRegionTouch = { activate: activateTouchDrag, deactivate: disableTouchDrag, disable: disableTouchDrag }; export { wwwcRegion, wwwcRegionTouch }; </code></pre> </article> </section> </div> <br class="clear"> <footer> Documentation generated by <a href="https://github.com/jsdoc3/jsdoc">JSDoc 3.5.4</a> using the <a href="https://github.com/clenemt/docdash">docdash</a> theme. </footer> <script>prettyPrint();</script> <script src="scripts/linenumber.js"></script> </body> </html>