Fix bug in translating

This commit is contained in:
Steve Ruiz 2021-06-13 14:55:37 +01:00
parent 9123fd62fc
commit 4a36ff7341
10 changed files with 59 additions and 33 deletions

View file

@ -51,8 +51,6 @@ export default function Page() {
.map((shape) => shape.id) .map((shape) => shape.id)
}, deepCompareArrays) }, deepCompareArrays)
console.log(currentPageShapeIds.length)
const isSelecting = useSelector((s) => s.isIn('selecting')) const isSelecting = useSelector((s) => s.isIn('selecting'))
return ( return (

View file

@ -58,11 +58,6 @@ const group = registerShapeUtils<GroupShape>({
) )
}, },
translateTo(shape, point) {
shape.point = point
return this
},
getBounds(shape) { getBounds(shape) {
if (!this.boundsCache.has(shape)) { if (!this.boundsCache.has(shape)) {
const [width, height] = shape.size const [width, height] = shape.size

View file

@ -222,12 +222,12 @@ function getDefaultShapeUtil<T extends Shape>(): ShapeUtility<T> {
}, },
translateBy(shape, delta) { translateBy(shape, delta) {
shape.point = vec.add(shape.point, delta) shape.point = vec.round(vec.add(shape.point, delta))
return this return this
}, },
translateTo(shape, point) { translateTo(shape, point) {
shape.point = point shape.point = vec.round(point)
return this return this
}, },

View file

@ -72,8 +72,10 @@ export default function translateCommand(
// Move shapes back to where they started // Move shapes back to where they started
for (const { id, point } of initialShapes) { for (const { id, point } of initialShapes) {
getDocumentBranch(data, id).forEach((id) => {
const shape = shapes[id] const shape = shapes[id]
getShapeUtils(shape).translateTo(shape, point) getShapeUtils(shape).translateTo(shape, point)
})
} }
// Delete clones // Delete clones

View file

@ -88,7 +88,21 @@ export function fastPinchCamera(
export function fastBrushSelect(point: number[]) { export function fastBrushSelect(point: number[]) {
const data = { ...state.data } const data = { ...state.data }
session.current.update(data, screenToWorld(point, data)) session.current.update(data, screenToWorld(point, data))
state.forceData(Object.freeze(data)) state.forceData(Object.freeze(data))
} }
export function fastTranslate(info: PointerInfo) {
const data = { ...state.data }
session.current.update(
data,
screenToWorld(info.point, data),
info.shiftKey,
info.altKey
)
state.forceData(Object.freeze(data))
}

View file

@ -24,7 +24,7 @@ export default class BrushSession extends BaseSession {
// Add a first point but don't update the shape yet. We'll update // Add a first point but don't update the shape yet. We'll update
// when the draw session ends; if the user hasn't added additional // when the draw session ends; if the user hasn't added additional
// points, this single point will be interpreted as a "dot" shape. // points, this single point will be interpreted as a "dot" shape.
this.points = [[0, 0]] this.points = [[0, 0, 0.5]]
const shape = getPage(data).shapes[id] const shape = getPage(data).shapes[id]
@ -103,13 +103,14 @@ export default class BrushSession extends BaseSession {
// Update the points and update the shape's parents. // Update the points and update the shape's parents.
const shape = getShape(data, snapshot.id) as DrawShape const shape = getShape(data, snapshot.id) as DrawShape
if (newPoint[0] < 0 || newPoint[1] < 0) { // Offset the points and shapes to avoid negative numbers
const offset = [Math.min(newPoint[0], 0), Math.min(newPoint[1], 0)] const ox = Math.min(newPoint[0], 0)
const oy = Math.min(newPoint[1], 0)
this.points = this.points.map((pt) => vec.sub(pt, offset))
this.origin = vec.sub(this.origin, offset)
if (ox < 0 || oy < 0) {
const offset = [ox, oy]
this.points = this.points.map((pt) => [...vec.sub(pt, offset), pt[2]])
this.origin = vec.add(this.origin, offset)
getShapeUtils(shape).translateBy(shape, offset) getShapeUtils(shape).translateBy(shape, offset)
} }
@ -121,6 +122,7 @@ export default class BrushSession extends BaseSession {
cancel = (data: Data) => { cancel = (data: Data) => {
const { snapshot } = this const { snapshot } = this
const shape = getShape(data, snapshot.id) as DrawShape const shape = getShape(data, snapshot.id) as DrawShape
getShapeUtils(shape).translateTo(shape, snapshot.point)
getShapeUtils(shape).setProperty(shape, 'points', snapshot.points) getShapeUtils(shape).setProperty(shape, 'points', snapshot.points)
updateParents(data, [shape.id]) updateParents(data, [shape.id])
} }
@ -144,10 +146,11 @@ export default class BrushSession extends BaseSession {
export function getDrawSnapshot(data: Data, shapeId: string) { export function getDrawSnapshot(data: Data, shapeId: string) {
const page = getPage(current(data)) const page = getPage(current(data))
const { points } = page.shapes[shapeId] as DrawShape const { points, point } = page.shapes[shapeId] as DrawShape
return { return {
id: shapeId, id: shapeId,
point,
points, points,
} }
} }

View file

@ -12,8 +12,6 @@ import {
getPage, getPage,
getRelativeTransformedBoundingBox, getRelativeTransformedBoundingBox,
getSelectedIds, getSelectedIds,
getSelectedShapes,
getShapes,
getTransformedBoundingBox, getTransformedBoundingBox,
setToArray, setToArray,
updateParents, updateParents,

View file

@ -8,8 +8,10 @@ import {
getChildIndexAbove, getChildIndexAbove,
getDocumentBranch, getDocumentBranch,
getPage, getPage,
getPageState,
getSelectedShapes, getSelectedShapes,
setSelectedIds, setSelectedIds,
setToArray,
updateParents, updateParents,
} from 'utils/utils' } from 'utils/utils'
import { getShapeUtils } from 'lib/shape-utils' import { getShapeUtils } from 'lib/shape-utils'
@ -50,25 +52,28 @@ export default class TranslateSession extends BaseSession {
if (!this.isCloning) { if (!this.isCloning) {
this.isCloning = true this.isCloning = true
for (const { id } of initialShapes) { // Move original shapes back to start
for (const { id, point } of initialShapes) {
const shape = shapes[id] const shape = shapes[id]
getShapeUtils(shape).translateBy(shape, trueDelta) getShapeUtils(shape).translateTo(shape, point)
} }
for (const clone of clones) { for (const clone of clones) {
shapes[clone.id] = { ...clone } shapes[clone.id] = { ...clone, point: [...clone.point] }
const parent = shapes[clone.parentId]
const shape = shapes[clone.id]
getShapeUtils(shape).translateBy(shape, delta)
const parent = shapes[shape.parentId]
if (!parent) continue if (!parent) continue
getShapeUtils(parent).setProperty(parent, 'children', [ getShapeUtils(parent).setProperty(parent, 'children', [
...parent.children, ...parent.children,
clone.id, shape.id,
]) ])
} }
setSelectedIds(
data,
clones.map((c) => c.id)
)
} }
for (const { id } of clones) { for (const { id } of clones) {
@ -76,6 +81,11 @@ export default class TranslateSession extends BaseSession {
getShapeUtils(shape).translateBy(shape, trueDelta) getShapeUtils(shape).translateBy(shape, trueDelta)
} }
setSelectedIds(
data,
clones.map((c) => c.id)
)
updateParents( updateParents(
data, data,
clones.map((c) => c.id) clones.map((c) => c.id)
@ -93,6 +103,13 @@ export default class TranslateSession extends BaseSession {
delete shapes[clone.id] delete shapes[clone.id]
} }
for (const initialShape of initialShapes) {
getDocumentBranch(data, initialShape.id).forEach((id) => {
const shape = shapes[id]
getShapeUtils(shape).translateBy(shape, delta)
})
}
initialParents.forEach( initialParents.forEach(
(parent) => (parent) =>
((shapes[parent.id] as GroupShape).children = parent.children) ((shapes[parent.id] as GroupShape).children = parent.children)

View file

@ -876,7 +876,7 @@ const state = createState({
createShape(data, payload, type: ShapeType) { createShape(data, payload, type: ShapeType) {
const shape = createShape(type, { const shape = createShape(type, {
parentId: data.currentPageId, parentId: data.currentPageId,
point: screenToWorld(payload.point, data), point: vec.round(screenToWorld(payload.point, data)),
style: getCurrent(data.currentStyle), style: getCurrent(data.currentStyle),
}) })

View file

@ -166,7 +166,6 @@ class Storage {
const savedPage = localStorage.getItem(storageId(fileId, 'page', pageId)) const savedPage = localStorage.getItem(storageId(fileId, 'page', pageId))
if (savedPage !== null) { if (savedPage !== null) {
console.log(lzw_decode(savedPage))
data.document.pages[pageId] = JSON.parse(lzw_decode(savedPage)) data.document.pages[pageId] = JSON.parse(lzw_decode(savedPage))
} else { } else {
data.document.pages[pageId] = { data.document.pages[pageId] = {