UNPKG

@thewtex/vtk.js-esm

Version:

Visualization Toolkit for the Web

260 lines (218 loc) 10.9 kB
import _toConsumableArray from '@babel/runtime/helpers/toConsumableArray'; import macro from '../../macro.js'; import vtkColorMaps from '../../Rendering/Core/ColorTransferFunction/ColorMapsLite.js'; import vtkPiecewiseGaussianWidget from '../Widgets/PiecewiseGaussianWidget.js'; import { s as svgLogo } from './Icons/Logo.svg.js'; import { s as svgEdge } from './Icons/Contrast.svg.js'; import { s as svgSpacing } from './Icons/Spacing.svg.js'; import { s as style } from './VolumeController/VolumeController.module.css.js'; // Global structures // ---------------------------------------------------------------------------- var PRESETS_OPTIONS = vtkColorMaps.rgbPresetNames.map(function (name) { return "<option value=\"".concat(name, "\">").concat(name, "</option>"); }); // ---------------------------------------------------------------------------- // vtkVolumeController methods // ---------------------------------------------------------------------------- function vtkVolumeController(publicAPI, model) { // Set our className model.classHierarchy.push('vtkVolumeController'); model.el = document.createElement('div'); model.el.setAttribute('class', style.container); model.widget = vtkPiecewiseGaussianWidget.newInstance({ numberOfBins: 256, size: model.size }); function updateUseShadow() { var useShadow = !!Number(model.el.querySelector('.js-shadow').value); model.actor.getProperty().setShade(useShadow); model.renderWindow.render(); } function updateColorMapPreset() { var sourceDS = model.actor.getMapper().getInputData(); if (!sourceDS) { return; } var dataArray = sourceDS.getPointData().getScalars() || sourceDS.getPointData().getArrays()[0]; var dataRange = model.rescaleColorMap ? model.colorDataRange : dataArray.getRange(); var preset = vtkColorMaps.getPresetByName(model.el.querySelector('.js-color-preset').value); var lookupTable = model.actor.getProperty().getRGBTransferFunction(0); lookupTable.applyColorMap(preset); lookupTable.setMappingRange.apply(lookupTable, _toConsumableArray(dataRange)); lookupTable.updateRange(); model.renderWindow.render(); } function updateSpacing() { var value = Number(model.el.querySelector('.js-spacing').value); var sourceDS = model.actor.getMapper().getInputData(); var sampleDistance = 0.7 * Math.sqrt(sourceDS.getSpacing().map(function (v) { return v * v; }).reduce(function (a, b) { return a + b; }, 0)); model.actor.getMapper().setSampleDistance(sampleDistance * Math.pow(2, value * 3.0 - 1.5)); model.renderWindow.render(); } function updateEdgeGradient() { var value = Number(model.el.querySelector('.js-edge').value); if (value === 0) { model.actor.getProperty().setUseGradientOpacity(0, false); } else { var sourceDS = model.actor.getMapper().getInputData(); var dataArray = sourceDS.getPointData().getScalars() || sourceDS.getPointData().getArrays()[0]; var dataRange = dataArray.getRange(); model.actor.getProperty().setUseGradientOpacity(0, true); var minV = Math.max(0.0, value - 0.3) / 0.7; model.actor.getProperty().setGradientOpacityMinimumValue(0, (dataRange[1] - dataRange[0]) * 0.2 * minV * minV); model.actor.getProperty().setGradientOpacityMaximumValue(0, (dataRange[1] - dataRange[0]) * 1.0 * value * value); } model.renderWindow.render(); } publicAPI.setupContent = function (renderWindow, actor, isBackgroundDark) { var useShadow = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : '1'; var presetName = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : 'erdc_rainbow_bright'; publicAPI.setActor(actor); publicAPI.setRenderWindow(renderWindow); var sourceDS = model.actor.getMapper().getInputData(); var dataArray = sourceDS.getPointData().getScalars() || sourceDS.getPointData().getArrays()[0]; var lookupTable = model.actor.getProperty().getRGBTransferFunction(0); var piecewiseFunction = model.actor.getProperty().getScalarOpacity(0); var stylePostFix = isBackgroundDark ? 'DarkBG' : 'BrightBG'; var localStyle = {}; ['button', 'presets', 'shadow'].forEach(function (name) { localStyle[name] = style["".concat(name).concat(stylePostFix)]; }); model.el.innerHTML = "\n <div class=\"".concat(style.line, "\">\n <div class=\"").concat(localStyle.button, " js-button\">").concat(svgLogo, "</div>\n <select class=\"").concat(localStyle.shadow, " js-shadow js-toggle\">\n <option value=\"1\">Use Shadow</option>\n <option value=\"0\">No Shadow</option>\n </select>\n <select class=\"").concat(localStyle.presets, " js-color-preset js-toggle\">\n ").concat(PRESETS_OPTIONS, "\n </select>\n </div>\n <div class=\"").concat(style.line, " js-toggle\">\n <div class=\"").concat(style.sliderEntry, "\">\n <div class=\"").concat(style.sliderIcon, "\">").concat(svgSpacing, "</div>\n <input type=\"range\" min=\"0\" max=\"1\" value=\"0.4\" step=\"0.01\" class=\"").concat(style.slider, " js-spacing\" />\n </div>\n <div class=\"").concat(style.sliderEntry, "\">\n <div class=\"").concat(style.sliderIcon, "\">").concat(svgEdge, "</div>\n <input type=\"range\" min=\"0\" max=\"1\" value=\"0.2\" step=\"0.01\" class=\"").concat(style.slider, " js-edge\" />\n </div>\n </div>\n <div class=\"").concat(style.piecewiseEditor, " js-pwf js-toggle\"></div>\n "); // DOM elements var domToggleButton = model.el.querySelector('.js-button'); var domShadow = model.el.querySelector('.js-shadow'); var domPreset = model.el.querySelector('.js-color-preset'); var domSpacing = model.el.querySelector('.js-spacing'); var domEdge = model.el.querySelector('.js-edge'); var widgetContainer = model.el.querySelector('.js-pwf'); // Piecewise editor widget model.widget.updateStyle({ backgroundColor: 'rgba(255, 255, 255, 0.6)', histogramColor: 'rgba(100, 100, 100, 0.5)', strokeColor: 'rgb(0, 0, 0)', activeColor: 'rgb(255, 255, 255)', handleColor: 'rgb(50, 150, 50)', buttonDisableFillColor: 'rgba(255, 255, 255, 0.5)', buttonDisableStrokeColor: 'rgba(0, 0, 0, 0.5)', buttonStrokeColor: 'rgba(0, 0, 0, 1)', buttonFillColor: 'rgba(255, 255, 255, 1)', strokeWidth: 2, activeStrokeWidth: 3, buttonStrokeWidth: 1.5, handleWidth: 3, iconSize: 0, padding: 10 }); model.widget.addGaussian(0.5, 1.0, 0.5, 0.5, 0.4); model.widget.setDataArray(dataArray.getData()); model.widget.setColorTransferFunction(lookupTable); model.widget.applyOpacity(piecewiseFunction); model.widget.setContainer(widgetContainer); model.widget.bindMouseListeners(); model.colorDataRange = model.widget.getOpacityRange(); // Attach listeners domToggleButton.addEventListener('click', publicAPI.toggleVisibility); domShadow.addEventListener('change', updateUseShadow); domPreset.addEventListener('change', updateColorMapPreset); domSpacing.addEventListener('input', updateSpacing); domEdge.addEventListener('input', updateEdgeGradient); model.widget.onOpacityChange(function () { model.widget.applyOpacity(piecewiseFunction); model.colorDataRange = model.widget.getOpacityRange(); if (model.rescaleColorMap) { updateColorMapPreset(); } if (!model.renderWindow.getInteractor().isAnimating()) { model.renderWindow.render(); } }); model.widget.onAnimation(function (start) { if (start) { model.renderWindow.getInteractor().requestAnimation(model.widget); } else { model.renderWindow.getInteractor().cancelAnimation(model.widget); model.renderWindow.render(); } }); lookupTable.onModified(function () { model.widget.render(); if (!model.renderWindow.getInteractor().isAnimating()) { model.renderWindow.render(); } }); // Set default values domShadow.value = Number(useShadow) ? '1' : '0'; domPreset.value = presetName; // Apply values updateUseShadow(); updateColorMapPreset(); updateSpacing(); updateEdgeGradient(); }; publicAPI.setContainer = function (el) { if (model.container && model.container !== el) { model.container.removeChild(model.el); } if (model.container !== el) { model.container = el; if (model.container) { model.container.appendChild(model.el); } publicAPI.modified(); } }; var rescaleColorMap = publicAPI.setRescaleColorMap; publicAPI.setRescaleColorMap = function (value) { if (rescaleColorMap(value)) { updateColorMapPreset(); return true; } return false; }; publicAPI.toggleVisibility = function () { publicAPI.setExpanded(!publicAPI.getExpanded()); }; publicAPI.setExpanded = function (expanded) { var elements = model.el.querySelectorAll('.js-toggle'); var count = elements.length; model.expanded = expanded; if (model.expanded) { while (count--) { elements[count].style.display = 'flex'; } } else { while (count--) { elements[count].style.display = 'none'; } } }; publicAPI.getExpanded = function () { return model.expanded; }; publicAPI.setSize = model.widget.setSize; publicAPI.render = model.widget.render; publicAPI.onAnimation = model.widget.onAnimation; // Trigger rendering for any modified event publicAPI.onModified(publicAPI.render); publicAPI.setSize.apply(publicAPI, _toConsumableArray(model.size)); } // ---------------------------------------------------------------------------- // Object factory // ---------------------------------------------------------------------------- var DEFAULT_VALUES = { size: [600, 300], expanded: true, rescaleColorMap: false }; // ---------------------------------------------------------------------------- function extend(publicAPI, model) { var initialValues = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {}; Object.assign(model, DEFAULT_VALUES, initialValues); // Object methods macro.obj(publicAPI, model); macro.setGet(publicAPI, model, ['actor', 'renderWindow', 'rescaleColorMap']); macro.get(publicAPI, model, ['widget']); // Object specific methods vtkVolumeController(publicAPI, model); } // ---------------------------------------------------------------------------- var newInstance = macro.newInstance(extend, 'vtkVolumeController'); // ---------------------------------------------------------------------------- var vtkVolumeController$1 = { newInstance: newInstance, extend: extend }; export default vtkVolumeController$1; export { extend, newInstance };