UNPKG

@seasketch/geoprocessing

Version:

Geoprocessing and reporting framework for SeaSketch 2.0

138 lines 6.12 kB
import React, { Suspense, useState, useEffect } from "react"; import { ReportContext } from "../context/index.js"; import { seaSketchReportingMessageEventType, seaSketchReportingVisibleLayersChangeEvent, seaSketchReportingLanguageChangeEvent, } from "../helpers/service.js"; import { ReportTextDirection } from "./i18n/ReportTextDirection.js"; const searchParams = new URLSearchParams(window.location.search); const service = searchParams.get("service"); const frameId = searchParams.get("frameId") || window.name; export const App = ({ reports }) => { if (!service) { throw new Error("App must be loaded with `service` query string parameter"); } // Maintain report context in app state const [reportContext, setReportContext] = useState(null); const [initialized, setInitialized] = useState(false); /** * Event handler for messages from the parent window * @param event - postMessage event */ const onMessage = (event) => { try { if (event.data && event.data.type === seaSketchReportingMessageEventType) { const message = event.data; // Convert id to string to ensure it is a string as gp expects message.sketchProperties.id = message.sketchProperties.id.toString(); setReportContext({ sketchProperties: message.sketchProperties, geometryUri: message.geometryUri, clientName: message.client, visibleLayers: message.visibleLayers || [], language: message.language || "en", /** * Send a message to the parent window to toggle the visibility of a layer * @param layerId - id of the layer to toggle */ toggleLayerVisibility: (layerId) => { setReportContext((prev) => { if (prev) { const wasToggled = prev.visibleLayers.includes(layerId); let target = window; if (window.parent) { target = window.parent; } target.postMessage({ type: "SeaSketchReportingToggleLayerVisibilityEvent", layerId, on: !wasToggled, }, "*"); return { ...prev, visibleLayers: wasToggled ? prev.visibleLayers.filter((id) => id !== layerId) : [...prev.visibleLayers, layerId], }; } else { return null; } }); }, }); } else if (event.data && event.data.type === seaSketchReportingVisibleLayersChangeEvent) { const message = event.data; // Update visible layers in context // Don't update context unless report is already initialized with SeaSketchReportingMessageEvent if (reportContext) { setReportContext((prev) => { if (prev) { return { ...prev, visibleLayers: message.visibleLayers }; } else { return null; } }); } } else if (event.data && event.data.type === seaSketchReportingLanguageChangeEvent) { const message = event.data; // Update language in context // Don't update context unless report is already initialized with SeaSketchReportingMessageEvent if (reportContext) { setReportContext((prev) => { if (prev) { return { ...prev, language: message.language }; } else { return null; } }); } } } catch (error) { // Do nothing. Might not even be related to SeaSketch reporting console.error(error); } }; const onKeyDown = (e) => { if (e.key === "x" && window.parent) { window.parent.postMessage({ type: "SeaSketchReportingKeydownEvent", key: "x" }, "*"); } }; useEffect(() => { // default to self for debugging let target = window; if (window.parent) { target = window.parent; } window.addEventListener("message", onMessage); window.addEventListener("keydown", onKeyDown); if (!initialized) { target.postMessage({ type: "SeaSketchReportingInitEvent", frameId }, "*"); setInitialized(true); } return () => { window.removeEventListener("message", onMessage); window.removeEventListener("keydown", onKeyDown); }; }, [initialized, reportContext]); if (reportContext) { const Report = reports[reportContext.clientName]; return (React.createElement(ReportContext.Provider, { value: { ...reportContext, projectUrl: service, } }, React.createElement(ReportTextDirection, null, React.createElement(Suspense, { fallback: React.createElement("div", null, "Loading...") }, React.createElement(Report, null))))); } else { return React.createElement("div", null); } }; export default App; //# sourceMappingURL=App.js.map