diff --git a/src/folk-shape.ts b/src/folk-shape.ts index f129fa9..6e3f010 100644 --- a/src/folk-shape.ts +++ b/src/folk-shape.ts @@ -1,3 +1,4 @@ +import { css, html } from './common/tags'; import { ResizeObserverManager } from './resize-observer'; const resizeObserver = new ResizeObserverManager(); @@ -31,112 +32,117 @@ export class RotateEvent extends CustomEvent { export type Dimension = number | 'auto'; const styles = new CSSStyleSheet(); -styles.replaceSync(` -:host { - display: block; - position: absolute; - cursor: var(--fc-move, move); - box-sizing: border-box; -} +styles.replaceSync(css` + :host { + display: block; + position: absolute; + cursor: var(--fc-move, move); + box-sizing: border-box; + } -:host::before { - content: ''; - position: absolute; - inset: -15px -15px -15px -15px; - z-index: -1; -} + :host::before { + content: ''; + position: absolute; + inset: -15px -15px -15px -15px; + z-index: -1; + } -div { - height: 100%; - width: 100%; - overflow: hidden; - cursor: default; -} + div { + height: 100%; + width: 100%; + overflow: hidden; + cursor: default; + } -:host(:focus-within) { - z-index: calc(infinity - 1); - outline: solid 1px hsl(214, 84%, 56%); -} + :host(:focus-within) { + z-index: calc(infinity - 1); + outline: solid 1px hsl(214, 84%, 56%); + } -:host(:hover) { - outline: solid 2px hsl(214, 84%, 56%); -} + :host(:hover) { + outline: solid 2px hsl(214, 84%, 56%); + } -:host(:state(move)), -:host(:state(rotate)), -:host(:state(resize-nw)), -:host(:state(resize-ne)), -:host(:state(resize-se)), -:host(:state(resize-sw)), { - user-select: none; -} + :host(:state(move)), + :host(:state(rotate)), + :host(:state(resize-nw)), + :host(:state(resize-ne)), + :host(:state(resize-se)), + :host(:state(resize-sw)) { + user-select: none; + } -[part="resize-nw"], -[part="resize-ne"], -[part="resize-se"], -[part="resize-sw"] { - display: block; - position: absolute; - box-sizing: border-box; - padding: 0; - background: hsl(210, 20%, 98%); - z-index: calc(infinity); - width: 13px; - aspect-ratio: 1; - transform: translate(-50%, -50%); - border: 1.5px solid hsl(214, 84%, 56%); - border-radius: 2px; -} + [part='resize-nw'], + [part='resize-ne'], + [part='resize-se'], + [part='resize-sw'] { + display: block; + position: absolute; + box-sizing: border-box; + padding: 0; + background: hsl(210, 20%, 98%); + z-index: calc(infinity); + width: 13px; + aspect-ratio: 1; + transform: translate(-50%, -50%); + border: 1.5px solid hsl(214, 84%, 56%); + border-radius: 2px; + } -[part="resize-nw"] { - top: 0; - left: 0; -} - -[part="resize-ne"] { - top: 0; - left: 100%; -} - -[part="resize-se"] { - top: 100%; - left: 100%; -} - -[part="resize-sw"] { - top: 100%; - left: 0; -} + [part='resize-nw'] { + top: 0; + left: 0; + } -[part="resize-nw"], [part="resize-se"] { - cursor: var(--fc-nwse-resize, nwse-resize) -} - -[part="resize-ne"], [part="resize-sw"] { - cursor: var(--fc-nesw-resize, nesw-resize) -} + [part='resize-ne'] { + top: 0; + left: 100%; + } -[part="rotate"] { - z-index: calc(infinity); - display: block; - position: absolute; - box-sizing: border-box; - padding: 0; - border: 1.5px solid hsl(214, 84%, 56%); - border-radius: 50%; - background: hsl(210, 20%, 98%); - width: 13px; - aspect-ratio: 1; - top: 0; - left: 50%; - translate: -50% -150%; - cursor: url("data:image/svg+xml,") 16 16, pointer; -} + [part='resize-se'] { + top: 100%; + left: 100%; + } -:host(:not(:focus-within)) [part^="resize"], :host(:not(:focus-within)) [part="rotate"] { - opacity: 0; - cursor: default; -} + [part='resize-sw'] { + top: 100%; + left: 0; + } + + [part='resize-nw'], + [part='resize-se'] { + cursor: var(--fc-nwse-resize, nwse-resize); + } + + [part='resize-ne'], + [part='resize-sw'] { + cursor: var(--fc-nesw-resize, nesw-resize); + } + + [part='rotate'] { + z-index: calc(infinity); + display: block; + position: absolute; + box-sizing: border-box; + padding: 0; + border: 1.5px solid hsl(214, 84%, 56%); + border-radius: 50%; + background: hsl(210, 20%, 98%); + width: 13px; + aspect-ratio: 1; + top: 0; + left: 50%; + translate: -50% -150%; + cursor: url("data:image/svg+xml,") + 16 16, + pointer; + } + + :host(:not(:focus-within)) [part^='resize'], + :host(:not(:focus-within)) [part='rotate'] { + opacity: 0; + cursor: default; + } `); declare global { @@ -258,13 +264,12 @@ export class FolkShape extends HTMLElement { // Ideally we would creating these lazily on first focus, but the resize handlers need to be around for delegate focus to work. // Maybe can add the first resize handler here, and lazily instantiate the rest when needed? // I can see it becoming important at scale - shadowRoot.innerHTML = ` - - - - - -
`; + shadowRoot.innerHTML = html` + + + + +
`; this.height = Number(this.getAttribute('height')) || 'auto'; this.width = Number(this.getAttribute('width')) || 'auto'; @@ -286,9 +291,7 @@ export class FolkShape extends HTMLElement { top: y, right: x + width, bottom: y + height, - toJSON() { - return this; - }, + toJSON: undefined as any, }; // return DOMRectReadOnly.fromRect({ x: this.x, y: this.y, width: this.width, height: this.height }); }