@infinite-canvas-tutorial/webcomponents
Version:
WebComponents UI implementation
216 lines (212 loc) • 10.7 kB
JavaScript
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
};
var _InfiniteCanvas_appStateProvider, _InfiniteCanvas_nodesProvider, _InfiniteCanvas_apiProvider;
import { html, css, LitElement } from 'lit';
import { Task } from '@lit/task';
import { ContextProvider } from '@lit/context';
import { customElement, property } from 'lit/decorators.js';
import { apiContext, appStateContext, getDefaultAppState, nodesContext, } from '../context';
import { Event } from '../event';
import { checkWebGPUSupport } from '../utils';
import { pendingCanvases } from '../API';
import '@spectrum-web-components/theme/sp-theme.js';
import '@spectrum-web-components/theme/src/themes.js';
// import '@spectrum-web-components/accordion/sp-accordion.js';
// import '@spectrum-web-components/accordion/sp-accordion-item.js';
import '@spectrum-web-components/action-group/sp-action-group.js';
import '@spectrum-web-components/action-menu/sp-action-menu.js';
import '@spectrum-web-components/alert-banner/sp-alert-banner.js';
import '@spectrum-web-components/menu/sp-menu-item.js';
import '@spectrum-web-components/menu/sp-menu-divider.js';
import '@spectrum-web-components/progress-circle/sp-progress-circle.js';
import '@spectrum-web-components/textfield/sp-textfield.js';
import '@spectrum-web-components/thumbnail/sp-thumbnail.js';
import '@spectrum-web-components/tooltip/sp-tooltip.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-text.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-visibility.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-visibility-off.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-properties.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-close.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-chevron-down.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-layers.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-properties.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-show-menu.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-hand.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-select.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-shapes.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-undo.js';
import '@spectrum-web-components/icons-workflow/icons/sp-icon-redo.js';
const TOP_NAVBAR_HEIGHT = 48;
let InfiniteCanvas = class InfiniteCanvas extends LitElement {
constructor() {
super(...arguments);
this.renderer = 'webgl';
this.shaderCompilerPath = 'https://unpkg.com/@antv/g-device-api@1.6.8/dist/pkg/glsl_wgsl_compiler_bg.wasm';
this.appState = getDefaultAppState();
this.nodes = [];
_InfiniteCanvas_appStateProvider.set(this, new ContextProvider(this, { context: appStateContext }));
_InfiniteCanvas_nodesProvider.set(this, new ContextProvider(this, { context: nodesContext }));
_InfiniteCanvas_apiProvider.set(this, new ContextProvider(this, { context: apiContext }));
this.initCanvas = new Task(this, {
task: (_a) => __awaiter(this, [_a], void 0, function* ([renderer, shaderCompilerPath]) {
if (renderer === 'webgpu') {
yield checkWebGPUSupport();
}
__classPrivateFieldGet(this, _InfiniteCanvas_appStateProvider, "f").setValue(this.appState);
/**
* Update context values
*/
this.addEventListener(Event.READY, (e) => {
e.detail.getAppState = () => __classPrivateFieldGet(this, _InfiniteCanvas_appStateProvider, "f").value;
e.detail.setAppState = (appState) => __classPrivateFieldGet(this, _InfiniteCanvas_appStateProvider, "f").setValue(appState);
e.detail.getNodes = () => __classPrivateFieldGet(this, _InfiniteCanvas_nodesProvider, "f").value;
e.detail.setNodes = (nodes) => __classPrivateFieldGet(this, _InfiniteCanvas_nodesProvider, "f").setValue(nodes);
__classPrivateFieldGet(this, _InfiniteCanvas_apiProvider, "f").setValue(e.detail);
});
this.addEventListener(Event.ZOOM_CHANGED, (e) => {
__classPrivateFieldGet(this, _InfiniteCanvas_appStateProvider, "f").setValue(Object.assign(Object.assign({}, __classPrivateFieldGet(this, _InfiniteCanvas_appStateProvider, "f").value), { cameraZoom: e.detail.zoom }));
});
const $canvas = document.createElement('canvas');
$canvas.style.width = '100%';
$canvas.style.height = 'calc(100% - 48px)';
const { width, height } = this.getBoundingClientRect();
const { cameraZoom } = this.appState;
pendingCanvases.push({
container: this,
canvas: {
element: $canvas,
width,
height: height - TOP_NAVBAR_HEIGHT,
devicePixelRatio: window.devicePixelRatio,
renderer,
shaderCompilerPath,
},
camera: {
zoom: cameraZoom,
},
});
return $canvas;
}),
args: () => [this.renderer, this.shaderCompilerPath],
});
}
connectedCallback() {
super.connectedCallback();
this.resizeObserver = new ResizeObserver((entries) => this.handleResize(entries));
this.updateComplete.then(() => this.resizeObserver.observe(this));
}
disconnectedCallback() {
var _a, _b;
super.disconnectedCallback();
(_a = this.resizeObserver) === null || _a === void 0 ? void 0 : _a.unobserve(this);
(_b = __classPrivateFieldGet(this, _InfiniteCanvas_apiProvider, "f").value) === null || _b === void 0 ? void 0 : _b.destroy();
}
handleResize(entries) {
var _a, _b;
const { width, height } = entries[0].contentRect;
const dpr = window.devicePixelRatio;
if (width && height) {
const $canvas = (_a = this.shadowRoot) === null || _a === void 0 ? void 0 : _a.querySelector('canvas');
$canvas.width = width * dpr;
$canvas.height = (height - TOP_NAVBAR_HEIGHT) * dpr;
(_b = __classPrivateFieldGet(this, _InfiniteCanvas_apiProvider, "f").value) === null || _b === void 0 ? void 0 : _b.resizeCanvas(width, height - TOP_NAVBAR_HEIGHT);
}
}
render() {
const themeWrapper = (content) => html `<sp-theme
system="spectrum"
color="${this.appState.theme.mode}"
scale="medium"
>${typeof content === 'string' ? html `${content}` : content}</sp-theme
>`;
return this.initCanvas.render({
pending: () => themeWrapper(html `<sp-progress-circle
label="A small representation of an unclear amount of work"
indeterminate
size="s"
></sp-progress-circle>`),
complete: ($canvas) => themeWrapper(html `<ic-spectrum-top-navbar></ic-spectrum-top-navbar>
<ic-spectrum-penbar></ic-spectrum-penbar>
<ic-spectrum-taskbar></ic-spectrum-taskbar>
<ic-spectrum-layers-panel></ic-spectrum-layers-panel>
${$canvas}`),
error: (e) => {
console.error(e);
return themeWrapper(html `<sp-alert-banner open variant="negative">
Initialize canvas failed<br />
<strong></strong><br />
${e.message}
</sp-alert-banner>`);
},
});
}
};
_InfiniteCanvas_appStateProvider = new WeakMap();
_InfiniteCanvas_nodesProvider = new WeakMap();
_InfiniteCanvas_apiProvider = new WeakMap();
InfiniteCanvas.styles = css `
:host {
display: block;
position: relative;
}
ic-spectrum-penbar {
position: absolute;
top: 48px;
left: 0;
}
ic-spectrum-taskbar {
position: absolute;
top: 48px;
right: 0;
}
ic-spectrum-layers-panel {
position: absolute;
top: 48px;
right: 54px;
}
canvas {
width: 100%;
height: 100%;
outline: none;
padding: 0;
margin: 0;
touch-action: none;
}
`;
__decorate([
property()
], InfiniteCanvas.prototype, "renderer", void 0);
__decorate([
property({
attribute: 'shader-compiler-path',
})
], InfiniteCanvas.prototype, "shaderCompilerPath", void 0);
__decorate([
property({ type: Object, attribute: 'app-state' })
], InfiniteCanvas.prototype, "appState", void 0);
__decorate([
property({ type: Array })
], InfiniteCanvas.prototype, "nodes", void 0);
InfiniteCanvas = __decorate([
customElement('ic-spectrum-canvas')
], InfiniteCanvas);
export { InfiniteCanvas };
//# sourceMappingURL=infinite-canvas.js.map