import { Deck, Widget, WidgetPlacement, } from '@deck.gl/core'; import { toPng } from 'html-to-image'; import {render} from 'preact'; interface SaveImageWidgetProps { id?: string; label?: string; placement?: WidgetPlacement; } export default class SaveImageWidget extends Widget { id = 'save-image'; placement: WidgetPlacement = 'top-right'; viewId?: string | null = null; className: string = "deck-widget-save-image"; constructor(props: SaveImageWidgetProps) { props.label = props.label ?? 'Save as Image'; super(props) this.setProps(props); } onRenderHTML(rootElement: HTMLElement): void { const ui = (
); render(ui, rootElement); } async handleClick() { if (this.deck) { this.deck.redraw('true'); const deck_wrapper = this.deck?.getCanvas()?.parentElement; if (deck_wrapper) { const filter = (node: HTMLElement) => { const exclusionClasses = ["deck-widget-save-image"]; return !exclusionClasses.some((classname) => node.classList?.contains(classname)); } toPng(deck_wrapper, {filter: filter}) .then(function (dataUrl) { const img = new Image(); img.src = dataUrl; const a = document.createElement("a"); a.href = dataUrl; a.download = "map.png"; a.click(); }) .catch(function (error) { console.error("Failed to export PNG", error); }); } } } }