From fafeecd3a92497ecd7c7a838f56ec777810ec1fa Mon Sep 17 00:00:00 2001 From: Liang Ding Date: Thu, 2 Feb 2023 22:35:01 +0800 Subject: [PATCH] =?UTF-8?q?:art:=20=E6=94=B9=E8=BF=9B=E5=9D=97=E6=A0=91?= =?UTF-8?q?=E6=95=B0=E6=8D=AE=E7=B4=A2=E5=BC=95=E7=A8=B3=E5=AE=9A=E6=80=A7?= =?UTF-8?q?=20https://github.com/siyuan-note/siyuan/issues/7240?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- kernel/treenode/blocktree.go | 43 +++++++++++++++++++++++++++--------- kernel/treenode/node.go | 18 +++++++++++++++ 2 files changed, 51 insertions(+), 10 deletions(-) diff --git a/kernel/treenode/blocktree.go b/kernel/treenode/blocktree.go index 01b98b81c..43da32297 100644 --- a/kernel/treenode/blocktree.go +++ b/kernel/treenode/blocktree.go @@ -248,14 +248,11 @@ func RemoveBlockTree(id string) { } func IndexBlockTree(tree *parse.Tree) { + var changedNodes []*ast.Node ast.Walk(tree.Root, func(n *ast.Node, entering bool) ast.WalkStatus { if !entering || !n.IsBlock() { return ast.WalkContinue } - var parentID string - if nil != n.Parent { - parentID = n.Parent.ID - } if "" == n.ID { return ast.WalkContinue } @@ -267,19 +264,45 @@ func IndexBlockTree(tree *parse.Tree) { blockTrees.Store(hash, val) } slice := val.(*btSlice) + slice.m.Lock() - if bt := slice.data[n.ID]; nil != bt { + bt := slice.data[n.ID] + slice.m.Unlock() + + if nil != bt { if bt.Updated != n.IALAttr("updated") { - slice.data[n.ID] = &BlockTree{ID: n.ID, ParentID: parentID, RootID: tree.ID, BoxID: tree.Box, Path: tree.Path, HPath: tree.HPath, Updated: n.IALAttr("updated"), Type: TypeAbbr(n.Type.String())} - slice.changed = time.Now() + children := ChildBlockNodes(n) // 需要考虑子块,因为一些操作(比如移动块)后需要同时更新子块 + changedNodes = append(changedNodes, children...) } } else { - slice.data[n.ID] = &BlockTree{ID: n.ID, ParentID: parentID, RootID: tree.ID, BoxID: tree.Box, Path: tree.Path, HPath: tree.HPath, Updated: n.IALAttr("updated"), Type: TypeAbbr(n.Type.String())} - slice.changed = time.Now() + children := ChildBlockNodes(n) + changedNodes = append(changedNodes, children...) } - slice.m.Unlock() return ast.WalkContinue }) + + for _, n := range changedNodes { + updateBtSlice(n, tree) + } +} + +func updateBtSlice(n *ast.Node, tree *parse.Tree) { + var parentID string + if nil != n.Parent { + parentID = n.Parent.ID + } + + hash := btHash(n.ID) + val, ok := blockTrees.Load(hash) + if !ok { + val = &btSlice{data: map[string]*BlockTree{}, changed: time.Time{}, m: &sync.Mutex{}} + blockTrees.Store(hash, val) + } + slice := val.(*btSlice) + slice.m.Lock() + slice.data[n.ID] = &BlockTree{ID: n.ID, ParentID: parentID, RootID: tree.ID, BoxID: tree.Box, Path: tree.Path, HPath: tree.HPath, Updated: n.IALAttr("updated"), Type: TypeAbbr(n.Type.String())} + slice.changed = time.Now() + slice.m.Unlock() } func InitBlockTree(force bool) { diff --git a/kernel/treenode/node.go b/kernel/treenode/node.go index 52e416ab7..763e847ab 100644 --- a/kernel/treenode/node.go +++ b/kernel/treenode/node.go @@ -285,6 +285,24 @@ func ParentNodes(node *ast.Node) (parents []*ast.Node) { return } +func ChildBlockNodes(node *ast.Node) (children []*ast.Node) { + children = []*ast.Node{} + if !node.IsContainerBlock() || ast.NodeDocument == node.Type { + children = append(children, node) + return + } + + ast.Walk(node, func(n *ast.Node, entering bool) ast.WalkStatus { + if !entering || !n.IsBlock() { + return ast.WalkContinue + } + + children = append(children, n) + return ast.WalkContinue + }) + return +} + func ParentBlock(node *ast.Node) *ast.Node { for p := node.Parent; nil != p; p = p.Parent { if "" != p.ID && p.IsBlock() {