Make imageSlider range input use reactive variables instead of updating it manually. Add min/max zoom levels, remove unnecessary precision for Zoom
This commit is contained in:
parent
5763abf29b
commit
87cc2a5bc0
@ -1,7 +1,11 @@
|
||||
<template name="imageControls">
|
||||
<div class="imageControls">
|
||||
<div id="scrollbar">
|
||||
<input id="imageSlider" type="range" min="1" val="1"/>
|
||||
<input id="imageSlider"
|
||||
type="range"
|
||||
min="1"
|
||||
value="{{imageIndex}}"
|
||||
max="{{numImages}}"/>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
@ -1,6 +1,20 @@
|
||||
const slideTimeoutTime = 40;
|
||||
let slideTimeout;
|
||||
|
||||
Template.imageControls.onRendered(() => {
|
||||
const instance = Template.instance();
|
||||
|
||||
Meteor.defer(() => {
|
||||
// Set the current imageSlider width to its parent's height
|
||||
// (because webkit is stupid and can't style vertical sliders)
|
||||
const $slider = instance.$('#imageSlider');
|
||||
const $element = $slider.parents().eq(2).siblings('.imageViewerViewport');
|
||||
const viewportHeight = $element.height();
|
||||
|
||||
$slider.width(viewportHeight - 20);
|
||||
});
|
||||
})
|
||||
|
||||
Template.imageControls.events({
|
||||
'input #imageSlider, change #imageSlider': function(e) {
|
||||
// Note that we throttle requests to prevent the
|
||||
|
||||
@ -17,6 +17,7 @@ $imageSliderCursor = grab
|
||||
padding: 5px
|
||||
|
||||
#scrollbar
|
||||
height: calc(100% - 20px);
|
||||
margin-top: 5px
|
||||
width: 31px
|
||||
|
||||
|
||||
@ -86,32 +86,6 @@ function loadDisplaySetIntoViewport(data, templateData) {
|
||||
imageIds: imageIds
|
||||
};
|
||||
|
||||
// Show or hide the image scrollbar depending
|
||||
// on the number of images in the stack
|
||||
var currentOverlay = $(element).siblings('.imageViewerViewportOverlay');
|
||||
var imageControls = currentOverlay.find('.imageControls');
|
||||
currentOverlay.find('.imageControls').height($(element).height());
|
||||
|
||||
if (stack.imageIds.length === 1) {
|
||||
imageControls.hide();
|
||||
currentOverlay.find('.topright, .bottomright').css('right', '3px');
|
||||
} else {
|
||||
imageControls.show();
|
||||
currentOverlay.find('.topright, .bottomright').css('right', '39px');
|
||||
|
||||
// Update the maximum value of the slider
|
||||
var currentImageSlider = currentOverlay.find('#imageSlider');
|
||||
currentImageSlider.attr('max', stack.imageIds.length);
|
||||
currentImageSlider.val(1);
|
||||
|
||||
// Set it's width to its parent's height
|
||||
// (because webkit is stupid and can't style vertical sliders)
|
||||
var scrollbar = currentOverlay.find('#scrollbar');
|
||||
scrollbar.height(scrollbar.parent().height() - 20);
|
||||
var overlayHeight = currentImageSlider.parent().height();
|
||||
currentImageSlider.width(overlayHeight);
|
||||
}
|
||||
|
||||
// Get the current image ID for the stack that will be rendered
|
||||
imageId = imageIds[stack.currentImageIdIndex];
|
||||
|
||||
@ -296,11 +270,6 @@ function loadDisplaySetIntoViewport(data, templateData) {
|
||||
|
||||
var stack = toolData.data[0];
|
||||
|
||||
// Update the imageSlider value
|
||||
var currentOverlay = $(element).siblings('.imageViewerViewportOverlay');
|
||||
var currentImageSlider = currentOverlay.find('#imageSlider');
|
||||
currentImageSlider.val(stack.currentImageIdIndex + 1);
|
||||
|
||||
// If this viewport is displaying a stack of images, save the current image
|
||||
// index in the stack to the global ViewerData object, as well as the Meteor Session.
|
||||
var stack = cornerstoneTools.getToolState(element, 'stack');
|
||||
@ -319,27 +288,6 @@ function loadDisplaySetIntoViewport(data, templateData) {
|
||||
// Set a random value for the Session variable in order to trigger an overlay update
|
||||
Session.set('CornerstoneNewImage' + viewportIndex, Random.id());
|
||||
|
||||
function OnStackScroll(e, eventData) {
|
||||
// Get the element and stack data
|
||||
var element = e.target;
|
||||
var toolData = cornerstoneTools.getToolState(element, 'stack');
|
||||
if (!toolData || !toolData.data || !toolData.data.length) {
|
||||
return;
|
||||
}
|
||||
|
||||
var stack = toolData.data[0];
|
||||
|
||||
// Update the imageSlider value
|
||||
var currentOverlay = $(element).siblings('.imageViewerViewportOverlay');
|
||||
var currentImageSlider = currentOverlay.find('#imageSlider');
|
||||
currentImageSlider.val(stack.currentImageIdIndex + 1);
|
||||
}
|
||||
|
||||
$(element).off('CornerstoneStackScroll', OnStackScroll);
|
||||
if (stack.imageIds.length > 1) {
|
||||
$(element).on('CornerstoneStackScroll', OnStackScroll);
|
||||
}
|
||||
|
||||
// Define a function to trigger an event whenever a new viewport is being used
|
||||
// This is used to update the value of the "active viewport", when the user interacts
|
||||
// with a new viewport element
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
<template name="viewportOverlay">
|
||||
<div class="imageViewerViewportOverlay noselect">
|
||||
<div class="imageViewerViewportOverlay noselect {{#if gt numImages 1}}controlsVisible{{/if}}">
|
||||
{{ #unless tagDisplaySpecified }}
|
||||
<div class="topleft dicomTag">
|
||||
<div>{{formatPN patientName}}</div>
|
||||
@ -11,13 +11,13 @@
|
||||
<div>{{formatDA studyDate}} {{formatTM studyTime}}</div>
|
||||
</div>
|
||||
<div class="bottomright dicomTag">
|
||||
<div>{{#if zoom}}Zoom: {{formatNumberPrecision zoom 2}}%{{/if}}</div>
|
||||
<div>{{#if zoom}}Zoom: {{formatNumberPrecision zoom 0}}%{{/if}}</div>
|
||||
<div>{{compression}}</div>
|
||||
<div>{{wwwc}}</div>
|
||||
</div>
|
||||
<div class="bottomleft dicomTag">
|
||||
<div>{{#if seriesNumber}}Ser: {{seriesNumber}}{{/if}}</div>
|
||||
<div>{{#if numImages}}Img: {{imageNumber}} ({{imageIndex}}/{{numImages}}){{/if}}</div>
|
||||
<div>{{#if gt numImages 1}}Img: {{imageNumber}} ({{imageIndex}}/{{numImages}}){{/if}}</div>
|
||||
<div>{{#if frameRate}}{{frameRate}} FPS{{/if}}</div>
|
||||
<div>{{imageDimensions}}</div>
|
||||
<div>{{seriesDescription}}</div>
|
||||
@ -34,11 +34,11 @@
|
||||
</div>
|
||||
<div class="bottomright dicomTag">
|
||||
<div>{{#if seriesNumber}}Ser: {{seriesNumber}}{{/if}}</div>
|
||||
<div>{{#if numImages}}Img: {{imageNumber}} ({{imageIndex}}/{{numImages}}){{/if}}</div>
|
||||
<div>{{#if gt numImages 1}}Img: {{imageNumber}} ({{imageIndex}}/{{numImages}}){{/if}}</div>
|
||||
<div>{{#if frameRate}}{{frameRate}} FPS{{/if}}</div>
|
||||
<div>{{imageDimensions}}</div>
|
||||
<div>{{seriesDescription}}</div>
|
||||
<div>{{#if zoom}}Zoom: {{formatNumberPrecision zoom 2}}%{{/if}}</div>
|
||||
<div>{{#if zoom}}Zoom: {{formatNumberPrecision zoom 0}}%{{/if}}</div>
|
||||
<div>{{compression}}</div>
|
||||
<div>{{wwwc}}</div>
|
||||
</div>
|
||||
@ -54,15 +54,18 @@
|
||||
</div>
|
||||
<div class="bottomleft dicomTag">
|
||||
<div>{{#if seriesNumber}}Ser: {{seriesNumber}}{{/if}}</div>
|
||||
<div>{{#if numImages}}Img: {{imageNumber}} ({{imageIndex}}/{{numImages}}){{/if}}</div>
|
||||
<div>{{#if gt numImages 1}}Img: {{imageNumber}} ({{imageIndex}}/{{numImages}}){{/if}}</div>
|
||||
<div>{{#if frameRate}}{{frameRate}} FPS{{/if}}</div>
|
||||
<div>{{imageDimensions}}</div>
|
||||
<div>{{seriesDescription}}</div>
|
||||
<div>{{#if zoom}}Zoom: {{formatNumberPrecision zoom 2}}%{{/if}}</div>
|
||||
<div>{{#if zoom}}Zoom: {{formatNumberPrecision zoom 0}}%{{/if}}</div>
|
||||
<div>{{compression}}</div>
|
||||
<div>{{wwwc}}</div>
|
||||
</div>
|
||||
{{ /if }}
|
||||
{{>imageControls}}
|
||||
|
||||
{{#if gt numImages 1}}
|
||||
{{> imageControls imageIndex=imageIndex numImages=numImages}}
|
||||
{{ /if }}
|
||||
</div>
|
||||
</template>
|
||||
@ -219,9 +219,6 @@ Template.viewportOverlay.helpers({
|
||||
imageIndex: function() {
|
||||
return getInstance.call(this, 'index');
|
||||
},
|
||||
numImages: function() {
|
||||
return getSeries.call(this, 'numImages');
|
||||
},
|
||||
imageIndex: function() {
|
||||
Session.get('CornerstoneNewImage' + this.viewportIndex);
|
||||
var stack = getStackDataIfNotEmpty(this.viewportIndex);
|
||||
|
||||
@ -30,4 +30,8 @@ $viewportTagPadding = 20px
|
||||
|
||||
.priorIndicator
|
||||
font-weight: bold
|
||||
color: yellow
|
||||
color: yellow
|
||||
|
||||
&.controlsVisible
|
||||
.topright, .bottomright
|
||||
right: "calc(%s + 19px)" % $viewportTagPadding
|
||||
@ -37,13 +37,19 @@ function configureTools() {
|
||||
cornerstoneTools.toolColors.setActiveColor('#00ffff'); //rgb(0, 255, 0)'
|
||||
|
||||
// Set the configuration values for the text annotation (Arrow) tool
|
||||
var annotateConfig = {
|
||||
const annotateConfig = {
|
||||
getTextCallback: getAnnotationTextCallback,
|
||||
changeTextCallback: changeAnnotationTextCallback,
|
||||
drawHandles: false,
|
||||
arrowFirst: true
|
||||
};
|
||||
cornerstoneTools.arrowAnnotate.setConfiguration(annotateConfig);
|
||||
|
||||
const zoomConfig = {
|
||||
minScale: 0.05,
|
||||
maxScale: 10
|
||||
};
|
||||
cornerstoneTools.zoom.setConfiguration(zoomConfig);
|
||||
}
|
||||
|
||||
toolManager = {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user