The video shape was not interactive in it's editing mode, so I just
updated it to have `pointer-events: all` when editing.
closes#1908
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Add a step-by-step description of how to test your PR here.
2.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- Fixes pointer events for editing video shapes.
closes https://github.com/tldraw/brivate/issues/2876
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Add a step-by-step description of how to test your PR here.
2.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- Fixes an issue where line handles were slightly offset from the
indicator line.
closes#1893
Normally when you start a pinch it does the following within a few
frames:
- first finger goes down, begins a drawing gesture, adds a mark to the
undo stack
- second finger goes down, cancels the drawing gesture, bails to the
mark
but when the toolbar is open, it follows the same process without adding
a mark to the undo stack, so that when it bails it bails to the previous
mark.
This PR updates the logic to create a mark ID when setting the mark, and
only bail if the mark id was set on enter.
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Add a step-by-step description of how to test your PR here.
2.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- Fixes a bug that could trigger undo by accident when closing the style
toolbar via a pinch gesture on mobile.
When editing shapes the viewport would be reset to the shape whenever it
moved out of camera bounds, it looked kinda janky. We're now going to
let the user scroll away if they'd like.
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Add a step-by-step description of how to test your PR here.
2.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
Removed a feature to reset the viewport back to a shape that is being
edited.
(Before) Don't be held back by the past
![Kapture 2023-09-15 at 10 57
29](https://github.com/tldraw/tldraw/assets/98838967/d8891621-766e-46a2-b1ca-afa968b7f08c)
(After) You are free to find new avenues of exploration
![Kapture 2023-09-15 at 11 02
36](https://github.com/tldraw/tldraw/assets/98838967/82f318ab-944b-41bd-8297-a35467a15987)
This PR fixes a bug that would cause an interactive iframe (e.g. a
youtube video) to lose its editing state once clicked.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Create an interactive iframe.
2. Begin editing.
3. Click inside of the iframe
Add `Store.migrateSnapshot`, another surface API alongside getSnapshot
and loadSnapshot.
### Change Type
- [x] `minor` — New feature
### Release Notes
- [editor] add `Store.migrateSnapshot`
This PR:
- adds a `snapshot` prop to the <Tldraw> component. It does basically
the same thing as calling `loadSnapshot` after creating the store, but
happens before the editor actually loads.
- adds a largeish example (including a JSON snapshot) to the examples
We have some very complex ways of juggling serialized data between
multiplayer, file formats, and the snapshot APIs. I'd like to see these
simplified, or at least for our documentation to reflect a narrow subset
of all the options available.
The most common questions seem to be:
Q: How do I serialize data?
A: Via the `Editor.getSnapshot()` method
Q: How do I restore serialized data?
A: Via the `Editor.loadSnapshot()` method OR via the `<Tldraw>`
component's `snapshot` prop
The store has an `initialData` constructor prop, however this is quite
complex as the store also requires a schema class instance with which to
migrate the data. In our components (<Tldraw> and <TldrawEditor>) we
were also accepting `initialData`, however we weren't accepting a
schema, and either way I think it's unrealistic to also expect users to
create schemas themselves and pass those in.
AFAIK the `initialData` prop is only used in the file loading, which is
a good example of how complex it looks like to create a schema and
migrate data outside of the components.
### Change Type
- [x] `minor` — New feature
This PR fixes zero width or height on Geometry2d bounds. It adds the
`zeroFix` helper to the `Box2d` class.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Create a straight line
2. Create a straight arrow that binds to the straight line
- [x] Unit Tests
### Release Notes
- Fix bug with straight lines / arrows
Closes [#2737](https://github.com/tldraw/brivate/issues/2737)
For the checkbox and x-box the inner lines are inset slightly from the
edges to account for the stroke width. Alas at tiny box sizes (the box
is creates as w:1,h:1 during a drag-to-create interaction) this was
ending up with the insets overflowing such that they left the box on the
other side, creating miscalculations during the initial resizing.
This PR clamps the positions of the x-box and checkbox inner lines so
they don't escape the bounds of the box.
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Add a step-by-step description of how to test your PR here.
2.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- Fixes a regression introduced by the geometry refactor related to
x-box and checkbox resizing.
Fixes pixel rounding when calculating css transformations for overlay
items. Also fixes issue where `editor.instanceState.devicePixelRatio`
wasn't properly updating.
TLDR; `width * window.devicePixelRatio` should be integer to avoid
rounding. `--tl-dpr-multiple` is smallest integer to multiply
`window.devicePixelRatio` such that its product is an integer.
#1852#1836#1834
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
Would need to add a test checking when `window.devicePixelRatio`
changes, that `editor.instanceState.devicePixelRatio` is equal.
---------
Co-authored-by: David Sheldrick <d.j.sheldrick@gmail.com>
This PR fixes a bug where pasted content would be placed incorrectly if
pasted into a parent frame.
Closes#1857
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Add a step-by-step description of how to test your PR here.
2.
- [x] Unit Tests
- [ ] End to end tests
### Release Notes
- Fixes a bug affecting the position of pasted content inside frames.
Before
![image](https://github.com/tldraw/tldraw/assets/1242537/3bd21dda-2dab-4e1b-8c57-f90799b98f53)
After
![image](https://github.com/tldraw/tldraw/assets/1242537/8e55e154-a4dc-4f46-ac5a-4b322926733b)
follow up to https://github.com/tldraw/tldraw/pull/1836 should fix the
caveat raised by @leolorenzoluis #1834
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Release Notes
- Fixes indicator transform miscalculation on android and windows
This PR fixes a bug that would effect pointer events inside of shapes.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Create a frame
2. Try to edit its title by double clicking on it
This PR fixes the "Exit Pen Mode" button (see first commit).
There are some other "wrap some stuff in editor.batch" changes in the
"follow up changes" commit.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Use an ipad / pencil to enter pen mode
2. Click the Exit pen mode button
This PR fixes a bug where external content handlers etc defined in an
`onMount` were being overwritten by the default external content
handlers.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Try adding images to rooms in our dot com staging environement
(sorry).
This PR fixes an extremely performance-crushing bug that was happening
in Safari and Chrome when iframes were present.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Create one hundred shapes
2. Create a gist or maps embed
3. Select all
If the app crashes or the rendering layers list grows to lots and lots
of layers, that's the bug.
### Release Notes
- [fix] iframe rendering issue
This PR fixes a bug where tool lock would cause the line tool to not
work properly.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Turn on tool lock.
2. Draw two line shapes
- [x] Unit Tests
This PR fixes the effect of browser zoom on SVG overlays. I don't know
why this works.
Should fix https://github.com/tldraw/tldraw/issues/1834
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Draw a rectangle.
2. Change your browser's zoom level (note: not tldraw's zoom level, just
your browser's).
3. Select the rectangle.
This PR fixes a bug where arrows would bind to locked shapes.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Lock a shape.
2. Confirm that an arrow can neither begin bound to the shape
3. Confirm that an arrow cannot bind to the shape
- [ ] Unit Tests
- [ ] End to end tests
---------
Co-authored-by: Mitja Bezenšek <mitja.bezensek@gmail.com>
This PR adds additional props to the <Tldraw> component for setting the
maximum asset size, maximum image dimensions, accepted image types, and
accepted video types. It adds an example for using these properties and
for uploading image assets.
### Change Type
- [x] `minor` — New feature
### Test Plan
1. Try (and fail) to upload image types other than the default types.
2. Try (and fail) to upload images / videos larger than 10mb.
3. Use the example to customize the properties.
### Release Notes
- [@tldraw/tldraw] add asset props
This PR fixes some creative use of CSS in setting the radius property of
various SVGs. While this use is supported in all browsers, it was
confusing CSS processors. Moving these out of CSS and into JavaScript
seems to be a pretty minor trade. Closes
https://github.com/tldraw/tldraw/issues/1775.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Ensure that borders and handles adjust their radii correctly when
zoomed in or out.
Previously, we'd used `Array.findLast` in `getSelectedShapeAtPoint`.
This PR removes that newish JS call and replaces it with a `replace` and
`find` instead. Closes bug mentioned in
https://github.com/tldraw/tldraw/issues/1798.
### Change Type
- [x] `patch` — Bug fix
This PR fixes editing video shapes. The controls are now interactive
again.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Create a video shape.
2. Double click to edit the shape.
3. Use the controls to pause, change time, etc.
### Release Notes
- Fix bug with editing video shapes.
This PR adds an "Unlock all" action to the edit menu.
- Selecting `unlock all` sets `isLocked` to false for all shapes on the
current page
- The option is disabled if the page is empty; but we don't check
whether there are locked shapes on the page (juice < squeeze)
Closes https://github.com/tldraw/tldraw/issues/1809
### Change Type
- [x] `minor` — New feature
### Test Plan
1. Create locked shapes
2. Select menu > edit > unlock all
### Release Notes
- Adds the unlock all feature.
This PR updates the way that styles are changed. It splits `setStyle`
and `setOpacity` into `setStyleForNext Shape` and
`setOpacityForNextShape` and `setStyleForSelectedShapes` and
`setOpacityForSelectedShapes`. It fixes the issue with setting one style
re-setting other styles.
### Change Type
- [x] `major` — Breaking change
### Test Plan
1. Set styles when shapes are not selected.
2. Set styles when shapes are selected.
3. Set styles when shapes are selected and the selected tool is not
select.
- [x] Unit Tests
This PR improves the UX around sticky notes. It fixes were some bugs
related to the editing / hovered shape after cloning a sticky note
shape.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Use the sticky note tool
2. Alt-drag to clone sticky notes
3. Use the Enter key to edit the selected shape.
4. Double click an editable shape and then click once to edit a shape of
the same type.
- [x] Unit Tests
This PR includes further UX improvements to selection.
- clicking inside of a hollow shape will no longer select it on pointer
up
- clicking a shape's filled label will select it on pointer down
- clicking a shape's empty label will select it on pointer up
- clicking and dragging a selected arrow is now better limited to its
body, not its bounds
- arrows will no longer bind to labels
### Text labels
A big change here relates to text labels. Previously, we had listeners
set on the text label elements; I've removed these and we now check the
actual label bounds geometry for a hit. For geo shapes, this geometry is
now placed correctly based on the alignment / vertical alignment of the
label.
- Clicking on a label with text in it will select the shape on pointer
down.
- Clicking on an empty text label will select the shape on pointer up.
## Hollow shapes
Previously, shapes with `fill: none` were also being selected on pointer
up. I've removed that logic because it was producing wrong-feeling
selections too often. We now select these shapes only when clicking on
the label (as mentioned above) or when clicking on the edges of the
shape. This is in line with the original behavior (currently on
tldraw.com, prior to the earlier PR that updated selection logic).
## Arrows
Arrows still hit the inside of hollow shapes, using the "smallest
hovered" logic previously used for pointer-up selection on hollow
shapes. They also now correctly do so while ignoring text labels.
### Change Type
- [x] `minor` — New feature
### Test Plan
1. try selecting geo shapes, nested geo shapes, arrows and shapes with
labels or without labels
- [x] Unit Tests
This PR fixes the collaborator scribble in the laser pointer, etc.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. In a multiplayer room, have a peer use the laser tool or eraser tool.
This PR cleans up some APIs around the editor's current page state:
- `setEditingShapeId` -> `setEditingShape`
- `setHoveredShapeId` -> `setHoveredShape`
- `setCroppingShapeId` -> `setCroppingShape`
- `setFocusedGroupId` -> `setFocusedGroup`
- `setErasingShapeIds` -> `setErasingShapes`
- `setHintingShapeIds` -> `setHintingShapes`
It also adds some additional computed getters, e.g.
`Editor.croppingShape`.
It also adds some errors around `setCroppingShape`.
### Change Type
- [x] `major` — Breaking change
### Test Plan
- [x] Unit Tests
This PR:
- improves the logic for computing `renderingShapes`
- improves the handling of side effects related to cropping
We might use the same side effect logic to edit / re-edit shapes, though
this may be more complicated with inputs that steal focus.
### Change Type
- [x] `major` — Breaking change
### Test Plan
1. Crop an image
2. Change the crop
3. Stop cropping
4. Undo — you should be cropping again!
5. Undo until you're not cropping anymore
6. Redo until you're cropping again
7. etc.
- [x] Unit Tests
This PR fixes our page to screen conversion.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Drop an image onto the screen while the camera is panned and zoomed.
- [x] Unit Tests
This PR:
- adds history options to several commands in order to allow them to
support squashing and ephemeral data (previously, these commands had
boolean values for squashing / ephemeral)
It also:
- changes `markId` to return the editor instance rather than the mark id
passed into the command
- removes `focus` and `blur` commands
- changes `createPage` parameters
- unifies `animateShape` / `animateShapes` options
### Change Type
- [x] `major` — Breaking change
### Test Plan
- [x] Unit Tests
This PR turns off snapping between shapes and arrows.
### Change Type
- [x] `patch`
### Test Plan
1. Drag a shape while snapping
2. The shape should not snap to the position of arrows
Describe what your pull request does. If appropriate, add GIFs or images
showing the before and after.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Resize the page so that the page menu scrolls
2. Edit the title of the last item
3. Click around the titles
### Release Notes
- (fix) page menu editing
This PR:
- fixes switching between an embed and a link (it's moved to the edit
menu for now, so a bit buried).
- fixes the tldraw embed
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Try to embed a tldraw url into a room.
### Release Notes
- [fix] tldraw embeds
This PR:
- supports client configuration of the rendering bounds via
`Editor.renderingBoundsMargin`
- no longer culls selected shapes
- restores rendering shape tests accidentally removed in #1786
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Select shapes, scroll quickly to see if they get culled
- [x] Unit Tests
### Release Notes
- [editor] add `Editor.renderingBoundsMargin`
This PR updates camera APIs:
- removes animateCamera
- adds animation support to setCamera
- makes camera commands accept points rather than an x/y
- `centerOnPoint`
- `pageToScreen`
- `screenToPoint`
- `pan`
- `setCamera`
- makes `zoomToBounds` accept a `Box2d` rather than x/y/w/h
- removes the `getBoundingClientRects` call from `getPointerInfo`
- removes the resize observer from `useScreenBounds`, uses an interval
instead when focused
A big (unexpected) improvement here is that `getBoundingClientRects` was
being called on every pointer move. This is a relatively expensive call
(it forces reflow) which could impact interactions. It's now called at
most once per second, and we could probably improve on that too if we
needed by only updating while in the select state.
### Change Type
- [x] `major` — Breaking change
### Test Plan
1. Try the multiple editors example after scrolling / resizing
2. Use the camera commands (zoom in, etc)
- [x] Unit Tests
### Release Notes
- (editor) improve camera commands
Reverts tldraw/tldraw#1778.
Fuzz testing picked up errors related to deleting pages and undo/redo
which may doom this PR.
### Change Type
- [x] `major` — Breaking change
This PR shrinks the commands API surface and adds a manager
(`CleanupManager`) for side effects.
### Change Type
- [x] `major` — Breaking change
### Test Plan
Use the app! Especially undo and redo. Our tests are passing but I've
found more cases where our coverage fails to catch issues.
### Release Notes
- tbd
This PR adds val town to tldraw's collection of embeddable things.
### Change Type
- [x] `minor` — New feature
### Test Plan
1. Add links to val town, e.g.
https://www.val.town/v/steveruizok.mathFact
### Release Notes
- (feature) val town
This PR fixes the extra outlines on text shapes when not editing those
shapes.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Create two text shapes
2. Edit one of them
3. The outline on the second shape should not be shown
This PR exports the `UiEventsProvider` component (and renames
`useEvents` to `useUiEvents`). It also changes the `useUiEvents` hook to
work outside of the context. When used outside of the context, the hook
will no longer throw an error—though it will also have no effect.
### Change Type
- [x] `minor`
### Release Notes
- [@tldraw/tldraw] export ui events, so that UI hooks can work without
context
These shapes no longer use perfect freehand for their rendering, so we
can drop the effect of `useForceSolid` for them.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Zoom out
2. Draw style draw shapes should not change
### Release Notes
- Remove the force solid switching for geo / line shapes
This PR makes it so that locked shapes do not show an indicator when
hovered.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Hover a locked shape
2. Hover a shape, then lock it
### Release Notes
- locked shapes do not show an indicator when hovered
This PR fixes a bug that was introduced (by me) in #1751, where:
- the `commonBoundsOfAllShapesOnCurrentPage` would mutate the first
bounding box
- the render reactor would fire too often
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Use the minimap
This PR removes `Editor.selectionPageCenter` and moves its
implementation inline where used (in two places).
### Change Type
- [x] `major` — Breaking change
### Release Notes
- [dev] Removes `Editor.selectionPageCenter`
This PR fixes a bug introduced with #1751 where pointing the bounds of
rotated selections would not correctly hit the bounds background.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Create a rotated selection.
2. Point into the bounds background
- [x] Unit Tests
This PR removes the indexes from `parentsToChildrenWithIndexes`. The
indexes weren't needed except for in one place, where a `getShape` was
easier.
### Change Type
- [x] `minor` — New feature
This PR fixes some GREP-introduced errors to the old structure of legacy
v1 documents.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Open a V1 document.
This PR is a significant rewrite of our selection / hit testing logic.
It
- replaces our current geometric helpers (`getBounds`, `getOutline`,
`hitTestPoint`, and `hitTestLineSegment`) with a new geometry API
- moves our hit testing entirely to JS using geometry
- improves selection logic, especially around editing shapes, groups and
frames
- fixes many minor selection bugs (e.g. shapes behind frames)
- removes hit-testing DOM elements from ShapeFill etc.
- adds many new tests around selection
- adds new tests around selection
- makes several superficial changes to surface editor APIs
This PR is hard to evaluate. The `selection-omnibus` test suite is
intended to describe all of the selection behavior, however all existing
tests are also either here preserved and passing or (in a few cases
around editing shapes) are modified to reflect the new behavior.
## Geometry
All `ShapeUtils` implement `getGeometry`, which returns a single
geometry primitive (`Geometry2d`). For example:
```ts
class BoxyShapeUtil {
getGeometry(shape: BoxyShape) {
return new Rectangle2d({
width: shape.props.width,
height: shape.props.height,
isFilled: true,
margin: shape.props.strokeWidth
})
}
}
```
This geometric primitive is used for all bounds calculation, hit
testing, intersection with arrows, etc.
There are several geometric primitives that extend `Geometry2d`:
- `Arc2d`
- `Circle2d`
- `CubicBezier2d`
- `CubicSpline2d`
- `Edge2d`
- `Ellipse2d`
- `Group2d`
- `Polygon2d`
- `Rectangle2d`
- `Stadium2d`
For shapes that have more complicated geometric representations, such as
an arrow with a label, the `Group2d` can accept other primitives as its
children.
## Hit testing
Previously, we did all hit testing via events set on shapes and other
elements. In this PR, I've replaced those hit tests with our own
calculation for hit tests in JavaScript. This removed the need for many
DOM elements, such as hit test area borders and fills which only existed
to trigger pointer events.
## Selection
We now support selecting "hollow" shapes by clicking inside of them.
This involves a lot of new logic but it should work intuitively. See
`Editor.getShapeAtPoint` for the (thoroughly commented) implementation.
![Kapture 2023-07-23 at 23 27
27](https://github.com/tldraw/tldraw/assets/23072548/a743275c-acdb-42d9-a3fe-b3e20dce86b6)
every sunset is actually the sun hiding in fear and respect of tldraw's
quality of interactions
This PR also fixes several bugs with scribble selection, in particular
around the shift key modifier.
![Kapture 2023-07-24 at 23 34
07](https://github.com/tldraw/tldraw/assets/23072548/871d67d0-8d06-42ae-a2b2-021effba37c5)
...as well as issues with labels and editing.
There are **over 100 new tests** for selection covering groups, frames,
brushing, scribbling, hovering, and editing. I'll add a few more before
I feel comfortable merging this PR.
## Arrow binding
Using the same "hollow shape" logic as selection, arrow binding is
significantly improved.
![Kapture 2023-07-22 at 07 46
25](https://github.com/tldraw/tldraw/assets/23072548/5aa724b3-b57d-4fb7-92d0-80e34246753c)
a thousand wise men could not improve on this
## Moving focus between editing shapes
Previously, this was handled in the `editing_shapes` state. This is
moved to `useEditableText`, and should generally be considered an
advanced implementation detail on a shape-by-shape basis. This addresses
a bug that I'd never noticed before, but which can be reproduced by
selecting an shape—but not focusing its input—while editing a different
shape. Previously, the new shape became the editing shape but its input
did not focus.
![Kapture 2023-07-23 at 23 19
09](https://github.com/tldraw/tldraw/assets/23072548/a5e157fb-24a8-42bd-a692-04ce769b1a9c)
In this PR, you can select a shape by clicking on its edge or body, or
select its input to transfer editing / focus.
![Kapture 2023-07-23 at 23 22
21](https://github.com/tldraw/tldraw/assets/23072548/7384e7ea-9777-4e1a-8f63-15de2166a53a)
tldraw, glorious tldraw
### Change Type
- [x] `major` — Breaking change
### Test Plan
1. Erase shapes
2. Select shapes
3. Calculate their bounding boxes
- [ ] Unit Tests // todo
- [ ] End to end tests // todo
### Release Notes
- [editor] Remove `ShapeUtil.getBounds`, `ShapeUtil.getOutline`,
`ShapeUtil.hitTestPoint`, `ShapeUtil.hitTestLineSegment`
- [editor] Add `ShapeUtil.getGeometry`
- [editor] Add `Editor.getShapeGeometry`
<img width="1372" alt="image"
src="https://github.com/tldraw/tldraw/assets/7578559/5d5f29fa-a3d7-488b-a4fe-25673d94134e">
This should be tldraw version instead of react version, the typo
happened here:
b7d9c8684c (diff-feb0a5bdada68de6bf60ae3fd8b83915d234dc78f56cae91f33e5c209ad3bf0a).
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Release Notes
- Fixed asset urls
This PR fixes snapping for arrow shapes. Previously, the middle handle
of an arrow was marked as a vertex, causing the arrow to have to
segments (one of which would be snapped to). In this PR we make the
second handle a "virtual" handle and tweak how we display handles to
preserve the same appearance.
### Change Type
- [x] `minor` — New feature
### Test Plan
1. Drag an arrow while snapping.
### Release Notes
- [fix] arrow snapping
This PR fixes a bug where dark mode would not immediately cause shapes
to update their colors. Previously, we got the current theme during
render but not in a way that hooked into the change. In this update, we
hook into the change. We also pass the change down to shape fills as
props rather than getting the theme from deeper down.
### Change Type
- [x] `patch`
### Test Plan
1. Use dark mode.
2. Switch colors
### Release Notes
- [fix] dark mode colors not updating
This PR is another grab bag:
- renames `readOnly` to `readonly` throughout editor
- fixes a regression related to focus and keyboard shortcuts
- adds a small outline for focused editors
### Change Type
- [x] `major`
### Test Plan
- [x] End to end tests
Fix minor typo error in shapeType declaration
**Change Type**
- [x] `patch`
**Test Plan**
- [x] Unit Tests
- [ ] End to end tests
**Release Notes**
Fix typo
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
This PR removes several extraneous computed values from the editor. It
adds some silly instance state onto the instance state record and
unifies a few methods which were inconsistent. This is fit and finish
work 🧽
## Computed Values
In general, where once we had a getter and setter for `isBlahMode`,
which really masked either an `_isBlahMode` atom on the editor or
`instanceState.isBlahMode`, these are merged into `instanceState`; they
can be accessed / updated via `editor.instanceState` /
`editor.updateInstanceState`.
## tldraw select tool specific things
This PR also removes some tldraw specific state checks and creates new
component overrides to allow us to include them in tldraw/tldraw.
### Change Type
- [x] `major` — Breaking change
### Test Plan
- [x] Unit Tests
- [x] End to end tests
### Release Notes
- [tldraw] rename `useReadonly` to `useReadOnly`
- [editor] remove `Editor.isDarkMode`
- [editor] remove `Editor.isChangingStyle`
- [editor] remove `Editor.isCoarsePointer`
- [editor] remove `Editor.isDarkMode`
- [editor] remove `Editor.isFocused`
- [editor] remove `Editor.isGridMode`
- [editor] remove `Editor.isPenMode`
- [editor] remove `Editor.isReadOnly`
- [editor] remove `Editor.isSnapMode`
- [editor] remove `Editor.isToolLocked`
- [editor] remove `Editor.locale`
- [editor] rename `Editor.pageState` to `Editor.currentPageState`
- [editor] add `Editor.pageStates`
- [editor] add `Editor.setErasingIds`
- [editor] add `Editor.setEditingId`
- [editor] add several new component overrides
Escape the eraser tool on pressing the escape key.
(note that the same bug exists for the laser tool, i'm not sure if the
escape key behaviour should be the same for it too)
![licecap-output](https://github.com/tldraw/tldraw/assets/5616556/14bcb1f3-325c-4d28-ad39-a6a7205bd011)
Fixes#1731
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Select eraser tool
2. Press [escape], you should be back in the select tool
3. Select eraser tool, and start dragging around and press [escape], the
behaviour should be same as before
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- escape eraser tool on escape
---------
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
This PR fixes the issue where the arrow label was black in dark mode
instead of white.
light mode (normal):
<img width="600" alt="Screenshot 2023-07-12 at 00 21 35"
src="https://github.com/tldraw/tldraw/assets/5616556/2ac5e951-7777-4e96-9dde-a410a754aa01">
dark mode (before):
<img width="600" alt="Screenshot 2023-07-12 at 00 21 52"
src="https://github.com/tldraw/tldraw/assets/5616556/c67c3309-2847-4499-b4ef-6ba686e1382e">
dark mode (after):
<img width="600" alt="Screenshot 2023-07-12 at 00 21 44"
src="https://github.com/tldraw/tldraw/assets/5616556/244987c0-4570-410b-8975-43db47b786fa">
Fixes#1716
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Add an arrow with label
2. Switch between dark and light mode and notice that the label color
adapts correctly
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- fixed arrow label dark mode color
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
This PR moves code between our packages so that:
- @tldraw/editor is a “core” library with the engine and canvas but no
shapes, tools, or other things
- @tldraw/tldraw contains everything particular to the experience we’ve
built for tldraw
At first look, this might seem like a step away from customization and
configuration, however I believe it greatly increases the configuration
potential of the @tldraw/editor while also providing a more accurate
reflection of what configuration options actually exist for
@tldraw/tldraw.
## Library changes
@tldraw/editor re-exports its dependencies and @tldraw/tldraw re-exports
@tldraw/editor.
- users of @tldraw/editor WITHOUT @tldraw/tldraw should almost always
only import things from @tldraw/editor.
- users of @tldraw/tldraw should almost always only import things from
@tldraw/tldraw.
- @tldraw/polyfills is merged into @tldraw/editor
- @tldraw/indices is merged into @tldraw/editor
- @tldraw/primitives is merged mostly into @tldraw/editor, partially
into @tldraw/tldraw
- @tldraw/file-format is merged into @tldraw/tldraw
- @tldraw/ui is merged into @tldraw/tldraw
Many (many) utils and other code is moved from the editor to tldraw. For
example, embeds now are entirely an feature of @tldraw/tldraw. The only
big chunk of code left in core is related to arrow handling.
## API Changes
The editor can now be used without tldraw's assets. We load them in
@tldraw/tldraw instead, so feel free to use whatever fonts or images or
whatever that you like with the editor.
All tools and shapes (except for the `Group` shape) are moved to
@tldraw/tldraw. This includes the `select` tool.
You should use the editor with at least one tool, however, so you now
also need to send in an `initialState` prop to the Editor /
<TldrawEditor> component indicating which state the editor should begin
in.
The `components` prop now also accepts `SelectionForeground`.
The complex selection component that we use for tldraw is moved to
@tldraw/tldraw. The default component is quite basic but can easily be
replaced via the `components` prop. We pass down our tldraw-flavored
SelectionFg via `components`.
Likewise with the `Scribble` component: the `DefaultScribble` no longer
uses our freehand tech and is a simple path instead. We pass down the
tldraw-flavored scribble via `components`.
The `ExternalContentManager` (`Editor.externalContentManager`) is
removed and replaced with a mapping of types to handlers.
- Register new content handlers with
`Editor.registerExternalContentHandler`.
- Register new asset creation handlers (for files and URLs) with
`Editor.registerExternalAssetHandler`
### Change Type
- [x] `major` — Breaking change
### Test Plan
- [x] Unit Tests
- [x] End to end tests
### Release Notes
- [@tldraw/editor] lots, wip
- [@tldraw/ui] gone, merged to tldraw/tldraw
- [@tldraw/polyfills] gone, merged to tldraw/editor
- [@tldraw/primitives] gone, merged to tldraw/editor / tldraw/tldraw
- [@tldraw/indices] gone, merged to tldraw/editor
- [@tldraw/file-format] gone, merged to tldraw/tldraw
---------
Co-authored-by: alex <alex@dytry.ch>
Fix cloud tool tooltip
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Add a step-by-step description of how to test your PR here.
2.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- Add a brief release note for your PR here.
This makes the bumps on the curvy parts more bumpy, and improves the way
inky clouds are drawn to make it less likely to produce double lines
that do not fully overlap.
<img width="1066" alt="image"
src="https://github.com/tldraw/tldraw/assets/1242537/6119c6e8-ceee-4cf6-b393-70efbbdd6373">
### Change Type
- [x] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [ ] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Add a step-by-step description of how to test your PR here.
2.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- Add a brief release note for your PR here.
![Kapture 2023-07-04 at 16 36
31](https://github.com/tldraw/tldraw/assets/1242537/bcb19959-ac66-46fa-92ea-50fe4692a96c)
### Change Type
- [x] `minor` — New feature
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Make some cloud shapes, try different sizes, colors, fills.
2. Export cloud shapes to images.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- Adds a cloud shape.
We'd like to make the @tldraw/editor layer more independent of specific
shapes. Unfortunately there are many places where shape types and
certain shape behavior is deeply embedded in the Editor. This PR begins
to refactor out dependencies between the editor library and shape utils.
It does this in two ways:
- removing shape utils from the arguments of `isShapeOfType`, replacing
with a generic
- removing shape utils from the arguments of `getShapeUtil`, replacing
with a generic
- moving custom arrow info cache out of the util and into the editor
class
- changing the a tool's `shapeType` to be a string instead of a shape
util
We're here trading type safety based on inferred types—"hey editor, give
me your instance of this shape util class"—for knowledge at the point of
call—"hey editor, give me a shape util class of this type; and trust me
it'll be an instance this shape util class". Likewise for shapes.
### A note on style
We haven't really established our conventions or style when it comes to
types, but I'm increasingly of the opinion that we should defer to the
point of call to narrow a type based on generics (keeping the types in
typescript land) rather than using arguments, which blur into JavaScript
land.
### Change Type
- [x] `major` — Breaking change
### Test Plan
- [x] Unit Tests
### Release Notes
- removes shape utils from the arguments of `isShapeOfType`, replacing
with a generic
- removes shape utils from the arguments of `getShapeUtil`, replacing
with a generic
- moves custom arrow info cache out of the util and into the editor
class
- changes the a tool's `shapeType` to be a string instead of a shape
util
🚨 Note 🚨
This PR has changed! See my [newer
comment](https://github.com/tldraw/tldraw/pull/1706#issuecomment-1623451709)
for what the PR does now.
This description is kept here to show the original intention of the PR.
---
This PR fixes the tsdocs formatting of `TldrawEditorProps`, so that they
appears on the docs site.
We have docs already written, but they weren't appearing. There are
probably others like this too.
![image](https://github.com/tldraw/tldraw/assets/15892272/8d8940b3-983f-48b3-9804-7ac88116ca9d)
### Change Type
- [x] `documentation` — Changes to the documentation only[^2]
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Navigate to `/gen/editor/TldrawEditorProps`
2. Make sure that that the parameters are listed out with descriptions.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- Docs: Fixed some missing docs for the TldrawEditor component.
This PR removes the `tool` parameter from the `defineShape` function.
It's an opinionated change that I think we should at the very least
consider.
## What's the context?
Currently, you can add **tools** (aka state nodes) to your state chart
in two different ways:
1. Passing them to the `<Tldraw>` component with the `tools` attribute.
2. As part of a shape definition's `tool` property, which you then pass
to the `<Tldraw>` component with the `shapes` attribute.
This is what (1) looks like:
```jsx
import { MyTool } from "./MyTool"
function Example() {
return <Tldraw tools={[MyTool]} />
}
```
This is what (2) looks like:
```jsx
import { MyTool } from "./MyTool"
import { MyShapeUtil, myShapeProps } from "./MyShape"
const MyShapeDefinition = defineShape("my-shape", {
util: MyShapeUtil,
props: myShapeProps,
tool: MyTool,
})
function Example() {
return <Tldraw shapes={[MyShapeDefinition]} />
}
```
Clearly, (1) is better for when you want to add *just a tool*, that
doesn't have an associated shape.
And (2) is better for when you want to add *both* a tool and an
associated shape.
## Why change it?
I think we should remove method (2). Because I think that it adds a few
complications.
#### Does it help?
I don't think that it helps to streamline the process of coupling shapes
and tools. You still need to remember to add your tool.
Seeing as `tool` is optional on the shape definition (rightly so), it
doesn't prompt you to do it.
#### What's easier to explain?
I think it's easier to just have to explain _one method_. It would take
longer to explain two methods, and it complicates the concepts involved.
Seeing as there's not a big benefit to one method over the other, the
added explanation wouldn't be a good trade-off.
#### What happens if I use both?
It's unclear to the user what would happen if they use both methods. Do
we know what the intended behaviour of this would be? I think this will
happen often.
```jsx
import { MyTool } from "./MyTool"
import { MyShapeUtil, myShapeProps } from "./MyShape"
const MyShapeDefinition = defineShape("my-shape", {
util: MyShapeUtil,
props: myShapeProps,
tool: MyTool,
})
function Example() {
return <Tldraw tools={[MyTool]} shapes={[MyShapeDefinition]} />
}
```
#### Does it fit my shape/tool?
Many shapes are coupled closely with one tool. But some shapes would
involve multiple tools. And some tools would involve multiple shapes.
For example, you might first add a tool and a shape that go nicely
together, so you use method (2). But two months later, you decide that
you want another tool to be able to make this shape too. Now you've
inserted your related tools in two different places, unless you
refactor.
Alternatively, you might want to add some more functionality to your
tool, so that it can make multiple types of shapes. Instead of
refactoring the existing shape, you want to create an entirely new
shape, to keep your new code separate. Should you add the `tool`
property to the new shape as well? What would happen if you did/didn't?
What happens if you later disable the original shape? Would you need to
move the `tool` property from there to the newer shape?
It would be a lot simpler to just have the tool in your list of tools,
instead of having them tangled up with shapes.
#### Plugins?
We've been considering moving towards some sort of 'plugins' system in
the future, that could collect together shapes, tools, and other stuff.
I think that a more complete concept of a 'plugin' would be the best
place to collect together shapes, and tools — not on the shape itself.
### Change Type
- [x] `major` — Breaking change
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Try using all of the app's tools, making sure they still work.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- [dev] Removed the `tool` property from `defineShape`
This PR:
- adds tests for shape reordering
- removes `Editor.getParentsMappedToChildren`
- removes `Editor.reorderShapes`
- moves reordering shapes code into its own file, outside of the editor
### Change Type
- [x] `major` — Breaking change (if you were using those APIs)
### Release Notes
- [api] removes `Editor.getParentsMappedToChildren`
- [api] removes `Editor.reorderShapes`
- [api] moves reordering shapes code into its own file, outside of the
editor
This PR removes the strict state checks for the brush and zoom brush. We
should consider making the canvas more controlled by what exists (e.g.
whether a `brush` exists) rather than depending on particular statechart
states.
### Change Type
- [x] `minor`
### Test Plan
1. Create a brush manually in the API.
2. The brush should be visible on the canvas.
### Release Notes
- [editor] remove `editor.isIn` state checks for displaying brush and
zoom brush.
Once we are done resizing (when inserting text) we now show the default
cursor.
Fixes#1699
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Select text tool
2. Insert a text shape by dragging to select it's size.
3. After you are done dragging the cursor should go back to the default
cursor.
### Release Notes
- Switch back to the default cursor after you are done inserting a new
text shape.
This PR fixes the editor sometimes incorrectly assuming that you're
using a coarse pointer in firefox. It's not a complete fix — it just
avoids some of the bigger issues with it. ie: It disables cursor chat.
To avoid the issue, we just assume that you have a fine pointer if
you're using firefox on desktop.
Eventually, we should do a more complete fix for this.
I QA'd this change on:
* Mac Firefox (no touch screen)
* Windows Firefox (touch screen)
* Android Firefox
### Change Type
- [x] `patch` — Bug fix
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Use firefox on desktop with a touch screen.
2. Check that you can still use cursor chat (when in a shared project).
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- Fixed firefox not being able to use cursor chat when using a touch
screen on desktop.
This PR fixes the tsdocs formatting on the TldrawUi component so that
they appear on the docs site. Very similar to
https://github.com/tldraw/tldraw/pull/1706
### Change Type
- [x] `documentation` — Changes to the documentation only[^2]
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Go to `/gen/ui/TldrawUiProps`
2. Make sure that there are descriptions for all parameters.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- Docs: Show some docs missing from TldrawUi component.
Disable the style panel button on mobile layouts when using the laser
tool.
Fixes#1702
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Use a mobile layout.
2. Select laser tool
3. Make sure you cannot click the style panel button - it should be
disabled.
### Release Notes
- Disable the styles panel button for laser tool on mobile.
Highlighter is autolocked, so we shouldn't show the lock icon
### Change Type
- [x] `patch` — Bug fix
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Add a step-by-step description of how to test your PR here.
2.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- We no longer show the tool lock option for highlighter - it didn't do
anything anyway
This PR fixes pen mode.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. On iPad, use the pencil to enter pen mode
2. Select the draw tool
3. touch the screen
- [x] Unit Tests (sort of)
### Release Notes
- [fix] pen mode
This PR adds some more nuance to collaborator cursors.
Rather than being timed out or not timed out, a collaborator can now be
`active`, `idle` or `inactive`.
We calculate this based on the difference between the time that has
elapsed since the user's last activity timestamp.
After 3 seconds of inactivity, they go `idle`.
After sixty seconds of inactivity, they are `inactive`.
After any activity, they become `active` again.
When a user is `active`, we always show their cursor.
When a user is `idle`, we hide their cursor if they're following us,
unless they're highlighted
When a user is `inactive`, we hide their cursor unless they're
highlighted.
### Change Type
- [x] `minor`
### Test Plan
1. Find a friend and experiment with inactive times
2. Join a room that includes an inactive cursors; they should be hidden
on load
3. Have people follow you; do their timeouts feel natural?
### Release Notes
- Improve cursor timeouts and hiding logic.
This PR fixes the shortcut for lock shapes, which may be blocked by
browser defaults. We now use Shift+L instead of Cmd+Shift+L. Closes
https://github.com/tldraw/tldraw/issues/1676.
### Change Type
- [x] `patch`
### Test Plan
1. Try the lock tool shortcuts.
- [x] End to end tests
### Release Notes
- [@tldraw/editor] Fix lock tool shortcut
This PR fixes some issues in our `useDocumentEvents`. It closes
https://github.com/tldraw/tldraw/issues/1667 (I think).
### Change Type
- [x] `patch`
### Release Notes
- [@tldraw/editor] Bug fixes on document events.
This PR adds `box-sizing: border-box` to the editor and its children.
### Change Type
- [x] `patch`
### Release Notes
- [@tldraw/editor] Add `box-sizing: border-box` to `tl-container`
This PR incorporates a crc method from
https://github.com/alexgorbatchev/crc into the library, removing a peer
dependency on `buffer`. This was causing build errors in apps that did
not include the buffer library. (Our codebase included buffer because of
vsce.)
### Change Type
- [x] `patch`
### Release Notes
- [@tldraw/editor] Remove peer dependency on buffer.
This PR adds the `ScribbleManager` to the exports from `@tldraw/editor`.
### Change Type
- [x] `minor` — New feature
### Release Notes
- [@tldraw/tldraw] Export `ScribbleManager`
We saw an issue on stackblitz where the `global` constant was causing a
conflict (possibly because that environment was injecting its own
`global`). Either way, perhaps `global` is a bit of a risky name—this PR
renames `global` to `tldrawStateGlobal`.
### Change Type
- [x] `patch`
This PR fixes shape rendering logic. Remember! memo's 2nd argument
returns "when should we NOT render" not "when should we render"
### Change Type
- [x] `patch`
### Test Plan
1. Use the draw tool
This PR adds a `meta` property to shapes and other records.
It adds it to:
- asset
- camera
- document
- instance
- instancePageState
- instancePresence
- page
- pointer
- rootShape
## Setting meta
This data can generally be added wherever you would normally update the
corresponding record.
An exception exists for shapes, which can be updated using a partial of
the `meta` in the same way that we update shapes with a partial of
`props`.
```ts
this.updateShapes([{
id: myShape.id,
type: "geo",
meta: {
nemesis: "steve",
special: true
}
])
```
## `Editor.getInitialMetaForShape`
The `Editor.getInitialMetaForShape` method is kind of a hack to set the
initial meta property for newly created shapes. You can set it
externally. Escape hatch!
### Change Type
- [x] `minor` — New feature
### Test Plan
todo
- [ ] Unit Tests (todo)
### Release Notes
- todo
This PR fixes an issue that I introduced where the `snapshot` argument
would be mutated by the `Store.migrateStoreSnapshot` method.
### Change Type
- [x] `patch`
### Release Notes
- [@tldraw/store] Fixed a bug that would cause
`Store.migrateStoreSnapshot` to mutate its `snapshot` argument.
This PR fixes a crash when rotating a deleted shapes, and adds a unit
test for it.
It also updates the docs of an editor method to communicate a current
limitation that we left a 'todo' for. See code comments for more info.
### Change Type
- [x] `patch` — Bug fix
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Get two devices out for this! (or write a little console script to do
it for you)
2. Rotate a shape on one device.
3. While rotating it, delete it on the other device.
4. Make sure the page doesn't crash!
- [x] Unit Tests
- [ ] End to end tests
### Release Notes
- Fixed a crash when trying to rotate a deleted shape.
This PR fixes an import in the custom shapes example. It also tweaks the
example to show how buttons and other interactive content should work.
### Change Type
- [x] `documentation`
This PR improves the types for the Store.
- renames `StoreSnapshot` to `SerializedStore`, which is the return type
of `Store.serialize`
- creates `StoreSnapshot` as a type for the return type of
`Store.getSnapshot` / the argument type for `Store.loadSnapshot`
- creates `TLStoreSnapshot` as the type used for the `TLStore`.
This came out of a session I had with a user. This should prevent
needing to import types from `@tldraw/store` directly.
### Change Type
- [x] `major` — Breaking change
### Test Plan
- [x] Unit Tests
### Release Notes
- [dev] Rename `StoreSnapshot` to `SerializedStore`
- [dev] Create new `StoreSnapshot` as type related to
`getSnapshot`/`loadSnapshot`
This PR fixes an issue (cough feature cough) where three touches would
exit pen mode.
### Change Type
- [x] `patch` — Bug fix
### Release Notes
- Removes three touches to cancel pen mode feature.
This PR fixes text shapes always being black.
It also fixes Note shapes not having the correct text colour.
<img width="759" alt="Screenshot 2023-06-26 at 11 26 45"
src="https://github.com/tldraw/tldraw/assets/15892272/a68ae0d1-69ba-43de-9e21-87c483ffd2dc">
### Change Type
- [x] `patch` — Bug fix
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Make a text shape.
2. Make sure you can change its colour.
3. Make a note shape.
4. Make sure its text label stays black when you change the note's
colour.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- None: Fixes an unreleased bug.
Adds some basic API docs for the new styles API.
### Change Type
- [x] `documentation` — Changes to the documentation only[^2]
### Test Plan
--
### Release Notes
--
---------
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
tldraw-zero themed follow-ups to the styles API added in #1580.
- Removed style related helpers from `ShapeUtil`
- `editor.css` no longer includes the tldraw default color palette.
Instead, a global `DefaultColorPalette` is defined as part of the color
style. If developers wish to cusomise the colors, they can mutate that
global.
- `ShapeUtil.toSvg` no longer takes font/color. Instead, it takes an
"svg export context" that can be used to add `<defs>` to the exported
SVG element. Converting e.g. fonts to inlined data urls is now the
responsibility of the shapes that use them rather than the Editor.
- `usePattern` is not longer a core part of the editor. Instead,
`ShapeUtil` has a `getCanvasSvgDefs` method for returning react
components representing anything a shape needs included in `<defs>` for
the canvas.
- The shape-specific cleanup logic in `setStyle` has been deleted. It
turned out that none of that logic has been running anyway, and instead
the relevant logic lives in shape `onBeforeChange` callbacks already.
### Change Type
- [x] `minor` — New feature
### Test Plan
- [x] Unit Tests
- [x] End to end tests
### Release Notes
--
---------
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
This PR fixes a bug where our custom SVG cursors were not being used,
causing cursor chat to look worse on Windows.
It was the result of a dodgy merge!
### Change Type
- [x] `patch` — Bug fix
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
To test this, you might need to change your OS cursor to something
different to usual. I set mine to off-black so that I can test this sort
of thing.
1. Make sure that your cursor is our custom black cursor when using the
app.
- [ ] Unit Tests
- [ ] End to end tests
### Release Notes
- None: Fixing an unreleased bug.
This PR fixes a few components that were updating too often. It changes
the format of our error boundaries in order to avoid re-rendering them
as changed props.
### Change Type
- [x] `major` — Breaking change
It tried to get out but we're dragging it back in.
This PR brings [signia](https://github.com/tldraw/signia) back into
tldraw as @tldraw/state.
### Change Type
- [x] major
---------
Co-authored-by: David Sheldrick <d.j.sheldrick@gmail.com>
This PR improves the ergonomics of `ShapeUtil` classes.
### Cached methods
First, I've remove the cached methods (such as `bounds`) from the
`ShapeUtil` class and lifted this to the `Editor` class.
Previously, calling `ShapeUtil.getBounds` would return the un-cached
bounds of a shape, while calling `ShapeUtil.bounds` would return the
cached bounds of a shape. We also had `Editor.getBounds`, which would
call `ShapeUtil.bounds`. It was confusing. The cached methods like
`outline` were also marked with "please don't override", which suggested
the architecture was just wrong.
The only weirdness from this is that utils sometimes reach out to the
editor for cached versions of data rather than calling their own cached
methods. It's still an easier story to tell than what we had before.
### More defaults
We now have three and only three `abstract` methods for a `ShapeUtil`:
- `getDefaultProps` (renamed from `defaultProps`)
- `getBounds`,
- `component`
- `indicator`
Previously, we also had `getCenter` as an abstract method, though this
was usually just the middle of the bounds anyway.
### Editing bounds
This PR removes the concept of editingBounds. The viewport will no
longer animate to editing shapes.
### Active area manager
This PR also removes the active area manager, which was not being used
in the way we expected it to be.
### Dpr manager
This PR removes the dpr manager and uses a hook instead to update it
from React. This is one less runtime browser dependency in the app, one
less thing to document.
### Moving things around
This PR also continues to try to organize related methods and properties
in the editor.
### Change Type
- [x] `major` — Breaking change
### Release Notes
- [editor] renames `defaultProps` to `getDefaultProps`
- [editor] removes `outline`, `outlineSegments`, `handles`, `bounds`
- [editor] renames `renderBackground` to `backgroundComponent`
This reverts commit b6716a3750.
Not sure why, but this introduced a `/// <references />` comment in the
tldraw/tldraw api-report.md file that doesn't show up when you build
from brivate. Reverting for now.
### Change Type
- [x] `dependencies` — Changes to package dependencies[^1]
### Test Plan
-
### Release Notes
-
This PR removes the `onDropOverride` prop from the canvas, which was a
bit of a hack.
### Change Type
- [x] `major` — Breaking change
### Release Notes
- [editor] Remove `onDropOverride`
This PR changes `resizeBox` to be a regular function rather than an
arrow function.
### Change Type
- [x] `minor` — New feature
### Release Notes
- [editor] Change `resizeBox` to be a regular function.
This PR introduces `@tldraw/tldraw/tldraw.css`, an exported CSS file
that replaces the `editor.css` and `ui.css` that were previously copied
from the editor and ui packages. Instead, these files are combined into
the `tldraw.css` file, simplifying the import story when using
`@tldraw/tldraw`.
### Change Type
- [x] `major` — Breaking change
### Release Notes
- [tldraw] Removes `editor.css` and `ui.css` exports, replaces with
`tldraw.css`
This PR:
- updates the yjs example to include user presence
- tweaks the `createPresenceStateDerivation` API
- fix a "double update" bug caused by re-syncing local changes
- fix connection bugs
### Change Type
- [x] `minor` — New feature
This PR restores camera culling behavior and includes a 500ms forced
render while the camera is moving to prevent weird long pan behavior.
It:
- removes `CameraManager`
- adds `cameraState` to editor
### Change Type
- [x] `major` — Breaking change
### Release Notes
- [editor] Adds `Editor.cameraState`
- Adds smart culling to make panning and zooming more smooth
This PR is intended to do some housecleaning ahead of our developer
release.
It:
- co-locates code in the `Editor` class, i.e. moving shape-related
methods next to other shape-related methods
- renames `cullingBounds` and other culling-related names to
`renderingBounds`
- renames `Editor.getParentPageId` to `Editor.getAncestorPageId`
- renames `Editor.shapeIds` to `Editor.currentPageShapeIds`
### Change Type
- [x] `major` — api changes
Removes `propsForNextShape` and replaces it with the new styles API.
Changes in here:
- New custom style example
- `setProp` is now `setStyle` and takes a `StyleProp` instead of a
string
- `Editor.props` and `Editor.opacity` are now `Editor.sharedStyles` and
`Editor.sharedOpacity`
- They return an object that flags mixed vs shared types instead of
using null to signal mixed types
- `Editor.styles` returns a `SharedStyleMap` - keyed on `StyleProp`
instead of `string`
- `StateNode.shapeType` is now the shape util rather than just a string.
This lets us pull the styles from the shape type directly.
- `color` is no longer a core part of the editor set on the shape
parent. Individual child shapes have to use color directly.
- `propsForNextShape` is now `stylesForNextShape`
- `InstanceRecordType` is created at runtime in the same way
`ShapeRecordType` is. This is so it can pull style validators out of
shape defs for `stylesForNextShape`
- Shape type are now defined by their props rather than having separate
validators & type defs
### Change Type
- [x] `major` — Breaking change
### Test Plan
1. Big time regression testing around styles!
2. Check UI works as intended for all shape/style/tool combos
- [x] Unit Tests
- [ ] End to end tests
### Release Notes
-
---------
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
This PR adds a timeout to collaborator cursors.
It's part 1 of two PRs. The second one is smaller:
https://github.com/tldraw/brivate/pull/2053
# What is this?
After three seconds of inactivity, collaborator cursors disappear.
![2023-06-08 at 10 42 43 - Moccasin
Flamingo](https://github.com/tldraw/tldraw/assets/15892272/93e463aa-0329-4ecb-ada1-4c38b36a655b)
If you're following someone, you can always see their cursor.
![2023-06-08 at 10 45 42 - Olive
Crayfish](https://github.com/tldraw/tldraw/assets/15892272/11e8d85a-18a8-4976-85c5-d14f3841c296)
# Is there anything else?
The PR also adds support for the brivate PR:
https://github.com/tldraw/brivate/pull/2053
# Admin
### Change Type
- [x] `minor` — New Feature
### Test Plan
You probably need to test this locally, as we don't do multiplayer
previews on this repo yet.
1. Open the same shared project in two browser sessions.
2. Move around the cursor in one session, while able to see it from the
other.
3. Stop moving the cursor.
4. Make sure that the cursor disappears on the other session after 3
seconds.
5. Move the cursor again, and make sure it reappears it.
6. Make sure that viewport-following the user makes the cursor show
permanently.
### Release Notes
- Brought back cursor timeouts. Collaborator cursors now disappear after
3 seconds of inactivity.
---------
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
This PR adds support for seeing **another user**'s chat messages.
It's part 1 of two PRs relating to Cursor Chat.
And it's needed for the much bigger part 2:
https://github.com/tldraw/brivate/pull/1981
# Presence
You can see another person's chat messages!
![2023-06-02 at 17 42 33 - Blush
Capybara](https://github.com/tldraw/tldraw/assets/15892272/8f3efb5f-9c05-459c-aa7e-24842be75e58)
If they have a name, it gets popped on top.
![2023-06-02 at 17 45 34 - Sapphire
Meerkat](https://github.com/tldraw/tldraw/assets/15892272/749bd924-c1f5-419b-a028-1fafe1b61292)
That's it!
With this PR, there's no way of actually *typing* your chat messages.
That comes with the [next
one](https://github.com/tldraw/brivate/pull/1981)!
# Admin
### To-do
- [x] Store chat message
- [x] Allow overflowing chat
- [x] Presence for chat message
- [x] Display chat message to others
### Change Type
- [x] `minor` — New Feature
### Test Plan
To test this, I recommend checking out both `lu/cursor-chat` branches,
and opening two browser sessions in the same shared project.
1. In one session, type some cursor chat by pressing the Enter key while
on the canvas (and typing).
2. On the other session, check that you can see the chat message appear.
3. Repeat this while being both named, and unnamed.
I recommend just focusing on the visible presense in this PR.
The [other PR](https://github.com/tldraw/brivate/pull/1981) is where we
can focus about how we _input_ the cursor chat.
### Release Notes
- [dev] Added support for cursor chat presence.
---------
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
This PR adds shape type checks that use the shape util, e.g.
`this.editor.isShapeOfType(shape, FrameShapeUtil)`. In part this is
designed to help us track down where dependencies exist between the
editor and our default shapes.
### Change Type
- [x] `internal` — Any other changes that don't affect the published
package
This PR is a refactor / tidy up of some snapping logic.
- Fix a bug where the recursive call to `findAdjacentGaps` could lead to
a maximum call stack error
- Fixed an issue that caused handle snapping to expensively recompute
- Fixed a dependency from the snap manager to the line shape
### Change Type
- [x] `patch`
### Test Plan
Our snap tests are pretty thorough, they should work here.
### Release Notes
- [editor] fix bug in snapping
Removes the cached (but not really needed) local transform for shapes.
We almost never get the local transform except when getting the page
transform.
### Change Type
- [x] `major` — Breaking change
### Release Notes
- [editor] Remove `ShapeUtil.transform`
We load the user preferences a bit earlier, so that we can make sure
that the `LoadingScreen` and `ErrorScreen` also use the correct color
and background color based on the dark mode setting.
There's still a brief flash of white screen, but that's before any of
our components load, not sure if we can avoid that one.
Solves https://github.com/tldraw/tldraw/issues/1248
### Change Type
- [x] `patch` — Bug Fix
### Test Plan
1. Probably best if you throttle your network speed.
2. Reload the page.
3. The asset loading screen should use take your dark mode setting into
account.
4. Change the dark mode and try again.
### Release Notes
- Make sure our loading and error screens take dark mode setting into
account.
---------
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
This PR tries to move some remaining kbds into actions and tools, which
allows them to be overwritten in actions or tools if developer wishes
so. It also modifies `getHotkeysStringFromKbd` to support multiple
`kbds` per action and parses them into proper hotkeys.
Right now, these kbds cannot be removed without reimplementing
`useKeyboardShortcuts` entirely.
### Change Type
- [ ] `patch` — Bug fix
- [ ] `minor` — New feature
- [ ] `major` — Breaking change
- [ ] `dependencies` — Changes to package dependencies[^1]
- [ ] `documentation` — Changes to the documentation only[^2]
- [ ] `tests` — Changes to any test code only[^2]
- [x] `internal` — Any other changes that don't affect the published
package[^2]
- [ ] I don't know
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
Should not affect existing kbds behavior as it just moves them into
actions or tools.
---------
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
This PR updates exports related to user presence, in order to enable
external sync solutions that use user presence.
### Change Type
- [x] `patch` — Bug fix
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
This PR removes the default SVG export for groups.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
1. Create a group
2. Export it to SVG
### Release Notes
- Fix image exports for groups
This PR does a first-pass of adding tsdocs to the methods of the Editor
class.
It's a minimal start — just descriptions of them, and their parameters.
It makes the Editor docs page a lot more fleshed out though, and easier
to quickly scan.
There's still a lot more to do!
### Change Type
- [x] `documentation` — Changes to the documentation only[^2]
### Release Notes
- [dev] Added initial documentation for the Editor class.
---------
Co-authored-by: Steve Ruiz <steveruizok@gmail.com>
This PR adds a generic that we can use with `updateShapes` and
`createShapes` in order to type the partials being passed into those
methods. By default, the partials are typed as `TLUnknownShape`, which
accepts any props.
### Change Type
- [x] `minor` — New feature
### Test Plan
- [x] Unit Tests
### Release Notes
- [editor] adds an optional shape generic to `updateShapes` and
`createShapes`
This PR fixes embeds to remove the `doesResize` prop when creating
embeds / converting between bookmarks and embeds.
### Change Type
- [x] `patch` — Bug fix
[^1]: publishes a `patch` release, for devDependencies use `internal`
[^2]: will not publish a new version
### Test Plan
1. Create an embed
2. Convert between bookmark and embed
This PR does some cleanup around our Embed Shape.
It:
- removes used `doesResize` and `overridePermissions` props
- removes the no-longer-needed `tmpOldUrl` prop
- adds a `canUnmount` property to embed definitions, so that some embeds
can unmount when desired
### Change Type
- [x] `patch` — Bug Fix
### Test Plan
1. Create embed shapes
2. Migrate old data that includes embed shapes?
- [x] Unit Tests
### Release Notes
- [editor] Remove unused props for `TLEditorShape`
- [editor] Adds `canUnmount` property to embed definitions
Move the preloading of assets to `TldrawEditorWithReadyStore` which
makes it sure that all codepaths preload assets. Before that didn't
happen for cases where we passed in an existing store - snapshots.
### Change Type
- [x] `patch` — Bug Fix
### Release notes
- Fix a problem where assets were not loading in some cases (snapshots).
This PR extracts some logic from the EditUrlDialog into the bookmark
shape util, removing the dependency between the two.
### Change Type
- [x] `internal` — Any other changes that don't affect the published
package (will not publish a new version)
### Test Plan
1. Create a bookmark shape
2. Set its URL to an empty string
- [x] Unit Tests
This diff adds a new property to `defineShape`: `tool`.
The tool prop allows shapes to bring a tool along with them as part of
their definition. E.g. the draw shape isn't much use without the draw
tool, so adding the draw shape to your app gives you the draw tool tool.
As part of this, i renamed the `shapeutils` folder to just `shapes`, and
moved a bunch of shape-specific tools from the tools folder into the
shapes folder. This more closely reflects how things will be once we
move our default shapes out of core for tldraw-zero.
### Change Type
- [x] `patch` — Bug fix
### Test Plan
Tested locally
### Release Notes
n/a
In my app, I have a sidebar and noticed that dropped shapes were being
created at an offset by the sidebar's width. This is because the current
point given to `putExternalContent` does not offset by the editor's
client rect.
Based on #1549, but with a lot of code-structure related changes backed
out. Shape schemas are still defined in tlschemas with this diff.
Couple differences between this and #1549:
- This tightens up the relationship between store schemas and editor
schemas a bit
- Reduces the number of places we need to remember to include core
shapes
- Only `<TLdrawEditor />` sets default shapes by default. If you're
doing something funky with lower-level APIs, you need to specify
`defaultShapes` manually
- Replaces `validator` with `props` for shapes
### Change Type
- [x] `major` — Breaking Change
### Test Plan
1. Add a step-by-step description of how to test your PR here.
2.
- [x] Unit Tests
- [ ] Webdriver tests
### Release Notes
[dev-facing, notes to come]