mirror of
https://github.com/wanglin2/mind-map.git
synced 2026-02-21 18:37:43 +08:00
Feat:1.优化节点样式设置,如果设置的是连线样式不触发节点重新创建;2.优化富文本模式下同时对大量节点调用setStyle方法修改文本样式非常慢的问题
This commit is contained in:
parent
7258ed9ea7
commit
508d8fe357
@ -336,7 +336,7 @@ class MindMap {
|
||||
this.opt.themeConfig = config
|
||||
if (!notRender) {
|
||||
// 检查改变的是否是节点大小无关的主题属性
|
||||
let res = checkIsNodeSizeIndependenceConfig(changedConfig)
|
||||
const res = checkIsNodeSizeIndependenceConfig(changedConfig)
|
||||
this.render(null, res ? '' : CONSTANTS.CHANGE_THEME)
|
||||
}
|
||||
}
|
||||
|
||||
@ -34,7 +34,8 @@ import {
|
||||
formatGetNodeGeneralization,
|
||||
sortNodeList,
|
||||
throttle,
|
||||
checkClipboardReadEnable
|
||||
checkClipboardReadEnable,
|
||||
isNodeNotNeedRenderData
|
||||
} from '../../utils'
|
||||
import { shapeList } from './node/Shape'
|
||||
import { lineStyleProps } from '../../theme/default'
|
||||
@ -1580,14 +1581,15 @@ class Render {
|
||||
|
||||
// 设置节点样式
|
||||
setNodeStyle(node, prop, value) {
|
||||
let data = {
|
||||
const data = {
|
||||
[prop]: value
|
||||
}
|
||||
// 如果开启了富文本,则需要应用到富文本上
|
||||
if (this.hasRichTextPlugin()) {
|
||||
this.mindMap.richText.setNotActiveNodeStyle(node, {
|
||||
[prop]: value
|
||||
})
|
||||
if (
|
||||
this.hasRichTextPlugin() &&
|
||||
this.mindMap.richText.isHasRichTextStyle(data)
|
||||
) {
|
||||
data.resetRichText = true
|
||||
}
|
||||
this.setNodeDataRender(node, data)
|
||||
// 更新了连线的样式
|
||||
@ -1598,10 +1600,13 @@ class Render {
|
||||
|
||||
// 设置节点多个样式
|
||||
setNodeStyles(node, style) {
|
||||
let data = { ...style }
|
||||
const data = { ...style }
|
||||
// 如果开启了富文本,则需要应用到富文本上
|
||||
if (this.hasRichTextPlugin()) {
|
||||
this.mindMap.richText.setNotActiveNodeStyle(node, style)
|
||||
if (
|
||||
this.hasRichTextPlugin() &&
|
||||
this.mindMap.richText.isHasRichTextStyle(data)
|
||||
) {
|
||||
data.resetRichText = true
|
||||
}
|
||||
this.setNodeDataRender(node, data)
|
||||
// 更新了连线的样式
|
||||
@ -1964,6 +1969,10 @@ class Render {
|
||||
// 设置节点数据,并判断是否渲染
|
||||
setNodeDataRender(node, data, notRender = false) {
|
||||
this.mindMap.execCommand('SET_NODE_DATA', node, data)
|
||||
if (isNodeNotNeedRenderData(data)) {
|
||||
this.mindMap.emit('node_tree_render_end')
|
||||
return
|
||||
}
|
||||
this.reRenderNodeCheckChange(node, notRender)
|
||||
}
|
||||
|
||||
|
||||
@ -57,6 +57,14 @@ class RichText {
|
||||
this.isCompositing = false
|
||||
this.textNodePaddingX = 6
|
||||
this.textNodePaddingY = 4
|
||||
this.supportStyleProps = [
|
||||
'fontFamily',
|
||||
'fontSize',
|
||||
'fontWeight',
|
||||
'fontStyle',
|
||||
'textDecoration',
|
||||
'color'
|
||||
]
|
||||
this.initOpt()
|
||||
this.extendQuill()
|
||||
this.appendCss()
|
||||
@ -675,14 +683,7 @@ class RichText {
|
||||
// 再将样式恢复为当前主题改节点的默认样式
|
||||
const style = {}
|
||||
if (this.node) {
|
||||
;[
|
||||
'fontFamily',
|
||||
'fontSize',
|
||||
'fontWeight',
|
||||
'fontStyle',
|
||||
'textDecoration',
|
||||
'color'
|
||||
].forEach(key => {
|
||||
this.supportStyleProps.forEach(key => {
|
||||
style[key] = this.node.style.merge(key)
|
||||
})
|
||||
}
|
||||
@ -713,14 +714,7 @@ class RichText {
|
||||
if (!this.node) return
|
||||
if (clear) {
|
||||
// 清除文本样式
|
||||
;[
|
||||
'fontFamily',
|
||||
'fontSize',
|
||||
'fontWeight',
|
||||
'fontStyle',
|
||||
'textDecoration',
|
||||
'color'
|
||||
].forEach(prop => {
|
||||
this.supportStyleProps.forEach(prop => {
|
||||
delete this.node.nodeData.data[prop]
|
||||
})
|
||||
} else {
|
||||
@ -795,6 +789,18 @@ class RichText {
|
||||
return data
|
||||
}
|
||||
|
||||
// 判断一个对象是否包含了富文本支持的样式字段
|
||||
isHasRichTextStyle(obj) {
|
||||
const keys = Object.keys(obj)
|
||||
for (let i = 0; i < keys.length; i++) {
|
||||
const key = keys[i]
|
||||
if (this.supportStyleProps.includes(key)) {
|
||||
return true
|
||||
}
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
// 给未激活的节点设置富文本样式
|
||||
setNotActiveNodeStyle(node, style) {
|
||||
const config = this.normalStyleToRichTextStyle(style)
|
||||
@ -807,17 +813,9 @@ class RichText {
|
||||
|
||||
// 检查指定节点是否存在自定义的富文本样式
|
||||
checkNodeHasCustomRichTextStyle(node) {
|
||||
const list = [
|
||||
'fontFamily',
|
||||
'fontSize',
|
||||
'fontWeight',
|
||||
'fontStyle',
|
||||
'textDecoration',
|
||||
'color'
|
||||
]
|
||||
const nodeData = node instanceof MindMapNode ? node.getData() : node
|
||||
for (let i = 0; i < list.length; i++) {
|
||||
if (nodeData[list[i]] !== undefined) {
|
||||
for (let i = 0; i < this.supportStyleProps.length; i++) {
|
||||
if (nodeData[this.supportStyleProps[i]] !== undefined) {
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
@ -15,6 +15,12 @@ export default {
|
||||
lineColor: '#549688',
|
||||
// 连线样式
|
||||
lineDasharray: 'none',
|
||||
// 连线是否开启流动效果,仅在虚线时有效(需要注册LineFlow插件)
|
||||
lineFlow: false,
|
||||
// 流动效果一个周期的时间,单位:s
|
||||
lineFlowDuration: 1,
|
||||
// 流动方向是否是从父节点到子节点
|
||||
lineFlowForward: true,
|
||||
// 连线风格
|
||||
lineStyle: 'straight', // 曲线(curve)【仅支持logicalStructure、mindMap、verticalTimeline三种结构】、直线(straight)、直连(direct)【仅支持logicalStructure、mindMap、organizationStructure、verticalTimeline四种结构】
|
||||
// 曲线连接时,根节点和其他节点的连接线样式保持统一,默认根节点为 ( 型,其他节点为 { 型,设为true后,都为 { 型。仅支持logicalStructure、mindMap两种结构
|
||||
@ -88,8 +94,15 @@ export default {
|
||||
hoverRectColor: '',
|
||||
// 点鼠标hover和激活时显示的矩形边框的圆角大小
|
||||
hoverRectRadius: 5
|
||||
// paddingX: 15,
|
||||
// paddingY: 5
|
||||
// 下列样式也支持给节点设置,用于覆盖最外层的设置
|
||||
// paddingX,
|
||||
// paddingY,
|
||||
// lineWidth,
|
||||
// lineColor,
|
||||
// lineDasharray,
|
||||
// lineFlow,
|
||||
// lineFlowDuration,
|
||||
// lineFlowForward
|
||||
},
|
||||
// 二级节点样式
|
||||
second: {
|
||||
@ -115,8 +128,6 @@ export default {
|
||||
lineMarkerDir: 'end',
|
||||
hoverRectColor: '',
|
||||
hoverRectRadius: 5
|
||||
// paddingX: 15,
|
||||
// paddingY: 5
|
||||
},
|
||||
// 三级及以下节点样式
|
||||
node: {
|
||||
@ -142,8 +153,6 @@ export default {
|
||||
lineMarkerDir: 'end',
|
||||
hoverRectColor: '',
|
||||
hoverRectRadius: 5
|
||||
// paddingX: 15,
|
||||
// paddingY: 5
|
||||
},
|
||||
// 概要节点样式
|
||||
generalization: {
|
||||
@ -168,8 +177,6 @@ export default {
|
||||
endDir: [1, 0],
|
||||
hoverRectColor: '',
|
||||
hoverRectRadius: 5
|
||||
// paddingX: 15,
|
||||
// paddingY: 5
|
||||
}
|
||||
}
|
||||
|
||||
@ -197,14 +204,12 @@ const nodeSizeIndependenceList = [
|
||||
'rootLineKeepSameInCurve',
|
||||
'rootLineStartPositionKeepSameInCurve',
|
||||
'showLineMarker',
|
||||
'gradientStyle',
|
||||
'lineRadius',
|
||||
'startColor',
|
||||
'endColor',
|
||||
'startDir',
|
||||
'endDir',
|
||||
'hoverRectColor',
|
||||
'hoverRectRadius'
|
||||
'hoverRectRadius',
|
||||
'lineFlow',
|
||||
'lineFlowDuration',
|
||||
'lineFlowForward'
|
||||
]
|
||||
export const checkIsNodeSizeIndependenceConfig = config => {
|
||||
let keys = Object.keys(config)
|
||||
@ -220,9 +225,13 @@ export const checkIsNodeSizeIndependenceConfig = config => {
|
||||
return true
|
||||
}
|
||||
|
||||
// 连线的样式
|
||||
export const lineStyleProps = [
|
||||
'lineColor',
|
||||
'lineDasharray',
|
||||
'lineWidth',
|
||||
'lineMarkerDir'
|
||||
'lineMarkerDir',
|
||||
'lineFlow',
|
||||
'lineFlowDuration',
|
||||
'lineFlowForward'
|
||||
]
|
||||
|
||||
@ -6,6 +6,7 @@ import {
|
||||
import MersenneTwister from './mersenneTwister'
|
||||
import { ForeignObject } from '@svgdotjs/svg.js'
|
||||
import merge from 'deepmerge'
|
||||
import { lineStyleProps } from '../theme/default'
|
||||
|
||||
// 深度优先遍历树
|
||||
export const walk = (
|
||||
@ -507,13 +508,14 @@ export const addHtmlStyle = (html, tag, style) => {
|
||||
if (!addHtmlStyleEl) {
|
||||
addHtmlStyleEl = document.createElement('div')
|
||||
}
|
||||
const tags = Array.isArray(tag) ? tag : [tag]
|
||||
addHtmlStyleEl.innerHTML = html
|
||||
let walk = root => {
|
||||
let childNodes = root.childNodes
|
||||
childNodes.forEach(node => {
|
||||
if (node.nodeType === 1) {
|
||||
// 元素节点
|
||||
if (node.tagName.toLowerCase() === tag) {
|
||||
if (tags.includes(node.tagName.toLowerCase())) {
|
||||
node.style.cssText = style
|
||||
} else {
|
||||
walk(node)
|
||||
@ -790,6 +792,18 @@ export const checkIsNodeStyleDataKey = key => {
|
||||
return false
|
||||
}
|
||||
|
||||
// 判断一个对象是否不需要触发节点重新创建
|
||||
export const isNodeNotNeedRenderData = config => {
|
||||
const list = [...lineStyleProps] // 节点连线样式
|
||||
const keys = Object.keys(config)
|
||||
for (let i = 0; i < keys.length; i++) {
|
||||
if (!list.includes(keys[i])) {
|
||||
return false
|
||||
}
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
// 合并图标数组
|
||||
// const data = [
|
||||
// { type: 'priority', name: '优先级图标', list: [{ name: '1', icon: 'a' }, { name: 2, icon: 'b' }] },
|
||||
|
||||
Loading…
Reference in New Issue
Block a user