Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feature: geo component and map series support SVG format source #14571

Merged
merged 27 commits into from
Apr 7, 2021

Conversation

100pah
Copy link
Member

@100pah 100pah commented Apr 1, 2021

Brief Information

This pull request is in the type of:

  • bug fixing
  • new feature
  • others

Features:

Support use SVG as the map in both Geo component and series map.

fetch('../../vis-data/map/svg/geo-topo/Map_of_Iceland.svg').then(response => response.text()).then((svg) => {
    echarts.registerMap('Map_of_Iceland', {
        svg: svg
    });
    option = {
        tooltip: {
            alwaysShowContent: true,
            enterable: true,
            extraCssText: 'user-select: text'
        },
        geo: [{
            map: 'Map_of_Iceland',
            ...
        }]
    };
});    

Support tooltip on Geo component

Support label option on Geo component

Support to name some SVG tags to enable them to be configured in option regions.

<path name="trip1"  ... />

Then this config enabled:

option = {
    geo: {
        tooltip: { show: true, ... },
        regions: [{
            name: 'trip1',
            itemStyle: { ... },
            label: { ... },
            tooltip: { ... }
        }]
    }
}

These SVG tags are available to be named:
'rect', 'circle', 'line', 'ellipse', 'polygon', 'polyline', 'path', 'text', 'tspan', 'g'

Once named:

  • All of the tags can trigger mouse event to users (like click, mouseover, ...).
    That is, can be listened by
    chart.on('click', { geoIndex: 0 }, function (params) {
        // ...
    });
  • All of those tags support to trigger state change when
    • mouseover/mouseout
    • dispatchAction({ type: 'highlight'/'downplay', ... });
  • The path can change state style (normal/emphasis/select/blur) when hover or dispatchAction
    • Only 'rect', 'circle', 'line', 'ellipse', 'polygon', 'polyline', 'path' support state style.
    • text/tspan/image can not apply state style.
  • All of those tags support to trigger tooltip when
    • mouseover/mouseout
    • dispatchAction({ type: 'showTip', ... });
  • If multiple tags can have the same name:
    • They have the "hover link" effect. That is, if hovering on one element, all of the elements with the same name will be highlighted, and other elements in SVG can be blurred if emphasis.focus set.
    • They share one region option (style, label, tooltip, ...).
    • They display their labels respectively.
  • <g> can be named.
    • If <g name="xxx">, all of the descendants will apply the region options styles if possible.
    • But a single label/tooltip only displayed based on the center of this <g>.

Support focus-blur on Geo component.

geo: {
    emphasis: {
        // enable focus-blur feature.
        // only 'self' supported.
        focus: 'self' 
    }
}

Once focus-blur feature enabled, the "blurScope" is this Geo component. That is, the entire SVG
Note: in series-map, we do not support "blur all of the SVG" yet. There is a little implementation trouble. So do not support it until some requirement come.

geoSVG named tag support select:

  • follow echarts select option.
  • follow "geoselectchanged" event (on geo component) and selectchanged event (on series-map).
  • "geoselectchanged" event: add param: allSelected: { geoIndex: number, name: string[] }[]

fix: [common focus-blur feature]

make API trigger emphasis blur correct (should leave blur firstly for other series).

fix: [common tooltip feature]

fix tooltip component default position: should apply position on option firstly.



Some implementation details:

  • refactor of geoJSON & SVG source loader and management.
  • label scale implementation change: user afterUpdate hook rather than divide parentScale.
  • Some refactor to Region: the original Region is migrated to GeoJSONRegion. And make Region as the base class of GeoJSONRegion and GeoSVGRegion. Modify the constructor of Geo.
  • Remove Geo['_nameCoordMap'], instead, calculate center on demand.
  • Fix that some API missing nameProperty and geoJSON should cached not only by mapName but also by nameProperty.
  • About focus-blur on component:
    • Support component focus blur. The option emphasis.focus can be specified to enable this feature. emphasis.focus only supports the value 'self'. The option emphasis.focusScope is not supported in component. That is, the focus scope can be only a single component itself. All of the elements in this component will be blurred. Added Component['focusBlurEnabled'] to enable component blur.
    • Support component hover link when highlight with a given name. There probably be multiple elements share one region name while those region elements has no common ancestor. hover link enables them to be highlighted together. Implementation: if a component implements Component['findHighDownDispatchers'], dispatcher elements by a given name will be found and this feature is enabled.
    • Support component highlight/downplay be triggered by dispatchAction. Implementation: if a component implements Component['findHighDownDispatchers'], dispatcher elements by a given name will be found and this feature is enabled.


Others

  • remove the support of "load multiple geoJSON or SVG in one map name". This feature is never documented and published. And this feature have an inherent problem that it's not easy to normalize the unit among the different SVG. After this PR, one map name can only have one geoJSON or one SVG.
  • Do not support nameMap in geoSVG until some real requirements come.

Test Case

test/geo-svg.html
test/geo-svg-demo.html

x1

x2

x3

x4

x5
x6
x7

(1) refactor of geoJSON & SVG source loader and management.
(2) remove the support of "load multiple geoJSON or SVG in one map name". This feature is never documented and published. And this feature have a inherent problem that it's not easy to normalize the unit among the different SVG. After this commit, one map name can only have one geoJSON or one SVG.
(1) label scale implementation change: user afterUpdate rather than / parentScale.
(2) some refactor and clean code.
(1) "geoselectchanged" event: add param: allSelected: { geoIndex: number, name: string[] }[]
(2) geoSVG resource support:
+ label
+ emphasis/select/blur state
+ "geoselectchanged" event (on geo component)
+ "selectchanged" event (on map series)
(3) some refactor to make those happen:
+ The original `Region` is migrated to `GeoJSONRegion`. And make `Region` as the base class of `GeoJSONRegion` and `GeoSVGRegion`.
+ Modify the constructor of `Geo`.
(1) fix contain point calculation.
(2) remove Geo['_nameCoordMap'], instead, calculate center on demand.
(3) fix that some API missing nameProperty and geoJSON should cached not only by mapName but also by nameProperty.
(4) do not support nameMap in geoSVG until some real requirements come.
(5) svg line polyline use 'region.lineStyle' rather than 'region.itemStyle'
(6) svg text tspan image are enabled to trigger tooltip and user event (but not supported to change state and style yet).
(1) add missing test:visual
(2) fix tooltip component default position: should apply `position` on option firstly.
(1) Support component focus blur.
The option `emphasis.focus` can be specified to enable this feature. `emphasis.focus` only supports the value `'self'`.
The option `emphasis.focusScope` is not supported in component. That is, the focus scope can be only a single component itself. All of the elements in this component will be blurred.
Added `Component['focusBlurEnabled']` to enable component blur.
(2) Support component hover link when highlight with a given name.
There probably be multiple elements share one region name while those region elements has no common ancestor. hover link enables them to be highlighted together.
Implementation: if a component implements `Component['findHighDownDispatchers']`,  dispatcher elements by a given name will be found and this feature is enabled.
(3) Support component highlight/downplay be triggered by `dispatchAction`.
Implementation: if a component implements `Component['findHighDownDispatchers']`,  dispatcher elements by a given name will be found and this feature is enabled.
(4) Some refactor.
(1) support name on <g>.
(2) some refactor.
@echarts-bot
Copy link

echarts-bot bot commented Apr 1, 2021

Thanks for your contribution!
The community will review it ASAP. In the meanwhile, please checkout the coding standard and Wiki about How to make a pull request.

The pull request is marked to be PR: author is committer because you are a committer of this project.

@100pah 100pah marked this pull request as ready for review April 6, 2021 18:20
@pissang pissang merged commit b059e22 into master Apr 7, 2021
@echarts-bot
Copy link

echarts-bot bot commented Apr 7, 2021

Congratulations! Your PR has been merged. Thanks for your contribution! 👍

@pissang pissang deleted the fix/geo-svg branch April 7, 2021 03:42
@pissang pissang added this to the 5.1.0 milestone Apr 7, 2021
@pissang pissang changed the title feature: support geoSVG feature: geo component and map series support SVG format source Apr 9, 2021
@100pah
Copy link
Member Author

100pah commented Jan 7, 2022

[memento] Some historical discussion about:

  • A. "all use itemStyle"
    • cons,
      • If <line> uses itemStyle, itemStyle.color means stoke, it might be weird to use color and borderWidth on line.
  • B. "<line> and <polyline> use lineStyle while others use itemStyle".
    • cons,
      • Some SVG uses fill on <polyline>, if <polyline> uses lineStyle, fill can not be specified. [major factor]
      • not easy to realize this special settings. If users intent to set opacity, it may be wried to set some opacity on lineStyle and some on itemStyle.
      • most of SVG uses <path>, which seems can only use itemStyle even it used to draws a line.

At present, the implementation is "all use itemStyle".

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

2 participants