From 86b928385898cc34eecc9d1d30b302e59b54f8e9 Mon Sep 17 00:00:00 2001 From: Yuxin <55794321+yvonneyx@users.noreply.github.com> Date: Mon, 28 Oct 2024 14:22:01 +0800 Subject: [PATCH] fix: fix issue with hidden elements being displayed in optimize-viewport-transform (#6438) * fix: fix issue with hidden elements being displayed in optimize-viewport-transform * fix: update remarks * fix: update remarks * test: update unit tests --- .../behavior-optimize-viewport-transform.ts | 14 +- .../viewport-change-key-text.svg | 1607 +++++++++++++++++ ...ort-change.svg => viewport-change-key.svg} | 0 .../viewport-change-keys.svg | 1607 +++++++++++++++++ .../optimize-viewport-transform.spec.ts | 57 +- .../behaviors/optimize-viewport-transform.ts | 54 +- 6 files changed, 3317 insertions(+), 22 deletions(-) create mode 100644 packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change-key-text.svg rename packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/{viewport-change.svg => viewport-change-key.svg} (100%) create mode 100644 packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change-keys.svg diff --git a/packages/g6/__tests__/demos/behavior-optimize-viewport-transform.ts b/packages/g6/__tests__/demos/behavior-optimize-viewport-transform.ts index ec3644503b1..adc68219865 100644 --- a/packages/g6/__tests__/demos/behavior-optimize-viewport-transform.ts +++ b/packages/g6/__tests__/demos/behavior-optimize-viewport-transform.ts @@ -1,4 +1,6 @@ import data from '@@/dataset/cluster.json'; +import type { DisplayObject } from '@antv/g'; +import type { ElementType } from '@antv/g6'; import { Graph } from '@antv/g6'; export const behaviorOptimizeViewportTransform: TestCase = async (context) => { @@ -23,7 +25,17 @@ export const behaviorOptimizeViewportTransform: TestCase = async (context) => { startArrow: true, }, }, - behaviors: ['drag-canvas', 'zoom-canvas', 'scroll-canvas', 'optimize-viewport-transform'], + behaviors: [ + 'drag-canvas', + 'zoom-canvas', + 'scroll-canvas', + { + key: 'optimize-viewport-transform', + type: 'optimize-viewport-transform', + shapes: (type: ElementType, shape: DisplayObject) => type === 'node' && shape.className === 'key', + }, + ], + animation: false, }); await graph.render(); diff --git a/packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change-key-text.svg b/packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change-key-text.svg new file mode 100644 index 00000000000..32a025c75db --- /dev/null +++ b/packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change-key-text.svg @@ -0,0 +1,1607 @@ + + + + + + + + + + + + + + + + + + 0-1 + + + + + + + + + + + + + + + + + 0-2 + + + + + + + + + + + + + + + + + 0-3 + + + + + + + + + + + + + + + + + 0-4 + + + + + + + + + + + + + + + + + 0-5 + + + + + + + + + + + + + + + + + 0-7 + + + + + + + + + + + + + + + + + 0-8 + + + + + + + + + + + + + + + + + 0-9 + + + + + + + + + + + + + + + + + 0-10 + + + + + + + + + + + + + + + + + 0-11 + + + + + + + + + + + + + + + + + 0-13 + + + + + + + + + + + + + + + + + 0-14 + + + + + + + + + + + + + + + + + 0-15 + + + + + + + + + + + + + + + + + 0-16 + + + + + + + + + + + + + + + + + 2-3 + + + + + + + + + + + + + + + + + 4-5 + + + + + + + + + + + + + + + + + 4-6 + + + + + + + + + + + + + + + + + 5-6 + + + + + + + + + + + + + + + + + 7-13 + + + + + + + + + + + + + + + + + 8-14 + + + + + + + + + + + + + + + + + 9-10 + + + + + + + + + + + + + + + + + 10-22 + + + + + + + + + + + + + + + + + 10-14 + + + + + + + + + + + + + + + + + 10-12 + + + + + + + + + + + + + + + + + 10-24 + + + + + + + + + + + + + + + + + 10-21 + + + + + + + + + + + + + + + + + 10-20 + + + + + + + + + + + + + + + + + 11-24 + + + + + + + + + + + + + + + + + 11-22 + + + + + + + + + + + + + + + + + 11-14 + + + + + + + + + + + + + + + + + 12-13 + + + + + + + + + + + + + + + + + 16-17 + + + + + + + + + + + + + + + + + 16-18 + + + + + + + + + + + + + + + + + 16-21 + + + + + + + + + + + + + + + + + 16-22 + + + + + + + + + + + + + + + + + 17-18 + + + + + + + + + + + + + + + + + 17-20 + + + + + + + + + + + + + + + + + 18-19 + + + + + + + + + + + + + + + + + 19-20 + + + + + + + + + + + + + + + + + 19-33 + + + + + + + + + + + + + + + + + 19-22 + + + + + + + + + + + + + + + + + 19-23 + + + + + + + + + + + + + + + + + 20-21 + + + + + + + + + + + + + + + + + 21-22 + + + + + + + + + + + + + + + + + 22-24 + + + + + + + + + + + + + + + + + 22-25 + + + + + + + + + + + + + + + + + 22-26 + + + + + + + + + + + + + + + + + 22-23 + + + + + + + + + + + + + + + + + 22-28 + + + + + + + + + + + + + + + + + 22-30 + + + + + + + + + + + + + + + + + 22-31 + + + + + + + + + + + + + + + + + 22-32 + + + + + + + + + + + + + + + + + 22-33 + + + + + + + + + + + + + + + + + 23-28 + + + + + + + + + + + + + + + + + 23-27 + + + + + + + + + + + + + + + + + 23-29 + + + + + + + + + + + + + + + + + 23-30 + + + + + + + + + + + + + + + + + 23-31 + + + + + + + + + + + + + + + + + 23-33 + + + + + + + + + + + + + + + + + 32-33 + + + + + + + + + + + + 0 + + + + + + + + + + + + + + + + + 1 + + + + + + + + + + + + + + + + + 2 + + + + + + + + + + + + + + + + + 3 + + + + + + + + + + + + + + + + + 4 + + + + + + + + + + + + + + + + + 5 + + + + + + + + + + + + + + + + + 6 + + + + + + + + + + + + + + + + + 7 + + + + + + + + + + + + + + + + + 8 + + + + + + + + + + + + + + + + + 9 + + + + + + + + + + + + + + + + + 10 + + + + + + + + + + + + + + + + + 11 + + + + + + + + + + + + + + + + + 12 + + + + + + + + + + + + + + + + + 13 + + + + + + + + + + + + + + + + + 14 + + + + + + + + + + + + + + + + + 15 + + + + + + + + + + + + + + + + + 16 + + + + + + + + + + + + + + + + + 17 + + + + + + + + + + + + + + + + + 18 + + + + + + + + + + + + + + + + + 19 + + + + + + + + + + + + + + + + + 20 + + + + + + + + + + + + + + + + + 21 + + + + + + + + + + + + + + + + + 22 + + + + + + + + + + + + + + + + + 23 + + + + + + + + + + + + + + + + + 24 + + + + + + + + + + + + + + + + + 25 + + + + + + + + + + + + + + + + + 26 + + + + + + + + + + + + + + + + + 27 + + + + + + + + + + + + + + + + + 28 + + + + + + + + + + + + + + + + + 29 + + + + + + + + + + + + + + + + + 30 + + + + + + + + + + + + + + + + + 31 + + + + + + + + + + + + + + + + + 32 + + + + + + + + + + + + + + + + + 33 + + + + + + + + + + + + + \ No newline at end of file diff --git a/packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change.svg b/packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change-key.svg similarity index 100% rename from packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change.svg rename to packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change-key.svg diff --git a/packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change-keys.svg b/packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change-keys.svg new file mode 100644 index 00000000000..1cc2a255633 --- /dev/null +++ b/packages/g6/__tests__/snapshots/behaviors/optimize-viewport-transform/viewport-change-keys.svg @@ -0,0 +1,1607 @@ + + + + + + + + + + + + + + + + + + 0-1 + + + + + + + + + + + + + + + + + 0-2 + + + + + + + + + + + + + + + + + 0-3 + + + + + + + + + + + + + + + + + 0-4 + + + + + + + + + + + + + + + + + 0-5 + + + + + + + + + + + + + + + + + 0-7 + + + + + + + + + + + + + + + + + 0-8 + + + + + + + + + + + + + + + + + 0-9 + + + + + + + + + + + + + + + + + 0-10 + + + + + + + + + + + + + + + + + 0-11 + + + + + + + + + + + + + + + + + 0-13 + + + + + + + + + + + + + + + + + 0-14 + + + + + + + + + + + + + + + + + 0-15 + + + + + + + + + + + + + + + + + 0-16 + + + + + + + + + + + + + + + + + 2-3 + + + + + + + + + + + + + + + + + 4-5 + + + + + + + + + + + + + + + + + 4-6 + + + + + + + + + + + + + + + + + 5-6 + + + + + + + + + + + + + + + + + 7-13 + + + + + + + + + + + + + + + + + 8-14 + + + + + + + + + + + + + + + + + 9-10 + + + + + + + + + + + + + + + + + 10-22 + + + + + + + + + + + + + + + + + 10-14 + + + + + + + + + + + + + + + + + 10-12 + + + + + + + + + + + + + + + + + 10-24 + + + + + + + + + + + + + + + + + 10-21 + + + + + + + + + + + + + + + + + 10-20 + + + + + + + + + + + + + + + + + 11-24 + + + + + + + + + + + + + + + + + 11-22 + + + + + + + + + + + + + + + + + 11-14 + + + + + + + + + + + + + + + + + 12-13 + + + + + + + + + + + + + + + + + 16-17 + + + + + + + + + + + + + + + + + 16-18 + + + + + + + + + + + + + + + + + 16-21 + + + + + + + + + + + + + + + + + 16-22 + + + + + + + + + + + + + + + + + 17-18 + + + + + + + + + + + + + + + + + 17-20 + + + + + + + + + + + + + + + + + 18-19 + + + + + + + + + + + + + + + + + 19-20 + + + + + + + + + + + + + + + + + 19-33 + + + + + + + + + + + + + + + + + 19-22 + + + + + + + + + + + + + + + + + 19-23 + + + + + + + + + + + + + + + + + 20-21 + + + + + + + + + + + + + + + + + 21-22 + + + + + + + + + + + + + + + + + 22-24 + + + + + + + + + + + + + + + + + 22-25 + + + + + + + + + + + + + + + + + 22-26 + + + + + + + + + + + + + + + + + 22-23 + + + + + + + + + + + + + + + + + 22-28 + + + + + + + + + + + + + + + + + 22-30 + + + + + + + + + + + + + + + + + 22-31 + + + + + + + + + + + + + + + + + 22-32 + + + + + + + + + + + + + + + + + 22-33 + + + + + + + + + + + + + + + + + 23-28 + + + + + + + + + + + + + + + + + 23-27 + + + + + + + + + + + + + + + + + 23-29 + + + + + + + + + + + + + + + + + 23-30 + + + + + + + + + + + + + + + + + 23-31 + + + + + + + + + + + + + + + + + 23-33 + + + + + + + + + + + + + + + + + 32-33 + + + + + + + + + + + + 0 + + + + + + + + + + + + + + + + + 1 + + + + + + + + + + + + + + + + + 2 + + + + + + + + + + + + + + + + + 3 + + + + + + + + + + + + + + + + + 4 + + + + + + + + + + + + + + + + + 5 + + + + + + + + + + + + + + + + + 6 + + + + + + + + + + + + + + + + + 7 + + + + + + + + + + + + + + + + + 8 + + + + + + + + + + + + + + + + + 9 + + + + + + + + + + + + + + + + + 10 + + + + + + + + + + + + + + + + + 11 + + + + + + + + + + + + + + + + + 12 + + + + + + + + + + + + + + + + + 13 + + + + + + + + + + + + + + + + + 14 + + + + + + + + + + + + + + + + + 15 + + + + + + + + + + + + + + + + + 16 + + + + + + + + + + + + + + + + + 17 + + + + + + + + + + + + + + + + + 18 + + + + + + + + + + + + + + + + + 19 + + + + + + + + + + + + + + + + + 20 + + + + + + + + + + + + + + + + + 21 + + + + + + + + + + + + + + + + + 22 + + + + + + + + + + + + + + + + + 23 + + + + + + + + + + + + + + + + + 24 + + + + + + + + + + + + + + + + + 25 + + + + + + + + + + + + + + + + + 26 + + + + + + + + + + + + + + + + + 27 + + + + + + + + + + + + + + + + + 28 + + + + + + + + + + + + + + + + + 29 + + + + + + + + + + + + + + + + + 30 + + + + + + + + + + + + + + + + + 31 + + + + + + + + + + + + + + + + + 32 + + + + + + + + + + + + + + + + + 33 + + + + + + + + + + + + + \ No newline at end of file diff --git a/packages/g6/__tests__/unit/behaviors/optimize-viewport-transform.spec.ts b/packages/g6/__tests__/unit/behaviors/optimize-viewport-transform.spec.ts index a7a29db6bf0..b145e8b0db9 100644 --- a/packages/g6/__tests__/unit/behaviors/optimize-viewport-transform.spec.ts +++ b/packages/g6/__tests__/unit/behaviors/optimize-viewport-transform.spec.ts @@ -1,6 +1,8 @@ -import { GraphEvent, type Graph } from '@/src'; +import type { ElementType, Graph } from '@/src'; +import { GraphEvent } from '@/src'; import { behaviorOptimizeViewportTransform } from '@@/demos'; import { createDemoGraph } from '@@/utils'; +import type { DisplayObject } from '@antv/g'; describe('behavior optimize canvas', () => { let graph: Graph; @@ -19,12 +21,61 @@ describe('behavior optimize canvas', () => { translate: [0, -3], }, }); - await expect(graph).toMatchSnapshot(__filename, 'viewport-change'); + await expect(graph).toMatchSnapshot(__filename, 'viewport-change-key'); graph.emit(GraphEvent.AFTER_TRANSFORM, { type: GraphEvent.AFTER_TRANSFORM, data: { mode: 'relative', - translate: [0, -1], + translate: [0, 3], + }, + }); + await expect(graph).toMatchSnapshot(__filename, 'after-viewport-change'); + }); + + it("show node's key and icon shapes", async () => { + graph.updateBehavior({ + key: 'optimize-viewport-transform', + shapes: (type: ElementType, shape: DisplayObject) => type === 'node' && ['key', 'text'].includes(shape.className), + }); + graph.emit(GraphEvent.BEFORE_TRANSFORM, { + type: GraphEvent.BEFORE_TRANSFORM, + data: { + mode: 'relative', + translate: [0, -3], + }, + }); + await expect(graph).toMatchSnapshot(__filename, 'viewport-change-key-text'); + graph.emit(GraphEvent.AFTER_TRANSFORM, { + type: GraphEvent.AFTER_TRANSFORM, + data: { + mode: 'relative', + translate: [0, 3], + }, + }); + await expect(graph).toMatchSnapshot(__filename, 'after-viewport-change'); + }); + + it("show node's key and edge's key", async () => { + graph.updateBehavior({ + key: 'optimize-viewport-transform', + shapes: { + node: ['key'], + edge: ['key'], + }, + }); + graph.emit(GraphEvent.BEFORE_TRANSFORM, { + type: GraphEvent.BEFORE_TRANSFORM, + data: { + mode: 'relative', + translate: [0, -3], + }, + }); + await expect(graph).toMatchSnapshot(__filename, 'viewport-change-keys'); + graph.emit(GraphEvent.AFTER_TRANSFORM, { + type: GraphEvent.AFTER_TRANSFORM, + data: { + mode: 'relative', + translate: [0, 3], }, }); await expect(graph).toMatchSnapshot(__filename, 'after-viewport-change'); diff --git a/packages/g6/src/behaviors/optimize-viewport-transform.ts b/packages/g6/src/behaviors/optimize-viewport-transform.ts index 8956579a447..4f9ea310ad5 100644 --- a/packages/g6/src/behaviors/optimize-viewport-transform.ts +++ b/packages/g6/src/behaviors/optimize-viewport-transform.ts @@ -2,6 +2,7 @@ import type { BaseStyleProps, DisplayObject } from '@antv/g'; import { debounce, isFunction } from '@antv/util'; import { GraphEvent } from '../constants'; import type { RuntimeContext } from '../runtime/types'; +import type { ElementType } from '../types'; import type { IViewportEvent } from '../types/event'; import { setVisibility } from '../utils/visibility'; import type { BaseBehaviorOptions } from './base-behavior'; @@ -21,16 +22,13 @@ export interface OptimizeViewportTransformOptions extends BaseBehaviorOptions { */ enable?: boolean | ((event: IViewportEvent) => boolean); /** - * 在画布操作过程中,元素会被隐藏以提高性能。通过设置 `shapes` 配置项,可以保留指定类名的子图形不被隐藏,从而保留整个元素的部分可见性 + * 指定始终显示的图形元素。应用此交互后,在画布操作过程中,只有通过该属性指定的图形元素会保持可见,其余图形元素将被隐藏,从而提升渲染性能。默认情况下,节点始终可见,而其他图形元素在操作画布过程中会自动隐藏 * - * During canvas operations, elements are hidden to improve performance. By configuring the `shapes` option, specific sub-elements with designated class names can be retained, thereby maintaining partial visibility of the entire element. - * @defaultValue { node: ['key'] } + * Specify the graphic elements that are always visible. After applying this interaction, only the graphic elements specified by this property will remain visible during the canvas operation, and the rest of the graphic elements will be hidden to improve rendering performance. By default, nodes are always visible, while other graphic elements are automatically hidden during canvas operations */ - shapes?: { - node?: string[]; - edge?: string[]; - combo?: string[]; - }; + shapes?: + | { node?: string[]; edge?: string[]; combo?: string[] } + | ((type: ElementType, shape: DisplayObject) => boolean); /** * 设置防抖时间 * @@ -49,9 +47,11 @@ export class OptimizeViewportTransform extends BaseBehavior = { enable: true, debounce: 200, - shapes: { node: ['key'] }, + shapes: (type: ElementType) => type === 'node', }; + private hiddenShapes: DisplayObject[] = []; + private isVisible: boolean = true; constructor(context: RuntimeContext, options: OptimizeViewportTransformOptions) { @@ -62,24 +62,36 @@ export class OptimizeViewportTransform extends BaseBehavior boolean, ) => { - elements.forEach((element) => { - setVisibility(element, visibility, false, (shape) => { - if (!shape.className) return true; - return !excludedClassnames?.includes(shape.className); - }); + elements.filter(Boolean).forEach((element) => { + if (visibility === 'hidden' && !element.isVisible()) { + this.hiddenShapes.push(element); + } else if (visibility === 'visible' && this.hiddenShapes.includes(element)) { + this.hiddenShapes.splice(this.hiddenShapes.indexOf(element), 1); + } else { + setVisibility(element, visibility, false, filter); + } }); }; + private filterShapes = (type: ElementType, filter: OptimizeViewportTransformOptions['shapes']) => { + if (isFunction(filter)) return (shape: DisplayObject) => !filter(type, shape); + const includesClassnames = filter?.[type]; + return (shape: DisplayObject) => { + if (!shape.className) return true; + return !includesClassnames?.includes(shape.className); + }; + }; + private hideShapes = (event: IViewportEvent) => { if (!this.validate(event) || !this.isVisible) return; const { element } = this.context; const { shapes = {} } = this.options; - this.setElementsVisibility(element!.getNodes(), 'hidden', shapes.node); - this.setElementsVisibility(element!.getEdges(), 'hidden', shapes.edge); - this.setElementsVisibility(element!.getCombos(), 'hidden', shapes.combo); + this.setElementsVisibility(element!.getNodes(), 'hidden', this.filterShapes('node', shapes)); + this.setElementsVisibility(element!.getEdges(), 'hidden', this.filterShapes('edge', shapes)); + this.setElementsVisibility(element!.getCombos(), 'hidden', this.filterShapes('combo', shapes)); this.isVisible = false; }; @@ -115,6 +127,12 @@ export class OptimizeViewportTransform extends BaseBehavior) { + this.unbindEvents(); + super.update(options); + this.bindEvents(); + } + public destroy() { this.unbindEvents(); super.destroy();