From 96a54cfe13049ccde3a3e5920d827745647d165b Mon Sep 17 00:00:00 2001 From: Lisa Stillwell Date: Thu, 7 Nov 2024 18:36:12 -0500 Subject: [PATCH] #296 cleaned up imperial/intervals combo bugs --- .../settings/colormaps/colormap-slider.js | 47 +++++-------------- .../trays/settings/colormaps/style-edit.js | 31 +++++++++--- .../trays/settings/colormaps/utils.js | 11 +++++ 3 files changed, 47 insertions(+), 42 deletions(-) diff --git a/src/components/trays/settings/colormaps/colormap-slider.js b/src/components/trays/settings/colormaps/colormap-slider.js index 7131fcd..c82b8f2 100644 --- a/src/components/trays/settings/colormaps/colormap-slider.js +++ b/src/components/trays/settings/colormaps/colormap-slider.js @@ -4,7 +4,7 @@ import SldStyleParser from 'geostyler-sld-parser'; import { Slider, Box } from '@mui/joy'; import { useSettings } from '@context'; import { restoreColorMapType, metersToFeet, feetToMeters, mpsToKnots, knotsToMps, mpsToMph, mphToMps } from '@utils/map-utils'; -import { maxSliderValues, sliderSteps, sliderMarkSteps } from './utils'; +import { getFloatNumberFromLabel, maxSliderValues, sliderSteps, sliderMarkSteps } from './utils'; const MAXELE = 'maxele'; const MAXWVEL = 'maxwvel'; @@ -24,28 +24,6 @@ export const ColormapSlider = ({style}) => { speedType, } = useSettings(); - // convert the value to imperial, if not metric - const convertValue = (product, v) => { - let newValue = v; - - if (unitsType.current !== "metric") { - // handle speed conversions - if(product === MAXWVEL) { - if(speedType.current === "knots") { - newValue = mpsToKnots(v); - } - else { // mph - newValue = mpsToMph(v); - } - } - else { // handle distance conversion - newValue = metersToFeet(v); - } - } - - return Math.round(newValue); - }; - const sldParser = new SldStyleParser(); // set the correct slider values for the appropriate style and unit type @@ -53,10 +31,8 @@ export const ColormapSlider = ({style}) => { let max_slider_value = 0; let slider_step = 0; const marks = []; - let product = ''; if (style.name.includes(MAXWVEL)) { - product = MAXWVEL; max_slider_value = maxSliderValues[MAXWVEL][unitsType.current]; slider_step = sliderSteps[MAXWVEL][unitsType.current]; for (let i = 0; i <= max_slider_value; i+=sliderMarkSteps[MAXWVEL][unitsType.current]) { @@ -65,7 +41,6 @@ export const ColormapSlider = ({style}) => { } else if (style.name.includes(SWAN)) { - product = SWAN; max_slider_value = maxSliderValues[SWAN][unitsType.current]; slider_step = sliderSteps[SWAN][unitsType.current]; for (let i = 0; i <= max_slider_value; i+=sliderMarkSteps[SWAN][unitsType.current]) { @@ -73,7 +48,6 @@ export const ColormapSlider = ({style}) => { } } else { // maxele - product = MAXELE; max_slider_value = maxSliderValues[MAXELE][unitsType.current]; slider_step = sliderSteps[MAXELE][unitsType.current]; for (let i = 0; i <= max_slider_value; i+=sliderMarkSteps[MAXELE][unitsType.current]) { @@ -87,8 +61,8 @@ export const ColormapSlider = ({style}) => { setMinSliderValue(0); const colormapEntries = style.rules[0].symbolizers[0].colorMap.colorMapEntries; - setValue([convertValue(product, parseFloat(colormapEntries[colormapEntries.length-1].quantity)), - convertValue(product, parseFloat(colormapEntries[0].quantity))]); + setValue([getFloatNumberFromLabel(colormapEntries[colormapEntries.length-1].label, 0), + parseFloat(colormapEntries[0].quantity)]); }; useEffect(() => { @@ -103,7 +77,8 @@ export const ColormapSlider = ({style}) => { const colorMapEntries = geostylerStyle.output.rules[0].symbolizers[0].colorMap.colorMapEntries; // now temporarily set that max range for the style colorMapEntries[colorMapEntries.length-1].quantity = - parseFloat(colorMapEntries[colorMapEntries.length-1].label.match(/[+-]?\d+(\.\d+)?/g)).toFixed(2); + getFloatNumberFromLabel(colorMapEntries[colorMapEntries.length-1].label, 2); + //parseFloat(colorMapEntries[colorMapEntries.length-1].label.match(/[+-]?\d+(\.\d+)?/g)).toFixed(2); } setCurrentStyle(geostylerStyle.output); @@ -160,7 +135,8 @@ export const ColormapSlider = ({style}) => { // if this is an intervals type of colormap, correct last entry in range if (style.rules[0].symbolizers[0].colorMap.type === "intervals") { const colorMapEntries = style.rules[0].symbolizers[0].colorMap.colorMapEntries; - dataRange[0] = parseFloat(colorMapEntries[colorMapEntries.length-1].label.match(/[+-]?\d+(\.\d+)?/g)).toFixed(2); + //dataRange[0] = parseFloat(colorMapEntries[colorMapEntries.length-1].label.match(/[+-]?\d+(\.\d+)?/g)).toFixed(2); + dataRange[0] = getFloatNumberFromLabel(colorMapEntries[colorMapEntries.length-1].label, 2); } return(dataRange.reverse()); @@ -215,7 +191,7 @@ export const ColormapSlider = ({style}) => { } else { entry.label = range[idx] + " " + speedType.current; - } + } } else { entry.label = range[idx] + ((unitsType.current === "metric")? " m" : " ft"); @@ -227,14 +203,15 @@ export const ColormapSlider = ({style}) => { if (style.name.includes("maxwvel")) { // 2 different speed types for imperial if (unitsType.current === "imperial") { - entry.label = range[idx] + ((speedType.current === "knots")? " kn" : " mph"); + entry.label = ">= " + range[idx] + ((speedType.current === "knots")? " kn" : " mph"); } else { - entry.label = range[idx] + " " + speedType.current; + entry.label = ">= " + range[idx] + " " + speedType.current; } } else { - entry.label = ">= " + entry.quantity + ((unitsType.current === "metric")? " m" : " ft"); + //entry.label = ">= " + entry.quantity + ((unitsType.current === "metric")? " m" : " ft"); + entry.label = ">= " + range[idx] + ((unitsType.current === "metric")? " m" : " ft"); } entry.quantity = maxSliderValue; } diff --git a/src/components/trays/settings/colormaps/style-edit.js b/src/components/trays/settings/colormaps/style-edit.js index aa066d7..62c30d2 100644 --- a/src/components/trays/settings/colormaps/style-edit.js +++ b/src/components/trays/settings/colormaps/style-edit.js @@ -15,7 +15,7 @@ import SldStyleParser from 'geostyler-sld-parser'; import { ColorMapEditor } from '@renci/apsviz-geostyler'; import { restoreColorMapType } from '@utils/map-utils'; import _cloneDeep from 'lodash/cloneDeep'; -import { maxSliderValues } from './utils'; +import { getFloatNumberFromLabel, maxSliderValues } from './utils'; const MAXELE = 'maxele'; const MAXWVEL = 'maxwvel'; @@ -30,6 +30,8 @@ export const StyleEditor = () => { const { mapStyle, layerOpacity, + unitsType, + speedType, } = useSettings(); const [colormap, setColormap] = useState(); @@ -99,7 +101,7 @@ export const StyleEditor = () => { // save the label units for later restoration let labelUnit = colormap.colorMapEntries[0].label.split("").reverse().join("").split(" ")[0]; - // reverse again if this was a m/s unit - whew! + // reverse again if this was anything other than meters unit - whew! if (labelUnit.length > 1) labelUnit = labelUnit.split("").reverse().join(""); //update type of colorMap @@ -113,7 +115,7 @@ export const StyleEditor = () => { // check to see if this an intervals type of colormap // must handle weird last entry case, if so const topRange = (colormap.type === "intervals") ? - Number(colormap.colorMapEntries[colormap.colorMapEntries.length-1].label.match(/[+-]?\d+(\.\d+)?/g)) + getFloatNumberFromLabel(colormap.colorMapEntries[colormap.colorMapEntries.length-1].label, 0) : Number(colormap.colorMapEntries[colormap.colorMapEntries.length-1].quantity); @@ -135,7 +137,7 @@ export const StyleEditor = () => { else { if (value.colorMapEntries[value.colorMapEntries.length-1].label.includes(">=")) { const last = value.colorMapEntries.length-1; - value.colorMapEntries[last].quantity = parseFloat(value.colorMapEntries[last].label.match(/[+-]?\d+(\.\d+)?/g)).toFixed(2); + value.colorMapEntries[last].quantity = getFloatNumberFromLabel(value.colorMapEntries[last].label, 2); const labelParts = value.colorMapEntries[last].label.split(" "); if (labelParts.length >= 3) value.colorMapEntries[last].label = parseFloat(labelParts[1]).toFixed(2) + " " + labelParts[2]; @@ -158,13 +160,28 @@ export const StyleEditor = () => { const styleName = geoStylerStyle.output.name.split('_')[0]; if (colormap.type === "intervals") { const lastIndex = colormap.colorMapEntries.length-1; + let labelUnit = ""; + // need to get value for last value in the range from the label + // for imperial based values, because the value is always represented + // in it metric form. + const lastQuantity = getFloatNumberFromLabel(colormap.colorMapEntries[lastIndex].label, 1); + console.log(lastQuantity); if (styleName === MAXWVEL) { - geoStylerStyle.output.rules[0].symbolizers[0].colorMap.colorMapEntries[lastIndex].label = ">= " + colormap.colorMapEntries[lastIndex].quantity + " m/s"; + if (unitsType.current === "imperial") { + labelUnit = ((speedType.current === "knots")? " kn" : " mph"); + } + else { + labelUnit = "mps"; + } } else { - geoStylerStyle.output.rules[0].symbolizers[0].colorMap.colorMapEntries[lastIndex].label = ">= " + colormap.colorMapEntries[lastIndex].quantity + " m"; + if (unitsType.current === "imperial") + labelUnit = " ft"; } - geoStylerStyle.output.rules[0].symbolizers[0].colorMap.colorMapEntries[lastIndex].quantity = maxSliderValues[styleName]; + geoStylerStyle.output.rules[0].symbolizers[0].colorMap.colorMapEntries[lastIndex].label = ">= " + lastQuantity + labelUnit; + // when the colormap type is intervals, have to set last colormap entry to be an estimated mav value for that layer + // to account for the way interval colormaps work. + geoStylerStyle.output.rules[0].symbolizers[0].colorMap.colorMapEntries[lastIndex].quantity = maxSliderValues[styleName][unitsType.current]; } // save colormap type - it seems to get wiped out when the parser diff --git a/src/components/trays/settings/colormaps/utils.js b/src/components/trays/settings/colormaps/utils.js index 62b0ec7..2dd9292 100644 --- a/src/components/trays/settings/colormaps/utils.js +++ b/src/components/trays/settings/colormaps/utils.js @@ -14,4 +14,15 @@ export const sliderMarkSteps = { "maxele": { "metric": 1, "imperial": 5 }, "maxwvel": { "metric": 10, "imperial": 20 }, "swan": { "metric": 5, "imperial": 10 } +}; + +// find a float number in a colormap entry label and +// return with designated decimal places. +export const getFloatNumberFromLabel = (label, decimalPlaces) => { + let num = 0.0; + const labelMatch = label.match(/[+-]?\d+(\.\d+)?/g); + if (labelMatch) + num = parseFloat(labelMatch).toFixed(decimalPlaces); + + return num; }; \ No newline at end of file