This is an automated email from the ASF dual-hosted git repository. sushuang pushed a commit to branch fix/visualMap-range in repository https://gitbox.apache.org/repos/asf/echarts.git
commit 707f88a7a72eef03dd2656e7526468b29b6329c1 Author: 100pah <[email protected]> AuthorDate: Thu Jul 17 18:35:31 2025 +0800 feat(visualMap): Support option `unboundedRange` to disable unbounded range behavior in continuous visual map component. --- src/component/visualMap/ContinuousModel.ts | 31 ++++++++++-- test/runTest/actions/__meta__.json | 1 + test/visualMap-on-data.html | 76 ++++++++++++++++++++++++++++++ 3 files changed, 104 insertions(+), 4 deletions(-) diff --git a/src/component/visualMap/ContinuousModel.ts b/src/component/visualMap/ContinuousModel.ts index 569842667..270595afc 100644 --- a/src/component/visualMap/ContinuousModel.ts +++ b/src/component/visualMap/ContinuousModel.ts @@ -45,11 +45,29 @@ export interface ContinousVisualMapOption extends VisualMapOption { calculable?: boolean /** - * selected range. In default case `range` is [min, max] - * and can auto change along with modification of min max, + * selected range. In default case `range` is `[min, max]` + * and can auto change along with user interaction or action "selectDataRange", * until user specified a range. + * @see strictRange for the special case when `range[0]` or `range[1]` touch `min` or `max`. */ range?: number[] + /** + * Whether to treat the range as unbounded when `range` touches `min` or `max`. + * - `true`: + * when `range[0]` <= `min`, the actual range becomes `[-Infinity, range[1]]`; + * when `range[1]` >= `max`, the actual range becomes `[range[0], Infinity]`. + * NOTE: + * - This provides a way to ensure all data can be considered in-range when `min`/`max` + * are not precisely known. + * - Default is `true` for backward compatibility. + * - Piecewise VisualMap does not need it, since it can define unbounded range in each piece, + * such as "< 12", ">= 300". + * - `false`: + * Disable the unbounded range behavior. + * Use case: `min`/`max` reflect the normal data range, and some outlier data should always be + * treated as out of range. + */ + unboundedRange?: boolean /** * Whether to enable hover highlight. */ @@ -183,8 +201,13 @@ class ContinuousModel extends VisualMapModel<ContinousVisualMapOption> { */ getValueState(value: number): VisualState { const range = this.option.range; + const dataExtent = this.getExtent(); + const unboundedRange = zrUtil.retrieve2(this.option.unboundedRange, true); - return range[0] <= value && value <= range[1] ? 'inRange' : 'outOfRange'; + return ( + ((unboundedRange && range[0] <= dataExtent[0]) || range[0] <= value) + && ((unboundedRange && range[1] >= dataExtent[1]) || value <= range[1]) + ) ? 'inRange' : 'outOfRange'; } findTargetDataIndices(range: number[]) { @@ -198,7 +221,7 @@ class ContinuousModel extends VisualMapModel<ContinousVisualMapOption> { const dataIndices: number[] = []; const data = seriesModel.getData(); - data.each(this.getDataDimensionIndex(data), function (value, dataIndex) { + data.each(this.getDataDimensionIndex(data), function (value: number, dataIndex) { range[0] <= value && value <= range[1] && dataIndices.push(dataIndex); }, this); diff --git a/test/runTest/actions/__meta__.json b/test/runTest/actions/__meta__.json index 757ec4b10..39b1bf85d 100644 --- a/test/runTest/actions/__meta__.json +++ b/test/runTest/actions/__meta__.json @@ -237,5 +237,6 @@ "universalTransition3": 2, "visualMap-categories": 1, "visualMap-multi-continuous": 1, + "visualMap-on-data": 1, "visualMap-selectMode": 2 } \ No newline at end of file diff --git a/test/visualMap-on-data.html b/test/visualMap-on-data.html index 34966d9fe..c0dc309c2 100644 --- a/test/visualMap-on-data.html +++ b/test/visualMap-on-data.html @@ -37,6 +37,7 @@ under the License. <div id="main0"></div> + <div id="main-unbounded-continuous"></div> <script> @@ -82,5 +83,80 @@ under the License. }); </script> + + + + <script> + + var option; + + require([ + 'echarts' + ], function (echarts) { + + var option = { + tooltip: { + }, + visualMap: { + type: 'continuous', + top: 'middle', + calculable: true, + min: 0, + max: 1000, + inRange: { + color: ['red', 'blue'] + }, + outOfRange: { + color: ['#999'] + }, + }, + xAxis: { + type: 'value', + }, + yAxis: { + type: 'value', + }, + series: [{ + type: 'scatter', + itemStyle: { + color: 'green' + }, + data: [ + [10, 712], + [20, 920], + [10, 503], + [40, 1020], + [50, -100], + [60, 420], + [70, -10] + ] + }] + }; + + var chart = testHelper.create(echarts, 'main-unbounded-continuous', { + option: option, + title: [ + '**unboundedRange** in continuous visualMap.', + 'outliers (>= 1000 or <= 0) should be always be treated as out of range.', + ], + inputs: [ + { + type: 'select', + text: 'unboundedRange:', + values: [true, false], + onChange: function (value) { + chart.setOption({ + visualMap: { + unboundedRange: this.value + } + }); + } + } + ] + }); + }); + + </script> + </body> </html> \ No newline at end of file --------------------------------------------------------------------- To unsubscribe, e-mail: [email protected] For additional commands, e-mail: [email protected]
