first thing that kinda works

This commit is contained in:
Orion Reed 2024-12-19 18:40:38 -05:00
parent e036e9859f
commit 9bbc37c729
4 changed files with 120 additions and 0 deletions

View File

@ -477,6 +477,7 @@ export class FolkShape extends HTMLElement {
#dispatchTransformEvent() {
const emmittedRect = new DOMRectTransform(this.#rect);
console.log('emit X', this.#rect.x);
const event = new TransformEvent(emmittedRect, this.#previousRect);
this.dispatchEvent(event);
@ -496,6 +497,7 @@ export class FolkShape extends HTMLElement {
emmittedRect.rotation = this.#previousRect.rotation;
}
console.log('applied X', emmittedRect.x);
this.style.transform = emmittedRect.toCssString();
this.style.width = this.#attrWidth === 'auto' ? '' : `${emmittedRect.width}px`;
this.style.height = this.#attrHeight === 'auto' ? '' : `${emmittedRect.height}px`;

70
labs/simple-space.ts Normal file
View File

@ -0,0 +1,70 @@
import { FolkElement } from '@lib';
import { html } from '@lib/tags';
import { TransformEvent } from '@lib/TransformEvent';
import { css } from '@lit/reactive-element';
export class SimpleSpace extends FolkElement {
static override tagName = 'simple-space';
static styles = css`
:host {
display: block;
// perspective: 1000px;
position: relative;
width: 100%;
height: 100%;
}
.space {
position: absolute;
width: 100%;
height: 100%;
transform-style: preserve-3d;
transform-origin: center;
backface-visibility: hidden;
}
`;
#matrix = new DOMMatrix();
override createRenderRoot() {
const root = super.createRenderRoot() as ShadowRoot;
root.setHTMLUnsafe(html`
<div class="space" style="transform: ${this.#matrix}">
<slot></slot>
</div>
`);
// Listen for transform events from shapes
this.addEventListener('transform', this.#handleTransform);
return root;
}
rotate(angle: number = 45) {
this.#matrix = new DOMMatrix().rotateAxisAngle(1, 0, 0, angle);
const space = this.shadowRoot?.querySelector('.space');
if (space instanceof HTMLElement) {
space.style.transform = this.#matrix.toString();
}
}
#handleTransform = (event: TransformEvent) => {
// Extract rotation angles from the transformation matrix
const rotationX = Math.atan2(this.#matrix.m32, this.#matrix.m33);
const rotationY = Math.atan2(
-this.#matrix.m31,
Math.sqrt(this.#matrix.m32 * this.#matrix.m32 + this.#matrix.m33 * this.#matrix.m33),
);
// Calculate projection factors for both axes
const projectionFactorY = 1 / Math.cos(rotationX);
const projectionFactorX = 1 / Math.cos(rotationY);
// Apply the transformed movement with both projection factors
event.current.x *= projectionFactorX;
event.current.y *= projectionFactorY;
};
}

View File

@ -0,0 +1,5 @@
import { SimpleSpace } from '../simple-space';
SimpleSpace.define();
export { SimpleSpace };

View File

@ -0,0 +1,43 @@
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>Simple Space Demo</title>
<style>
html,
body {
margin: 0;
height: 100%;
}
simple-space {
width: 100%;
height: 100%;
}
folk-shape {
background: rgb(134, 37, 37);
border: 1px solid rgba(0, 0, 0, 0.5);
}
</style>
</head>
<body>
<simple-space id="space">
<folk-shape x="250" y="100" width="50" height="50"></folk-shape>
<folk-shape x="200" y="200" width="75" height="75" rotation="90"></folk-shape>
<folk-shape x="50" y="250" width="25" height="25" rotation="180"></folk-shape>
<folk-shape x="350" y="50" width="100" height="100" rotation="270"></folk-shape>
<folk-shape x="500" y="500" width="150" height="150" rotation="360"></folk-shape>
</simple-space>
<script type="module">
import '@labs/standalone/simple-space.ts';
import '@labs/standalone/folk-shape.ts';
const space = document.getElementById('space');
document.addEventListener('click', () => {
// Random rotation between 30 and 75 degrees
const randomRotation = Math.random() * 45 + 30;
space.rotate(randomRotation);
});
</script>
</body>
</html>