UNPKG

@instantdb/core

Version:

Instant's core local abstraction

126 lines 4.99 kB
import * as flags from "./utils/flags.js"; let currentDevtool; export function createDevtool(appId, config) { currentDevtool === null || currentDevtool === void 0 ? void 0 : currentDevtool.dispose(); const iframeContrainer = createIframeContainer(config); const toggler = createToggler(config, toggleView); const iframe = createIframe(getSrc(appId)); function onPostMessage(event) { var _a; if (event.source !== iframe.element.contentWindow) return; if (((_a = event.data) === null || _a === void 0 ? void 0 : _a.type) === 'close' && iframeContrainer.isVisible()) { toggleView(); } } function onKeyDown(event) { const isToggleShortcut = event.shiftKey && event.ctrlKey && event.key === '0'; const isEsc = event.key === 'Escape' || event.key === 'Esc'; if (isToggleShortcut) { toggleView(); } else if (isEsc && iframeContrainer.isVisible()) { toggleView(); } } function toggleView() { if (iframeContrainer.isVisible()) { iframeContrainer.element.style.display = 'none'; } else { iframeContrainer.element.style.display = 'block'; // lazily render iframe on first open if (!iframeContrainer.element.contains(iframe.element)) { iframeContrainer.element.appendChild(iframe.element); } } } function dispose() { iframeContrainer.element.remove(); toggler.element.remove(); removeEventListener('keydown', onKeyDown); removeEventListener('message', onPostMessage); } function create() { document.body.appendChild(iframeContrainer.element); document.body.appendChild(toggler.element); addEventListener('keydown', onKeyDown); addEventListener('message', onPostMessage); currentDevtool = { dispose, }; } return create(); } function getSrc(appId) { const useLocalDashboard = flags.devBackend || flags.devtoolLocalDashboard; const src = `${useLocalDashboard ? 'http://localhost:3000' : 'https://instantdb.com'}/_devtool?appId=${appId}`; return src; } function createIframe(src) { const element = document.createElement('iframe'); element.src = src; element.className = 'instant-devtool-iframe'; Object.assign(element.style, { width: '100%', height: '100%', backgroundColor: 'white', border: 'none', }); return { element }; } function createToggler(config, onClick) { const logoSVG = ` <svg width="32" height="32" viewBox="0 0 512 512" fill="none" xmlns="http://www.w3.org/2000/svg"> <rect width="512" height="512" fill="black"/> <rect x="97.0973" y="91.3297" width="140" height="330" fill="white"/> </svg> `; const element = document.createElement('button'); element.innerHTML = logoSVG; element.className = 'instant-devtool-toggler'; Object.assign(element.style, Object.assign(Object.assign({ // pos position: 'fixed' }, cssPositionForToggler(config.position)), { height: '32px', width: '32px', // layout display: 'flex', alignItems: 'center', justifyContent: 'center', zIndex: '9010', // look padding: '0', margin: '0', border: 'none', cursor: 'pointer' })); element.addEventListener('click', onClick); return { element }; } function cssPositionForToggler(position) { switch (position) { case 'bottom-left': return { bottom: '24px', left: '24px' }; case 'bottom-right': return { bottom: '24px', right: '24px' }; case 'top-right': return { top: '24px', right: '24px' }; case 'top-left': return { top: '24px', left: '24px' }; } } function cssPositionForIframeContainer(position) { switch (position) { case 'bottom-left': return { bottom: '24px', right: '24px', left: '60px', top: '72px' }; case 'bottom-right': return { bottom: '24px', left: '24px', right: '60px', top: '72px' }; case 'top-right': return { top: '24px', left: '24px', right: '60px', bottom: '72px' }; case 'top-left': return { top: '24px', right: '24px', left: '60px', bottom: '72px' }; } } function createIframeContainer(config) { const element = document.createElement('div'); Object.assign(element.style, Object.assign(Object.assign({ position: 'fixed' }, cssPositionForIframeContainer(config.position)), { display: 'block', borderRadius: '4px', border: '1px #ccc solid', boxShadow: '0px 0px 8px #00000044', backgroundColor: '#eee', zIndex: '999990' })); element.style.display = 'none'; element.className = 'instant-devtool-container'; function isVisible() { return element.style.display !== 'none'; } return { element, isVisible }; } //# sourceMappingURL=devtool.js.map