From 634d5960f46fa359251e22a939da7bbab1387b16 Mon Sep 17 00:00:00 2001 From: Yuxin <55794321+yvonneyx@users.noreply.github.com> Date: Mon, 26 Feb 2024 15:45:59 +0800 Subject: [PATCH] feat: add light and dark theme; node supports new `badgePalette` attribute (#5467) * feat(node): support new badgePalette attribute * feat: add light theme and dark theme;update demo and test panel * refactor(site): update site demos * refactor: rename disable to disabled * refactor: rename disable to disabled --------- Co-authored-by: Aaron --- .../demo/animation/controller-element.ts | 6 +- .../g6/__tests__/demo/static/edge-line.ts | 65 +- .../g6/__tests__/demo/static/node-circle.ts | 42 +- .../g6/__tests__/demo/static/node-ellipse.ts | 40 +- .../g6/__tests__/demo/static/node-image.ts | 35 +- .../g6/__tests__/demo/static/node-rect.ts | 42 +- .../g6/__tests__/demo/static/node-star.ts | 37 +- .../g6/__tests__/demo/static/node-triangle.ts | 36 +- packages/g6/__tests__/demo/types.ts | 6 + packages/g6/__tests__/index.html | 11 +- .../__tests__/integration/animation.spec.ts | 2 +- .../controller-element-1000(3_3).svg | 40 +- .../animation/controller-element-200(2_3).svg | 83 +- .../animation/controller-element-50(1_3).svg | 83 +- .../controller-element-position-0(1_3).svg | 183 ++- .../controller-element-position-1000(3_3).svg | 183 ++- .../controller-element-position-200(2_3).svg | 183 ++- .../controller-element-state-0(1_2).svg | 111 +- .../controller-element-state-1000(2_2).svg | 113 +- .../static/controller-element-position.svg | 183 ++- .../static/controller-element-visibility.svg | 69 +- .../controller-element-visibility__hidden.svg | 69 +- .../static/controller-element-z-index.svg | 9 +- .../controller-element-z-index__back.svg | 9 +- .../controller-element-z-index__front.svg | 9 +- .../snapshots/static/controller-element.svg | 66 +- .../static/controller-layout-circular.svg | 1248 +++++++++++++++-- .../static/controller-layout-compact-box.svg | 851 ++++++++--- .../static/controller-layout-d3-force.svg | 1248 +++++++++++++++-- .../static/controller-layout-dagre.svg | 254 +++- .../static/controller-layout-dendrogram.svg | 851 ++++++++--- .../static/controller-layout-grid.svg | 1248 +++++++++++++++-- .../static/controller-layout-indented.svg | 401 +++++- .../static/controller-layout-mindmap.svg | 665 +++++++-- .../static/controller-layout-radial.svg | 1156 +++++++++++++-- .../snapshots/static/edge-line.svg | 420 ++++-- .../snapshots/static/graph-element.svg | 1190 ++++++++++++++-- .../snapshots/static/node-circle.svg | 370 +++-- .../snapshots/static/node-ellipse.svg | 355 +++-- .../snapshots/static/node-image.svg | 241 ++-- .../snapshots/static/node-rect.svg | 348 +++-- .../snapshots/static/node-star.svg | 271 ++-- .../snapshots/static/node-triangle.svg | 222 +-- .../g6/__tests__/integration/static.spec.ts | 1 + packages/g6/__tests__/main.ts | 21 +- .../g6/__tests__/unit/utils/palette.spec.ts | 7 +- packages/g6/src/elements/nodes/base-node.ts | 18 +- packages/g6/src/themes/dark.ts | 167 ++- packages/g6/src/themes/light.ts | 163 ++- packages/g6/src/utils/palette.ts | 14 + .../examples/item/defaultNodes/demo/circle.ts | 40 +- .../item/defaultNodes/demo/ellipse.ts | 38 +- .../item/defaultNodes/demo/radiusRect.ts | 39 +- .../examples/item/defaultNodes/demo/rect.ts | 39 +- .../examples/item/defaultNodes/demo/star.ts | 35 +- .../item/defaultNodes/demo/triangle.ts | 35 +- 56 files changed, 11099 insertions(+), 2572 deletions(-) diff --git a/packages/g6/__tests__/demo/animation/controller-element.ts b/packages/g6/__tests__/demo/animation/controller-element.ts index 05f8f4be850..38358efe40f 100644 --- a/packages/g6/__tests__/demo/animation/controller-element.ts +++ b/packages/g6/__tests__/demo/animation/controller-element.ts @@ -36,9 +36,9 @@ export const controllerElement: AnimationTestCase = async (context) => { await graph.draw(); graph.addNodeData([ - { id: 'node-4', style: { x: 50, y: 200, stroke: 'orange' } }, - { id: 'node-5', style: { x: 75, y: 150, stroke: 'purple' } }, - { id: 'node-6', style: { x: 200, y: 100, stroke: 'cyan' } }, + { id: 'node-4', style: { x: 50, y: 200, fill: 'orange' } }, + { id: 'node-5', style: { x: 75, y: 150, fill: 'purple' } }, + { id: 'node-6', style: { x: 200, y: 100, fill: 'cyan' } }, ]); graph.removeNodeData(['node-1']); diff --git a/packages/g6/__tests__/demo/static/edge-line.ts b/packages/g6/__tests__/demo/static/edge-line.ts index 148deebb754..2e57bc62675 100644 --- a/packages/g6/__tests__/demo/static/edge-line.ts +++ b/packages/g6/__tests__/demo/static/edge-line.ts @@ -2,78 +2,34 @@ import { Graph } from '@/src'; import type { StaticTestCase } from '../types'; export const edgeLine: StaticTestCase = async (context) => { - const { canvas, animation } = context; + const { canvas, animation, theme } = context; + + const edgeIds = ['line-default', 'line-active', 'line-selected', 'line-highlight', 'line-inactive', 'line-disabled']; const data = { - nodes: [{ id: 'node1' }, { id: 'node2' }, { id: 'node3' }, { id: 'node4' }, { id: 'node5' }, { id: 'node6' }], - edges: [ - { - id: 'line-default', - source: 'node1', - target: 'node2', - }, - { - id: 'line-active', - source: 'node1', - target: 'node3', - }, - { - id: 'line-selected', - source: 'node1', - target: 'node4', - }, - { - id: 'line-highlight', - source: 'node1', - target: 'node5', - }, - { - id: 'line-inactive', - source: 'node1', - target: 'node6', - }, - ], + nodes: new Array(7).fill(0).map((_, i) => ({ id: `node${i + 1}` })), + edges: edgeIds.map((id, i) => ({ + id, + source: 'node1', + target: `node${i + 2}`, + })), }; const graph = new Graph({ container: canvas, + theme, data, node: { style: { type: 'circle', // πŸ‘ˆπŸ» Node shape type. - size: 40, - color: '#1783FF', }, }, edge: { style: { type: 'line', // πŸ‘ˆπŸ» Edge shape type. - color: 'rgb(153, 173, 209)', labelText: (d: any) => d.id, - labelBackgroundPadding: 0, - labelBackgroundFill: '#fff', - labelBackgroundLineWidth: 0, - labelBackgroundOpacity: 0.75, endArrow: true, }, - state: { - active: { - halo: true, - }, - selected: { - lineWidth: 2, - labelFontWeight: 700, - halo: true, - }, - highlight: { - halo: false, - lineWidth: 2, - labelFontWeight: 700, - }, - inactive: { - color: 'rgb(210, 218, 233)', - }, - }, }, layout: { type: 'radial', @@ -89,4 +45,5 @@ export const edgeLine: StaticTestCase = async (context) => { graph.setElementState('line-selected', 'selected'); graph.setElementState('line-highlight', 'highlight'); graph.setElementState('line-inactive', 'inactive'); + graph.setElementState('line-disabled', 'disabled'); }; diff --git a/packages/g6/__tests__/demo/static/node-circle.ts b/packages/g6/__tests__/demo/static/node-circle.ts index 92220106460..270cc06955f 100644 --- a/packages/g6/__tests__/demo/static/node-circle.ts +++ b/packages/g6/__tests__/demo/static/node-circle.ts @@ -2,7 +2,7 @@ import { Graph } from '@/src'; import type { StaticTestCase } from '../types'; export const nodeCircle: StaticTestCase = async (context) => { - const { canvas } = context; + const { canvas, animation, theme } = context; const data = { nodes: [ @@ -14,65 +14,44 @@ export const nodeCircle: StaticTestCase = async (context) => { { id: 'circle-selected' }, { id: 'circle-highlight' }, { id: 'circle-inactive' }, + { id: 'circle-disabled' }, ], }; const graph = new Graph({ container: canvas, data, + theme, node: { style: { type: 'circle', // πŸ‘ˆπŸ» Node shape type. size: 40, - fill: '#1783FF', + labelMaxWidth: 120, labelText: (d: any) => d.id, + iconHeight: 20, + iconWidth: 20, iconSrc: 'https://gw.alipayobjects.com/zos/basement_prod/012bcf4f-423b-4922-8c24-32a89f8c41ce.svg', - iconWidth: 30, - iconHeight: 30, halo: (d: any) => d.id.includes('halo'), ports: (d: any) => d.id.includes('ports') ? [{ position: 'left' }, { position: 'right' }, { position: 'top' }, { position: 'bottom' }] : [], - portStroke: '#31d0c6', - portFill: '#fff', - portR: 2, - portLineWidth: 1, badges: (d: any) => d.id.includes('badges') ? [ - { text: 'A', position: 'right-top', backgroundFill: '#8291b2' }, - { text: 'Important', position: 'right', backgroundFill: '#e66c5b' }, - { text: 'Notice', position: 'right-bottom', backgroundFill: '#e5b95e' }, + { text: 'A', position: 'right-top' }, + { text: 'Important', position: 'right' }, + { text: 'Notice', position: 'right-bottom' }, ] : [], - badgeFill: '#fff', badgeFontSize: 8, badgePadding: [1, 4], }, - state: { - active: { - halo: true, - }, - selected: { - halo: true, - lineWidth: 2, - stroke: '#000', - }, - highlight: { - halo: false, - lineWidth: 2, - stroke: '#000', - }, - inactive: { - opacity: 0.2, - }, - }, }, layout: { type: 'grid', }, - animation: false, + animation, }); await graph.render(); @@ -81,4 +60,5 @@ export const nodeCircle: StaticTestCase = async (context) => { graph.setElementState('circle-selected', 'selected'); graph.setElementState('circle-highlight', 'highlight'); graph.setElementState('circle-inactive', 'inactive'); + graph.setElementState('circle-disabled', 'disabled'); }; diff --git a/packages/g6/__tests__/demo/static/node-ellipse.ts b/packages/g6/__tests__/demo/static/node-ellipse.ts index 64394393104..34d8d55255e 100644 --- a/packages/g6/__tests__/demo/static/node-ellipse.ts +++ b/packages/g6/__tests__/demo/static/node-ellipse.ts @@ -2,7 +2,7 @@ import { Graph } from '@/src'; import type { StaticTestCase } from '../types'; export const nodeEllipse: StaticTestCase = async (context) => { - const { canvas } = context; + const { canvas, animation, theme } = context; const data = { nodes: [ @@ -14,63 +14,44 @@ export const nodeEllipse: StaticTestCase = async (context) => { { id: 'ellipse-selected' }, { id: 'ellipse-highlight' }, { id: 'ellipse-inactive' }, + { id: 'ellipse-disabled' }, ], }; const graph = new Graph({ container: canvas, + theme, data, node: { style: { type: 'ellipse', // πŸ‘ˆπŸ» Node shape type. size: [45, 35], - fill: '#1783FF', + labelMaxWidth: 120, labelText: (d: any) => d.id, + iconHeight: 20, + iconWidth: 20, iconSrc: 'https://gw.alipayobjects.com/zos/basement_prod/012bcf4f-423b-4922-8c24-32a89f8c41ce.svg', halo: (d: any) => d.id.includes('halo'), ports: (d: any) => d.id.includes('ports') ? [{ position: 'left' }, { position: 'right' }, { position: 'top' }, { position: 'bottom' }] : [], - portStroke: '#31d0c6', - portFill: '#fff', - portR: 2, - portLineWidth: 1, badges: (d: any) => d.id.includes('badges') ? [ - { text: 'A', position: 'right-top', backgroundFill: '#8291b2' }, - { text: 'Important', position: 'right', backgroundFill: '#e66c5b' }, - { text: 'Notice', position: 'right-bottom', backgroundFill: '#e5b95e' }, + { text: 'A', position: 'right-top' }, + { text: 'Important', position: 'right' }, + { text: 'Notice', position: 'right-bottom' }, ] : [], - badgeFill: '#fff', badgeFontSize: 8, badgePadding: [1, 4], }, - state: { - active: { - halo: true, - }, - selected: { - halo: true, - lineWidth: 2, - stroke: '#000', - }, - highlight: { - halo: false, - lineWidth: 2, - stroke: '#000', - }, - inactive: { - opacity: 0.2, - }, - }, }, layout: { type: 'grid', }, - animation: false, + animation, }); await graph.render(); @@ -79,4 +60,5 @@ export const nodeEllipse: StaticTestCase = async (context) => { graph.setElementState('ellipse-selected', 'selected'); graph.setElementState('ellipse-highlight', 'highlight'); graph.setElementState('ellipse-inactive', 'inactive'); + graph.setElementState('ellipse-disabled', 'disabled'); }; diff --git a/packages/g6/__tests__/demo/static/node-image.ts b/packages/g6/__tests__/demo/static/node-image.ts index c60629425f8..06d613fc4a4 100644 --- a/packages/g6/__tests__/demo/static/node-image.ts +++ b/packages/g6/__tests__/demo/static/node-image.ts @@ -2,7 +2,7 @@ import { Graph } from '@/src'; import type { StaticTestCase } from '../types'; export const nodeImage: StaticTestCase = async (context) => { - const { canvas } = context; + const { canvas, animation, theme } = context; const data = { nodes: [ @@ -14,54 +14,40 @@ export const nodeImage: StaticTestCase = async (context) => { { id: 'image-selected' }, { id: 'image-highlight' }, { id: 'image-inactive' }, + { id: 'image-disabled' }, ], }; const graph = new Graph({ container: canvas, + theme, data, node: { style: { type: 'image', // πŸ‘ˆπŸ» Node shape type. size: 40, + labelMaxWidth: 120, labelText: (d: any) => d.id, src: 'https://gw.alipayobjects.com/mdn/rms_6ae20b/afts/img/A*N4ZMS7gHsUIAAAAAAAAAAABkARQnAQ', halo: (d: any) => d.id.includes('halo'), - haloStroke: '#1783FF', + haloStroke: '#227eff', ports: (d: any) => d.id.includes('ports') ? [{ position: 'left' }, { position: 'right' }, { position: 'top' }, { position: 'bottom' }] : [], - portStroke: '#31d0c6', - portFill: '#fff', - portR: 2, - portLineWidth: 1, badges: (d: any) => d.id.includes('badges') ? [ - { text: 'A', position: 'right-top', backgroundFill: '#8291b2' }, - { text: 'Important', position: 'right', backgroundFill: '#e66c5b' }, - { text: 'Notice', position: 'right-bottom', backgroundFill: '#e5b95e' }, + { text: 'A', position: 'right-top' }, + { text: 'Important', position: 'right' }, + { text: 'Notice', position: 'right-bottom' }, ] : [], - badgeFill: '#fff', badgeFontSize: 8, badgePadding: [1, 4], }, state: { - active: { - halo: true, - }, - selected: { - halo: true, - labelFontWeight: 700, - labelFontSize: 14, - }, - highlight: { - halo: false, - labelFontWeight: 700, - }, - inactive: { + disabled: { opacity: 0.2, }, }, @@ -69,7 +55,7 @@ export const nodeImage: StaticTestCase = async (context) => { layout: { type: 'grid', }, - animation: false, + animation, }); await graph.render(); @@ -77,4 +63,5 @@ export const nodeImage: StaticTestCase = async (context) => { graph.setElementState('image-selected', 'selected'); graph.setElementState('image-highlight', 'highlight'); graph.setElementState('image-inactive', 'inactive'); + graph.setElementState('image-disabled', 'disabled'); }; diff --git a/packages/g6/__tests__/demo/static/node-rect.ts b/packages/g6/__tests__/demo/static/node-rect.ts index add1df855a8..9e5c16082ec 100644 --- a/packages/g6/__tests__/demo/static/node-rect.ts +++ b/packages/g6/__tests__/demo/static/node-rect.ts @@ -2,7 +2,7 @@ import { Graph } from '@/src'; import type { StaticTestCase } from '../types'; export const nodeRect: StaticTestCase = async (context) => { - const { canvas } = context; + const { canvas, animation, theme } = context; const data = { nodes: [ @@ -14,66 +14,45 @@ export const nodeRect: StaticTestCase = async (context) => { { id: 'rect-selected' }, { id: 'rect-highlight' }, { id: 'rect-inactive' }, + { id: 'rect-disabled' }, ], }; const graph = new Graph({ container: canvas, + theme, data, node: { style: { type: 'rect', // πŸ‘ˆπŸ» Node shape type. radius: 4, // πŸ‘ˆπŸ» Set the radius. size: 40, - fill: '#1783FF', + labelMaxWidth: 120, labelText: (d: any) => d.id, + iconWidth: 20, + iconHeight: 20, iconSrc: 'https://gw.alipayobjects.com/zos/basement_prod/012bcf4f-423b-4922-8c24-32a89f8c41ce.svg', - iconWidth: 30, - iconHeight: 30, halo: (d: any) => d.id.includes('halo'), ports: (d: any) => d.id.includes('ports') ? [{ position: 'left' }, { position: 'right' }, { position: 'top' }, { position: 'bottom' }] : [], - portStroke: '#31d0c6', - portFill: '#fff', - portR: 2, - portLineWidth: 1, badges: (d: any) => d.id.includes('badges') ? [ - { text: 'A', position: 'right-top', backgroundFill: '#8291b2' }, - { text: 'Important', position: 'right', backgroundFill: '#e66c5b' }, - { text: 'Notice', position: 'right-bottom', backgroundFill: '#e5b95e' }, + { text: 'A', position: 'right-top' }, + { text: 'Important', position: 'right' }, + { text: 'Notice', position: 'right-bottom' }, ] : [], - badgeFill: '#fff', badgeFontSize: 8, badgePadding: [1, 4], }, - state: { - active: { - halo: true, - }, - selected: { - halo: true, - lineWidth: 2, - stroke: '#000', - }, - highlight: { - halo: false, - lineWidth: 2, - stroke: '#000', - }, - inactive: { - opacity: 0.2, - }, - }, }, layout: { type: 'grid', }, - animation: false, + animation, }); await graph.render(); @@ -82,4 +61,5 @@ export const nodeRect: StaticTestCase = async (context) => { graph.setElementState('rect-selected', 'selected'); graph.setElementState('rect-highlight', 'highlight'); graph.setElementState('rect-inactive', 'inactive'); + graph.setElementState('rect-disabled', 'disabled'); }; diff --git a/packages/g6/__tests__/demo/static/node-star.ts b/packages/g6/__tests__/demo/static/node-star.ts index 63d4788a520..82979f38f1a 100644 --- a/packages/g6/__tests__/demo/static/node-star.ts +++ b/packages/g6/__tests__/demo/static/node-star.ts @@ -2,7 +2,7 @@ import { Graph } from '@/src'; import type { StaticTestCase } from '../types'; export const nodeStar: StaticTestCase = async (context) => { - const { canvas } = context; + const { canvas, animation, theme } = context; const data = { nodes: [ @@ -14,17 +14,19 @@ export const nodeStar: StaticTestCase = async (context) => { { id: 'star-selected' }, { id: 'star-highlight' }, { id: 'star-inactive' }, + { id: 'star-disabled' }, ], }; const graph = new Graph({ container: canvas, + theme, data, node: { style: { type: 'star', // πŸ‘ˆπŸ» Node shape type. size: 40, - fill: '#1783FF', + labelMaxWidth: 120, labelText: (d: any) => d.id, iconSrc: 'https://gw.alipayobjects.com/zos/basement_prod/012bcf4f-423b-4922-8c24-32a89f8c41ce.svg', halo: (d: any) => d.id.includes('halo'), @@ -32,44 +34,22 @@ export const nodeStar: StaticTestCase = async (context) => { d.id.includes('ports') ? [{ position: 'left' }, { position: 'right' }, { position: 'top' }, { position: 'bottom' }] : [], - portStroke: '#31d0c6', - portFill: '#fff', - portR: 2, - portLineWidth: 1, badges: (d: any) => d.id.includes('badges') ? [ - { text: 'A', position: 'right-top', backgroundFill: '#8291b2' }, - { text: 'Important', position: 'right', backgroundFill: '#e66c5b' }, - { text: 'Notice', position: 'right-bottom', backgroundFill: '#e5b95e' }, + { text: 'A', position: 'right-top' }, + { text: 'Important', position: 'right' }, + { text: 'Notice', position: 'right-bottom' }, ] : [], - badgeFill: '#fff', badgeFontSize: 8, badgePadding: [1, 4], }, - state: { - active: { - halo: true, - }, - selected: { - halo: true, - lineWidth: 2, - stroke: '#000', - }, - highlight: { - halo: false, - lineWidth: 2, - stroke: '#000', - }, - inactive: { - opacity: 0.2, - }, - }, }, layout: { type: 'grid', }, + animation, }); await graph.render(); @@ -78,4 +58,5 @@ export const nodeStar: StaticTestCase = async (context) => { graph.setElementState('star-selected', 'selected'); graph.setElementState('star-highlight', 'highlight'); graph.setElementState('star-inactive', 'inactive'); + graph.setElementState('star-disabled', 'disabled'); }; diff --git a/packages/g6/__tests__/demo/static/node-triangle.ts b/packages/g6/__tests__/demo/static/node-triangle.ts index 6bab6b8edac..0f63e4421b5 100644 --- a/packages/g6/__tests__/demo/static/node-triangle.ts +++ b/packages/g6/__tests__/demo/static/node-triangle.ts @@ -2,7 +2,7 @@ import { Graph } from '@/src'; import type { StaticTestCase } from '../types'; export const nodeTriangle: StaticTestCase = async (context) => { - const { canvas } = context; + const { canvas, animation, theme } = context; const data = { nodes: [ @@ -19,57 +19,35 @@ export const nodeTriangle: StaticTestCase = async (context) => { const graph = new Graph({ container: canvas, + theme, data, node: { style: { type: 'triangle', // πŸ‘ˆπŸ» Node shape type. size: 40, direction: (d: any) => d.data?.direction, - fill: '#1783FF', + labelMaxWidth: 120, labelText: (d: any) => d.id, iconSrc: 'https://gw.alipayobjects.com/zos/basement_prod/012bcf4f-423b-4922-8c24-32a89f8c41ce.svg', halo: (d: any) => d.id.includes('halo'), ports: (d: any) => d.id.includes('ports') ? [{ position: 'left' }, { position: 'top' }, { position: 'bottom' }] : [], - portStroke: '#31d0c6', - portFill: '#fff', - portR: 2, - portLineWidth: 1, badges: (d: any) => d.id.includes('badges') ? [ - { text: 'A', position: 'right-top', backgroundFill: '#8291b2' }, - { text: 'Important', position: 'right', backgroundFill: '#e66c5b' }, - { text: 'Notice', position: 'right-bottom', backgroundFill: '#e5b95e' }, + { text: 'A', position: 'right-top' }, + { text: 'Important', position: 'right' }, + { text: 'Notice', position: 'right-bottom' }, ] : [], - badgeFill: '#fff', badgeFontSize: 8, badgePadding: [1, 4], }, - state: { - active: { - halo: true, - }, - selected: { - halo: true, - lineWidth: 2, - stroke: '#000', - }, - highlight: { - halo: false, - lineWidth: 2, - stroke: '#000', - }, - inactive: { - opacity: 0.2, - }, - }, }, layout: { type: 'grid', }, - animation: false, + animation, }); await graph.render(); diff --git a/packages/g6/__tests__/demo/types.ts b/packages/g6/__tests__/demo/types.ts index 6fadf75842d..8348e03bf2c 100644 --- a/packages/g6/__tests__/demo/types.ts +++ b/packages/g6/__tests__/demo/types.ts @@ -22,6 +22,12 @@ type TestCaseContext = { * Test case environment */ env: 'test' | 'dev'; + /** + * ζ΅‹θ―•η”¨δΎ‹δΈ»ι’˜ + * + * Test case theme + */ + theme: string; }; export type TestCase = StaticTestCase | AnimationTestCase; diff --git a/packages/g6/__tests__/index.html b/packages/g6/__tests__/index.html index 82184f6f5fd..45b0aef76c1 100644 --- a/packages/g6/__tests__/index.html +++ b/packages/g6/__tests__/index.html @@ -84,7 +84,7 @@ - +
@@ -95,15 +95,6 @@