|
|
@@ -15,14 +15,23 @@ import { getShapeUtils } from 'lib/shape-utils'
|
|
15
|
15
|
import * as vec from 'utils/vec'
|
|
16
|
16
|
import storage from 'state/storage'
|
|
17
|
17
|
|
|
18
|
|
-export default function nudgeCommand(data: Data, toPageId: string) {
|
|
19
|
|
- const { currentPageId: fromPageId } = data
|
|
|
18
|
+export default function nudgeCommand(data: Data, newPageId: string) {
|
|
|
19
|
+ const { currentPageId: oldPageId } = data
|
|
|
20
|
+ const oldPage = getPage(data)
|
|
20
|
21
|
const selectedIds = setToArray(getSelectedIds(data))
|
|
21
|
22
|
|
|
22
|
|
- const selectedParents = uniqueArray(
|
|
23
|
|
- ...selectedIds.map((id) => getTopParentId(data, id))
|
|
|
23
|
+ const idsToMove = uniqueArray(
|
|
|
24
|
+ ...selectedIds.flatMap((id) => getDocumentBranch(data, id))
|
|
24
|
25
|
)
|
|
25
|
26
|
|
|
|
27
|
+ const oldParentIds = Object.fromEntries(
|
|
|
28
|
+ idsToMove.map((id) => [id, oldPage.shapes[id].parentId])
|
|
|
29
|
+ )
|
|
|
30
|
+
|
|
|
31
|
+ // const selectedParents = uniqueArray(
|
|
|
32
|
+ // ...selectedIds.map((id) => getTopParentId(data, id))
|
|
|
33
|
+ // )
|
|
|
34
|
+
|
|
26
|
35
|
history.execute(
|
|
27
|
36
|
data,
|
|
28
|
37
|
new Command({
|
|
|
@@ -30,16 +39,33 @@ export default function nudgeCommand(data: Data, toPageId: string) {
|
|
30
|
39
|
category: 'canvas',
|
|
31
|
40
|
manualSelection: true,
|
|
32
|
41
|
do(data) {
|
|
33
|
|
- // The page we're moving the shapes from
|
|
|
42
|
+ const fromPageId = oldPageId
|
|
|
43
|
+ const toPageId = newPageId
|
|
|
44
|
+
|
|
34
|
45
|
const fromPage = getPage(data, fromPageId)
|
|
35
|
46
|
|
|
36
|
47
|
// Get all of the selected shapes and their descendents
|
|
37
|
|
- const shapesToMove = selectedParents.flatMap((id) =>
|
|
38
|
|
- getDocumentBranch(data, id).map((id) => fromPage.shapes[id])
|
|
39
|
|
- )
|
|
|
48
|
+ const shapesToMove = idsToMove.map((id) => fromPage.shapes[id])
|
|
|
49
|
+
|
|
|
50
|
+ shapesToMove.forEach((shape) => {
|
|
|
51
|
+ // If the shape is a parent of a group that isn't selected,
|
|
|
52
|
+ // remove the shape's id from its parent's children.
|
|
|
53
|
+ if (
|
|
|
54
|
+ shape.parentId !== fromPageId &&
|
|
|
55
|
+ !idsToMove.includes(shape.parentId)
|
|
|
56
|
+ ) {
|
|
|
57
|
+ const parent = fromPage.shapes[shape.parentId]
|
|
|
58
|
+
|
|
|
59
|
+ getShapeUtils(parent).setProperty(
|
|
|
60
|
+ parent,
|
|
|
61
|
+ 'children',
|
|
|
62
|
+ parent.children.filter((id) => id !== shape.id)
|
|
|
63
|
+ )
|
|
|
64
|
+ }
|
|
40
|
65
|
|
|
41
|
|
- // Delete the shapes from the "from" page
|
|
42
|
|
- shapesToMove.forEach((shape) => delete fromPage.shapes[shape.id])
|
|
|
66
|
+ // Delete the shapes from the "from" page
|
|
|
67
|
+ delete fromPage.shapes[shape.id]
|
|
|
68
|
+ })
|
|
43
|
69
|
|
|
44
|
70
|
// Clear the current page state's selected ids
|
|
45
|
71
|
getPageState(data, fromPageId).selectedIds.clear()
|
|
|
@@ -53,21 +79,18 @@ export default function nudgeCommand(data: Data, toPageId: string) {
|
|
53
|
79
|
// The page we're moving the shapes to
|
|
54
|
80
|
const toPage = getPage(data, toPageId)
|
|
55
|
81
|
|
|
56
|
|
- // Add all of the selected shapes to the "from" page. Any shapes that
|
|
57
|
|
- // were children of the "from" page should become children of the "to"
|
|
58
|
|
- // page. Grouped shapes should keep their same parent.
|
|
59
|
|
-
|
|
60
|
|
- // What about shapes that were children of a group that we haven't moved?
|
|
|
82
|
+ // Add all of the selected shapes to the "from" page.
|
|
61
|
83
|
shapesToMove.forEach((shape) => {
|
|
62
|
84
|
toPage.shapes[shape.id] = shape
|
|
63
|
|
- if (shape.parentId === fromPageId) {
|
|
|
85
|
+ })
|
|
|
86
|
+
|
|
|
87
|
+ // If a shape's parent isn't in the document, re-parent to the page.
|
|
|
88
|
+ shapesToMove.forEach((shape) => {
|
|
|
89
|
+ if (!toPage.shapes[shape.parentId]) {
|
|
64
|
90
|
getShapeUtils(shape).setProperty(shape, 'parentId', toPageId)
|
|
65
|
91
|
}
|
|
66
|
92
|
})
|
|
67
|
93
|
|
|
68
|
|
- console.log('from', getPage(data, fromPageId))
|
|
69
|
|
- console.log('to', getPage(data, toPageId))
|
|
70
|
|
-
|
|
71
|
94
|
// Select the selected ids on the new page
|
|
72
|
95
|
getPageState(data, toPageId).selectedIds = new Set(selectedIds)
|
|
73
|
96
|
|
|
|
@@ -75,32 +98,58 @@ export default function nudgeCommand(data: Data, toPageId: string) {
|
|
75
|
98
|
data.currentPageId = toPageId
|
|
76
|
99
|
},
|
|
77
|
100
|
undo(data) {
|
|
78
|
|
- const toPage = getPage(data, fromPageId)
|
|
|
101
|
+ const fromPageId = newPageId
|
|
|
102
|
+ const toPageId = oldPageId
|
|
79
|
103
|
|
|
80
|
|
- const shapesToMove = selectedParents.flatMap((id) =>
|
|
81
|
|
- getDocumentBranch(data, id).map((id) => toPage.shapes[id])
|
|
82
|
|
- )
|
|
|
104
|
+ const fromPage = getPage(data, fromPageId)
|
|
83
|
105
|
|
|
84
|
|
- shapesToMove.forEach((shape) => delete toPage.shapes[shape.id])
|
|
|
106
|
+ const shapesToMove = idsToMove.map((id) => fromPage.shapes[id])
|
|
85
|
107
|
|
|
86
|
|
- getPageState(data, toPageId).selectedIds.clear()
|
|
|
108
|
+ shapesToMove.forEach((shape) => {
|
|
|
109
|
+ if (
|
|
|
110
|
+ shape.parentId !== fromPageId &&
|
|
|
111
|
+ !idsToMove.includes(shape.parentId)
|
|
|
112
|
+ ) {
|
|
|
113
|
+ const parent = fromPage.shapes[shape.parentId]
|
|
|
114
|
+
|
|
|
115
|
+ getShapeUtils(parent).setProperty(
|
|
|
116
|
+ parent,
|
|
|
117
|
+ 'children',
|
|
|
118
|
+ parent.children.filter((id) => id !== shape.id)
|
|
|
119
|
+ )
|
|
|
120
|
+ }
|
|
87
|
121
|
|
|
88
|
|
- storage.savePage(data, toPageId)
|
|
|
122
|
+ delete fromPage.shapes[shape.id]
|
|
|
123
|
+ })
|
|
89
|
124
|
|
|
90
|
|
- storage.loadPage(data, fromPageId)
|
|
|
125
|
+ getPageState(data, fromPageId).selectedIds.clear()
|
|
91
|
126
|
|
|
92
|
|
- const fromPage = getPage(data, toPageId)
|
|
|
127
|
+ storage.savePage(data, fromPageId)
|
|
|
128
|
+
|
|
|
129
|
+ storage.loadPage(data, toPageId)
|
|
|
130
|
+
|
|
|
131
|
+ const toPage = getPage(data, toPageId)
|
|
93
|
132
|
|
|
94
|
133
|
shapesToMove.forEach((shape) => {
|
|
95
|
|
- fromPage.shapes[shape.id] = shape
|
|
96
|
|
- if (shape.parentId === toPageId) {
|
|
97
|
|
- getShapeUtils(shape).setProperty(shape, 'parentId', fromPageId)
|
|
|
134
|
+ toPage.shapes[shape.id] = shape
|
|
|
135
|
+
|
|
|
136
|
+ // Move shapes back to their old parent
|
|
|
137
|
+ const parentId = oldParentIds[shape.id]
|
|
|
138
|
+ getShapeUtils(shape).setProperty(shape, 'parentId', parentId)
|
|
|
139
|
+
|
|
|
140
|
+ // And add the shape back to the parent's children
|
|
|
141
|
+ if (parentId !== toPageId) {
|
|
|
142
|
+ const parent = toPage.shapes[parentId]
|
|
|
143
|
+ getShapeUtils(parent).setProperty(parent, 'children', [
|
|
|
144
|
+ ...parent.children,
|
|
|
145
|
+ shape.id,
|
|
|
146
|
+ ])
|
|
98
|
147
|
}
|
|
99
|
148
|
})
|
|
100
|
149
|
|
|
101
|
|
- getPageState(data, fromPageId).selectedIds = new Set(selectedIds)
|
|
|
150
|
+ getPageState(data, toPageId).selectedIds = new Set(selectedIds)
|
|
102
|
151
|
|
|
103
|
|
- data.currentPageId = fromPageId
|
|
|
152
|
+ data.currentPageId = toPageId
|
|
104
|
153
|
},
|
|
105
|
154
|
})
|
|
106
|
155
|
)
|