mirror of
https://github.com/apache/superset.git
synced 2026-04-19 08:04:53 +00:00
feat: Enable cross fitlers in WorldMap and Graph charts (#22886)
This commit is contained in:
committed by
GitHub
parent
a0ca0c04ff
commit
871cab8cbe
@@ -46,6 +46,9 @@ const propTypes = {
|
||||
showBubbles: PropTypes.bool,
|
||||
linearColorScheme: PropTypes.string,
|
||||
color: PropTypes.string,
|
||||
setDataMask: PropTypes.func,
|
||||
onContextMenu: PropTypes.func,
|
||||
emitCrossFilters: PropTypes.bool,
|
||||
};
|
||||
|
||||
const formatter = getNumberFormatter();
|
||||
@@ -66,7 +69,10 @@ function WorldMap(element, props) {
|
||||
sliceId,
|
||||
theme,
|
||||
onContextMenu,
|
||||
setDataMask,
|
||||
inContextMenu,
|
||||
filterState,
|
||||
emitCrossFilters,
|
||||
} = props;
|
||||
const div = d3.select(element);
|
||||
div.classed('superset-legacy-chart-world-map', true);
|
||||
@@ -108,11 +114,47 @@ function WorldMap(element, props) {
|
||||
mapData[d.country] = d;
|
||||
});
|
||||
|
||||
const handleClick = source => {
|
||||
if (!emitCrossFilters) {
|
||||
return;
|
||||
}
|
||||
const pointerEvent = d3.event;
|
||||
pointerEvent.preventDefault();
|
||||
const key = source.id || source.country;
|
||||
let val =
|
||||
countryFieldtype === 'name' ? mapData[key]?.name : mapData[key]?.country;
|
||||
if (!val) {
|
||||
return;
|
||||
}
|
||||
if (val === filterState.value) {
|
||||
val = null;
|
||||
}
|
||||
|
||||
setDataMask({
|
||||
extraFormData: {
|
||||
filters: val
|
||||
? [
|
||||
{
|
||||
col: entity,
|
||||
op: 'IN',
|
||||
val: [val],
|
||||
},
|
||||
]
|
||||
: [],
|
||||
},
|
||||
filterState: {
|
||||
value: val ?? null,
|
||||
selectedValues: val ? [key] : [],
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
const handleContextMenu = source => {
|
||||
const pointerEvent = d3.event;
|
||||
pointerEvent.preventDefault();
|
||||
const key = source.id || source.country;
|
||||
const val = countryFieldtype === 'name' ? mapData[key]?.name : key;
|
||||
const val =
|
||||
countryFieldtype === 'name' ? mapData[key]?.name : mapData[key]?.country;
|
||||
if (val) {
|
||||
const filters = [
|
||||
{
|
||||
@@ -178,7 +220,8 @@ function WorldMap(element, props) {
|
||||
done: datamap => {
|
||||
datamap.svg
|
||||
.selectAll('.datamaps-subunit')
|
||||
.on('contextmenu', handleContextMenu);
|
||||
.on('contextmenu', handleContextMenu)
|
||||
.on('click', handleClick);
|
||||
},
|
||||
});
|
||||
|
||||
@@ -190,7 +233,26 @@ function WorldMap(element, props) {
|
||||
.selectAll('circle.datamaps-bubble')
|
||||
.style('fill', color)
|
||||
.style('stroke', color)
|
||||
.on('contextmenu', handleContextMenu);
|
||||
.on('contextmenu', handleContextMenu)
|
||||
.on('click', handleClick);
|
||||
}
|
||||
|
||||
if (filterState.selectedValues?.length > 0) {
|
||||
d3.selectAll('path.datamaps-subunit')
|
||||
.filter(
|
||||
countryFeature =>
|
||||
!filterState.selectedValues.includes(countryFeature.id),
|
||||
)
|
||||
.style('fill-opacity', theme.opacity.mediumLight);
|
||||
|
||||
// hack to ensure that the clicked country's color is preserved
|
||||
// sometimes the fill color would get default grey value after applying cross filter
|
||||
filterState.selectedValues.forEach(value => {
|
||||
d3.select(`path.datamaps-subunit.${value}`).style(
|
||||
'fill',
|
||||
mapData[value]?.fillColor,
|
||||
);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user