mirror of
https://github.com/maputnik/editor.git
synced 2026-10-13 14:33:44 +00:00
Fix layer group expansion state after deletion (#2146)
Deleting a layer changes the starting indices of later groups, so their stored expansion state no longer matches. Preserve that state through surviving layer IDs when rebuilding the group keys. This keeps expanded groups open after deleting an earlier layer or the first layer of a group. Separate groups with the same prefix retain their own states; if deletion joins two groups, the merged group stays expanded when either was expanded. - Fixes #1781. Adds five deletion regression tests, a small style fixture, and a changelog entry. Validation: - All 33 layer-list E2E tests and 50 unit tests pass. - Lint and the production build, including TypeScript checking, pass. - Manually checked OSM Liberty: all 15 groups remain expanded after deleting the background layer. - The full E2E suite reports 160 passing tests and one failure in `modals > open > upload` (`Could not get styleItem from localStorage`). The same failure reproduces with the original production code restored. --------- Co-authored-by: Harel M <harel.mazor@gmail.com>
This commit is contained in:
co-authored by
Harel M
parent
0a4c1710e2
commit
1301dc03e7
@@ -106,13 +106,13 @@ class LayerListContainerInternal extends React.Component<LayerListContainerInter
|
||||
});
|
||||
};
|
||||
|
||||
groupedLayers(): (LayerSpecification & {key: string})[][] {
|
||||
groupedLayers(layers = this.props.layers): (LayerSpecification & {key: string})[][] {
|
||||
const groups = [];
|
||||
const layerIdCount = new Map();
|
||||
|
||||
for (let i = 0; i < this.props.layers.length; i++) {
|
||||
const origLayer = this.props.layers[i];
|
||||
const previousLayer = this.props.layers[i-1];
|
||||
for (let i = 0; i < layers.length; i++) {
|
||||
const origLayer = layers[i];
|
||||
const previousLayer = layers[i-1];
|
||||
layerIdCount.set(origLayer.id,
|
||||
layerIdCount.has(origLayer.id) ? layerIdCount.get(origLayer.id) + 1 : 0
|
||||
);
|
||||
@@ -192,7 +192,39 @@ class LayerListContainerInternal extends React.Component<LayerListContainerInter
|
||||
return propsChanged;
|
||||
}
|
||||
|
||||
/**
|
||||
* Preserves group state through surviving layer IDs when group indices change.
|
||||
* If deletion joins groups, the result stays expanded when either group was.
|
||||
*/
|
||||
private preserveLayerGroupState(previousLayers: LayerSpecification[]) {
|
||||
if (previousLayers === this.props.layers) return;
|
||||
|
||||
const collapsedByLayer = new Map<string, boolean>();
|
||||
let idx = 0;
|
||||
for (const layers of this.groupedLayers(previousLayers)) {
|
||||
const collapsed = this.isCollapsed(layerPrefix(layers[0].id), idx);
|
||||
for (const layer of layers) {
|
||||
collapsedByLayer.set(layer.id, collapsed);
|
||||
}
|
||||
idx += layers.length;
|
||||
}
|
||||
|
||||
const collapsedGroups: {[key: string]: boolean} = {};
|
||||
idx = 0;
|
||||
for (const layers of this.groupedLayers()) {
|
||||
const lookupKey = [layerPrefix(layers[0].id), idx].join("-");
|
||||
collapsedGroups[lookupKey] = layers.every(layer => collapsedByLayer.get(layer.id) !== false);
|
||||
idx += layers.length;
|
||||
}
|
||||
|
||||
if (!lodash.isEqual(collapsedGroups, this.state.collapsedGroups)) {
|
||||
this.setState({ collapsedGroups });
|
||||
}
|
||||
}
|
||||
|
||||
componentDidUpdate (prevProps: LayerListContainerProps) {
|
||||
this.preserveLayerGroupState(prevProps.layers);
|
||||
|
||||
if (prevProps.selectedLayerIndex !== this.props.selectedLayerIndex) {
|
||||
const selectedItemNode = this.selectedItemRef.current;
|
||||
if (selectedItemNode && selectedItemNode.node) {
|
||||
|
||||
Reference in New Issue
Block a user