Skip to content
Snippets Groups Projects
Commit ff573cfe authored by Clark's avatar Clark
Browse files

resolved merge conflicts in GeoStacApp.jsx

parents 57a3e9cc d6d2b822
No related branches found
No related tags found
No related merge requests found
...@@ -35,10 +35,10 @@ export default function App() { ...@@ -35,10 +35,10 @@ export default function App() {
let jsonPromise = {}; let jsonPromise = {};
// Fetched Maps // Fetched Maps
var mapsJson = {}; let mapsJson = {};
// Combined Data // Combined Data
var aggregateMapList = {}; let aggregateMapList = {};
// Init // Init
fetchStatus[astroWebMaps] = "Not Started"; fetchStatus[astroWebMaps] = "Not Started";
......
...@@ -29,7 +29,7 @@ let css = { ...@@ -29,7 +29,7 @@ let css = {
* @component * @component
*/ */
export default function GeoStacApp(props) { export default function GeoStacApp(props) {
const [targetPlanet, setTargetPlanet] = React.useState("Mars"); const [targetPlanet, setTargetPlanet] = React.useState(props.mapList.systems[4].bodies[0]);
const [footprintData, setFootprintData] = React.useState([]); const [footprintData, setFootprintData] = React.useState([]);
...@@ -68,7 +68,7 @@ export default function GeoStacApp(props) { ...@@ -68,7 +68,7 @@ export default function GeoStacApp(props) {
bodyChange={handleTargetBodyChange} bodyChange={handleTargetBodyChange}
/> />
<div id="map-area"> <div id="map-area">
<MapContainer target={targetPlanet} mapList={props.mapList} /> <MapContainer target={targetPlanet.name} mapList={props.mapList}/>
</div> </div>
<QueryConsole /> <QueryConsole />
</div> </div>
......
...@@ -120,18 +120,15 @@ function PlanetDialog(props) { ...@@ -120,18 +120,15 @@ function PlanetDialog(props) {
onClose(value); onClose(value);
}; };
console.log(props.mapList)
return ( return (
<Dialog PaperProps={{sx: {overflowY: "scroll"}}} onClose={handleClose} open={open}> <Dialog PaperProps={{sx: {overflowY: "scroll"}}} onClose={handleClose} open={open}>
<DialogTitle sx={{ minWidth: 225 }}>Select Target Body</DialogTitle> <DialogTitle sx={{ minWidth: 225 }}>Select Target Body</DialogTitle>
<List sx={{ pt: 0 }}> <List sx={{ pt: 0 }}>
<ListSubheader value="None">Systems</ListSubheader> <ListSubheader value="None">Systems</ListSubheader>
{props.mapList.systems.map((system, sysIndex) => ( {props.mapList.systems.map((system, sysIndex) => (
<> <React.Fragment key={system.name}>
<ListItemButton <ListItemButton
onClick={() => handleSysOpen(sysIndex)} onClick={() => handleSysOpen(sysIndex)}
key={system.name}
> >
<ListItemAvatar> <ListItemAvatar>
<Avatar sx={{ bgcolor: blue[100] }}> <Avatar sx={{ bgcolor: blue[100] }}>
...@@ -147,7 +144,7 @@ function PlanetDialog(props) { ...@@ -147,7 +144,7 @@ function PlanetDialog(props) {
{props.mapList.systems[sysIndex].bodies.map((body, bodIndex) => ( {props.mapList.systems[sysIndex].bodies.map((body, bodIndex) => (
<ListItemButton <ListItemButton
sx={{ pl: 4 }} sx={{ pl: 4 }}
onClick={() => handleListItemClick(body.name)} onClick={() => handleListItemClick(body)}
key={body.name} key={body.name}
> >
<ListItemAvatar> <ListItemAvatar>
...@@ -161,7 +158,7 @@ function PlanetDialog(props) { ...@@ -161,7 +158,7 @@ function PlanetDialog(props) {
))} ))}
</List> </List>
</Collapse> </Collapse>
</> </React.Fragment>
))} ))}
</List> </List>
</Dialog> </Dialog>
...@@ -171,7 +168,7 @@ function PlanetDialog(props) { ...@@ -171,7 +168,7 @@ function PlanetDialog(props) {
PlanetDialog.propTypes = { PlanetDialog.propTypes = {
onClose: PropTypes.func.isRequired, onClose: PropTypes.func.isRequired,
open: PropTypes.bool.isRequired, open: PropTypes.bool.isRequired,
selectedValue: PropTypes.string.isRequired, selectedValue: PropTypes.object.isRequired,
}; };
/** /**
...@@ -187,7 +184,7 @@ PlanetDialog.propTypes = { ...@@ -187,7 +184,7 @@ PlanetDialog.propTypes = {
*/ */
export default function ConsoleTargetInfo(props) { export default function ConsoleTargetInfo(props) {
const [open, setOpen] = React.useState(false); const [open, setOpen] = React.useState(false);
const [selectedValue, setSelectedValue] = React.useState(planets[3][0]); const [selectedValue, setSelectedValue] = React.useState(props.mapList.systems[4].bodies[0]);
const handleClickOpen = () => { const handleClickOpen = () => {
setOpen(true); setOpen(true);
...@@ -215,7 +212,7 @@ export default function ConsoleTargetInfo(props) { ...@@ -215,7 +212,7 @@ export default function ConsoleTargetInfo(props) {
variant="h4" variant="h4"
onClick={handleClickOpen} onClick={handleClickOpen}
> >
{props.target.toUpperCase()} <ArrowDropDownIcon fontSize="large" /> {props.target.name.toUpperCase()} <ArrowDropDownIcon fontSize="large" />
</Typography> </Typography>
</Grid> </Grid>
<PlanetDialog <PlanetDialog
......
import React, { useEffect } from "react"; import React, { useEffect } from "react";
import Checkbox from "@mui/material/Checkbox"; import Checkbox from "@mui/material/Checkbox";
import {Card, CardContent, CardActions} from "@mui/material";
// result action links // result action links
import Chip from "@mui/material/Chip"; import Chip from "@mui/material/Chip";
...@@ -10,6 +11,7 @@ import PreviewIcon from "@mui/icons-material/Preview"; ...@@ -10,6 +11,7 @@ import PreviewIcon from "@mui/icons-material/Preview";
import LaunchIcon from "@mui/icons-material/Launch"; import LaunchIcon from "@mui/icons-material/Launch";
import OpenInFullIcon from "@mui/icons-material/OpenInFull"; import OpenInFullIcon from "@mui/icons-material/OpenInFull";
import CloseFullscreenIcon from "@mui/icons-material/CloseFullscreen"; import CloseFullscreenIcon from "@mui/icons-material/CloseFullscreen";
import TravelExploreIcon from '@mui/icons-material/TravelExplore'; // Footprints.]
// object with results // object with results
import { getFeatures } from "../../js/ApiJsonCollection"; import { getFeatures } from "../../js/ApiJsonCollection";
...@@ -17,6 +19,61 @@ import { getFeatures } from "../../js/ApiJsonCollection"; ...@@ -17,6 +19,61 @@ import { getFeatures } from "../../js/ApiJsonCollection";
// geotiff thumbnail viewer // geotiff thumbnail viewer
import DisplayGeoTiff from "../presentational/DisplayGeoTiff.jsx"; import DisplayGeoTiff from "../presentational/DisplayGeoTiff.jsx";
import GeoTiffViewer from "../../js/geoTiffViewer.js"; import GeoTiffViewer from "../../js/geoTiffViewer.js";
import { Skeleton } from "@mui/material";
/**
* Skeleton to show when footprints are loading
*/
function LoadingFootprints() {
return (
<div className="resultsList">
{ Array(5).fill(null).map((_, i) => (
<Card sx={{ width: 250, margin: 1}} key={i}>
<CardContent sx={{padding: 0.9, paddingBottom: 0}}>
<div className="resultContainer">
<div className="resultImgDiv">
<Skeleton variant="rectangular" width={32} height={32}/>
</div>
<div className="resultData">
<Skeleton/>
<Skeleton/>
<Skeleton/>
<Skeleton/>
<Skeleton/>
</div>
</div>
</CardContent>
<CardActions>
<div className="resultLinks">
<Stack direction="row" spacing={1} sx={{marginTop:1}}>
<Skeleton variant="rounded" width={100} height={20} sx={{borderRadius:5}}/>
<Skeleton variant="rounded" width={100} height={20} sx={{borderRadius:5}}/>
</Stack>
</div>
</CardActions>
</Card>
))}
</div>
);
}
function NoFootprints(){
return(
<div style={{padding: 10, maxWidth: 268}}>
<p>
This target has no footprints. To see
footprints, go to the dropdown menu
in the upper left and pick a target
body with the <TravelExploreIcon sx={{fontSize: 16, verticalAlign: "middle"}}/> icon next to it.
</p>
</div>
);
}
/** /**
* Controls css styling for this component using js to css * Controls css styling for this component using js to css
...@@ -42,10 +99,14 @@ let css = { ...@@ -42,10 +99,14 @@ let css = {
* *
*/ */
export default function FootprintResults(props) { export default function FootprintResults(props) {
const [features, setFeatures] = React.useState([]); const [features, setFeatures] = React.useState([]);
const geoTiffViewer = new GeoTiffViewer("GeoTiffAsset"); const [isLoading, setIsLoading] = React.useState(true);
const [hasFootprints, setHasFootprints] = React.useState(true);
// Metadata Popup
const geoTiffViewer = new GeoTiffViewer("GeoTiffAsset");
const showMetadata = (value) => () => { const showMetadata = (value) => () => {
geoTiffViewer.displayGeoTiff(value.assets.thumbnail.href); geoTiffViewer.displayGeoTiff(value.assets.thumbnail.href);
geoTiffViewer.changeMetaData( geoTiffViewer.changeMetaData(
...@@ -58,10 +119,97 @@ export default function FootprintResults(props) { ...@@ -58,10 +119,97 @@ export default function FootprintResults(props) {
}; };
useEffect(() => { useEffect(() => {
setTimeout(() => {
setFeatures(getFeatures); // If target has collections (of footprints)
}, 1000); if (props.target.collections.length > 0) {
// Set Loading
setIsLoading(true);
setHasFootprints(true);
// Promise tracking
let fetchPromise = {};
let jsonPromise = {};
// Result
let jsonRes = {};
let itemCollectionUrls = [];
for(const collection of props.target.collections) {
// Get "items" link for each collection
let newItemCollectionUrl =
collection.links.find(obj => obj.rel === "items").href
+ props.queryString;
itemCollectionUrls.push(newItemCollectionUrl);
}
for(const itemCollectionUrl of itemCollectionUrls) {
fetchPromise[itemCollectionUrl] = "Not Started";
jsonPromise[itemCollectionUrl] = "Not Started";
jsonRes[itemCollectionUrl] = [];
}
// Fetch JSON and read into object
async function startFetch(targetUrl) {
fetchPromise[targetUrl] = fetch(
targetUrl
).then((res)=>{
jsonPromise[targetUrl] = res.json().then((jsonData)=>{
jsonRes[targetUrl] = jsonData;
}).catch((err)=>{
console.log(err);
}); });
}).catch((err) => {
console.log(err);
});
}
async function awaitFetch(targetUrl) {
await fetchPromise[targetUrl];
await jsonPromise[targetUrl];
}
async function fetchAndWait() {
// Start fetching
for(const itemCollectionUrl of itemCollectionUrls) {
startFetch(itemCollectionUrl);
}
// Wait for completion
for(const itemCollectionUrl of itemCollectionUrls) {
await awaitFetch(itemCollectionUrl);
}
// Extract footprints into array
let resultsArr = [];
let myFeatures = [];
for(const itemCollectionUrl of itemCollectionUrls) {
myFeatures.push(jsonRes[itemCollectionUrl]);
}
for(const featCollection of myFeatures) {
resultsArr.push(...featCollection.features)
}
return resultsArr;
}
(async () => {
// Wait
let myFeatures = await fetchAndWait()
setFeatures(myFeatures);
setHasFootprints(myFeatures.length > 0);
setIsLoading(false);
})();
} else {
setIsLoading(false);
setHasFootprints(false);
}
// setTimeout(() => {
// setFeatures(getFeatures);
// }, 1000);
}, [props.target.name, props.queryString]);
return ( return (
<div style={css.root} className="scroll-parent"> <div style={css.root} className="scroll-parent">
...@@ -81,9 +229,14 @@ export default function FootprintResults(props) { ...@@ -81,9 +229,14 @@ export default function FootprintResults(props) {
/> />
</span> </span>
</div> </div>
{isLoading ?
<LoadingFootprints/>
: hasFootprints ?
<div className="resultsList"> <div className="resultsList">
{features.map((feature) => ( {features.map((feature) => (
<div className="resultContainer" key={feature.id}> <Card sx={{ width: 250, margin: 1}} key={feature.id}>
<CardContent sx={{padding: 1.2, paddingBottom: 0}}>
<div className="resultContainer" >
<div className="resultImgDiv"> <div className="resultImgDiv">
<img className="resultImg" src={feature.assets.thumbnail.href} /> <img className="resultImg" src={feature.assets.thumbnail.href} />
</div> </div>
...@@ -98,6 +251,9 @@ export default function FootprintResults(props) { ...@@ -98,6 +251,9 @@ export default function FootprintResults(props) {
<strong>Date:</strong>&nbsp;{feature.properties.datetime} <strong>Date:</strong>&nbsp;{feature.properties.datetime}
</div> </div>
</div> </div>
</div>
</CardContent>
<CardActions>
<div className="resultLinks"> <div className="resultLinks">
<Stack direction="row" spacing={1}> <Stack direction="row" spacing={1}>
<Chip <Chip
...@@ -115,15 +271,18 @@ export default function FootprintResults(props) { ...@@ -115,15 +271,18 @@ export default function FootprintResults(props) {
component="a" component="a"
href={`https://stac.astrogeology.usgs.gov/browser-dev/#/collections/${feature.collection}/items/${feature.id}`} href={`https://stac.astrogeology.usgs.gov/browser-dev/#/collections/${feature.collection}/items/${feature.id}`}
target="_blank" target="_blank"
//href="https://stac.astrogeology.usgs.gov/browser-dev/"
variant="outlined" variant="outlined"
clickable clickable
/> />
</Stack> </Stack>
</div> </div>
</div> </CardActions>
</Card>
))} ))}
</div> </div>
:
<NoFootprints/>
}
</div> </div>
); );
} }
...@@ -95,32 +95,41 @@ let css = { ...@@ -95,32 +95,41 @@ let css = {
* *
*/ */
export default function SearchAndFilterInput(props) { export default function SearchAndFilterInput(props) {
// Allows showing/hiding of fields
const keywordDetails = React.useRef(null); const keywordDetails = React.useRef(null);
const dateDetails = React.useRef(null); const dateDetails = React.useRef(null);
// React States // Sort By
const [sortVal, setSortVal] = React.useState(""); const [sortVal, setSortVal] = React.useState(""); // Sort By What?
const [sortAscCheckVal, setSortAscCheckVal] = React.useState(false); const [sortAscCheckVal, setSortAscCheckVal] = React.useState(false); // Sort Ascending or Descending
const [areaCheckVal, setAreaCheckVal] = React.useState(false);
// Filter by X checkboxes
const [areaCheckVal, setAreaCheckVal] = React.useState(false); // Area
const [keywordCheckVal, setKeywordCheckVal] = React.useState(false); // Keyword
const [dateCheckVal, setDateCheckVal] = React.useState(false); // Date
// Filter by X values
const [areaTextVal, setAreaTextVal] = React.useState(""); // Area (received by window message from AstroDrawFilterControl)
const [keywordTextVal, setKeywordTextVal] = React.useState(""); // Keyword
const [dateFromVal, setDateFromVal] = React.useState(null); // From Date
const [dateToVal, setDateToVal] = React.useState(null); // To Date
const [keywordCheckVal, setKeywordCheckVal] = React.useState(false); // Page Number
const [keywordTextVal, setKeywordTextVal] = React.useState(""); const [pageNumber, setPageNumber] = React.useState(1);
const [dateCheckVal, setDateCheckVal] = React.useState(false); // Pagination
const [dateFromVal, setDateFromVal] = React.useState(null);
const [dateToVal, setDateToVal] = React.useState(null);
const [maxPages, setMaxPages] = React.useState(10); const [maxPages, setMaxPages] = React.useState(10);
const [maxNumberFootprints, setMaxNumberFootprints] = React.useState(10); const [maxNumberFootprints, setMaxNumberFootprints] = React.useState(10);
const [numberReturned, setNumberReturned] = React.useState(10); const [numberReturned, setNumberReturned] = React.useState(10);
const [limitVal, setLimitVal] = React.useState(10); const [limitVal, setLimitVal] = React.useState(10); // Max Number of footprints requested per collection
const [applyChipVisStyle, setApplyChipVisStyle] = React.useState( // Apply/Alert Chip
css.chipHidden const [applyChipVisStyle, setApplyChipVisStyle] = React.useState(css.chipHidden);
); const [chipMessage, setChipMessage] = React.useState("Apply to Show Footprints on Map");
const [gotoPage, setGotopage] = React.useState("Apply to go to page 2");
const setApplyChip = (value) => { const setApplyChip = (value) => {
setGotopage(value); setChipMessage("Apply to Show Footprints on Map");
setApplyChipVisStyle(css.chipShown); setApplyChipVisStyle(css.chipShown);
}; };
...@@ -148,12 +157,56 @@ export default function SearchAndFilterInput(props) { ...@@ -148,12 +157,56 @@ export default function SearchAndFilterInput(props) {
setMaxPages(1); setMaxPages(1);
setMaxNumberFootprints(0); setMaxNumberFootprints(0);
setNumberReturned(0); setNumberReturned(0);
setApplyChip("Apply to show Footprints"); setApplyChip("Apply to Show Footprints on Map");
//// Uncomment to close details on clear //// Uncomment to close details on clear
// keywordDetails.current.open = false; // keywordDetails.current.open = false;
// dateDetails.current.open = false; // dateDetails.current.open = false;
}; };
const buildQueryString = () => {
let myQueryString = "?";
// Page Number
if (pageNumber != 1) myQueryString += "page=" + pageNumber + "&";
// Number of footprints requested per request
if (limitVal != 10) myQueryString += "limit=" + limitVal + "&"
// Date
if (dateCheckVal) {
let d = new Date();
let fromDate = "1970-01-01T00:00:00Z"; // From start of 1970 by default
let toDate = d.getFullYear() + "-12-31T23:59:59Z"; // To end of current year by default
// From
if(dateFromVal instanceof Date && !isNaN(dateFromVal.valueOf())) {
fromDate = dateFromVal.toISOString();
}
// To
if(dateToVal instanceof Date && !isNaN(dateToVal.valueOf())) {
toDate = dateToVal.toISOString();
}
myQueryString += "datetime=" + fromDate + "/" + toDate + "&";
}
// Keyword
if(keywordCheckVal) myQueryString += "keywords=[" + keywordTextVal.split(" ") + "]&";
// Area
if(areaCheckVal && areaTextVal !== "") myQueryString += areaTextVal;
// Sorting... Not supported by the API?
const sortAscDesc = sortAscCheckVal ? "asc" : "desc";
if (sortVal === "date" || sortVal === "location") {
console.log("Warning: Sorting not Supported!");
// myQueryString += 'sort=[{field:datetime,direction:' + sortAscDesc + '}]&'
}
props.setQueryString(myQueryString);
}
// Sorting // Sorting
const handleSortChange = (event) => { const handleSortChange = (event) => {
setSortVal(event.target.value); setSortVal(event.target.value);
...@@ -211,9 +264,18 @@ export default function SearchAndFilterInput(props) { ...@@ -211,9 +264,18 @@ export default function SearchAndFilterInput(props) {
setApplyChip("Apply to show " + value + " footprints"); setApplyChip("Apply to show " + value + " footprints");
}; };
// Pagination
const handlePageChange = (event, value) => {
setPageNumber(value);
setCurrentPage(value);
setApplyChip("Apply to go to page " + value);
};
// resets pagination and limit when switching targets // resets pagination and limit when switching targets
useEffect(() => { useEffect(() => {
setTimeout(() => { setTimeout(() => {
setCurrentPage(1);
setPageNumber(1);
setMaxNumberFootprints(getNumberMatched); setMaxNumberFootprints(getNumberMatched);
setNumberReturned(getNumberReturned); setNumberReturned(getNumberReturned);
setLimitVal(10); setLimitVal(10);
...@@ -221,13 +283,27 @@ export default function SearchAndFilterInput(props) { ...@@ -221,13 +283,27 @@ export default function SearchAndFilterInput(props) {
setMaxPages(getMaxNumberPages); setMaxPages(getMaxNumberPages);
props.footprintNavClick(); props.footprintNavClick();
}, 2000); }, 2000);
}, [props.target]); }, [props.target.name]);
// Pagination // Listen for any state change (input) and update the query string based on it
const handlePageChange = (event, value) => { useEffect(() => {
setCurrentPage(value); buildQueryString();
setApplyChip("Apply to go to page " + value); }, [sortVal, sortAscCheckVal, areaCheckVal, areaTextVal, keywordCheckVal, keywordTextVal, dateCheckVal, dateFromVal, dateToVal, limitVal, pageNumber]);
};
const onBoxDraw = event => {
if(typeof event.data == "string" && event.data.includes("bbox")){
setAreaTextVal(event.data);
setAreaCheckVal(true);
}
}
useEffect(() => {
window.addEventListener("message", onBoxDraw);
return () => {
window.removeEventListener("message", onBoxDraw);
}
}, []);
/* Control IDs for reference: /* Control IDs for reference:
applyButton applyButton
...@@ -429,7 +505,7 @@ export default function SearchAndFilterInput(props) { ...@@ -429,7 +505,7 @@ export default function SearchAndFilterInput(props) {
<div style={applyChipVisStyle}> <div style={applyChipVisStyle}>
<Chip <Chip
id="applyChip" id="applyChip"
label={gotoPage} label={chipMessage}
icon={<FlagIcon />} icon={<FlagIcon />}
onClick={handleApply} onClick={handleApply}
variant="outlined" variant="outlined"
......
...@@ -46,10 +46,11 @@ export default function Sidebar(props) { ...@@ -46,10 +46,11 @@ export default function Sidebar(props) {
); );
const [showSidePanel, setShowSidePanel] = React.useState(true); const [showSidePanel, setShowSidePanel] = React.useState(true);
const [sidePanelSubStyle, setSidePanelSubStyle] = React.useState(css.shown);
const [expandResults, setExpandResults] = React.useState(true); const [expandResults, setExpandResults] = React.useState(true);
const [queryString, setQueryString] = React.useState("?");
const showHideSort = () => { const showHideSort = () => {
setShowSidePanel(!showSidePanel); setShowSidePanel(!showSidePanel);
}; };
...@@ -72,6 +73,7 @@ export default function Sidebar(props) { ...@@ -72,6 +73,7 @@ export default function Sidebar(props) {
> >
<SearchAndFilterInput <SearchAndFilterInput
target={props.target} target={props.target}
setQueryString={setQueryString}
footprintNavClick={props.footprintNavClick} footprintNavClick={props.footprintNavClick}
/> />
{!expandResults && <OutPortal node={footprintResultPortalNode} />} {!expandResults && <OutPortal node={footprintResultPortalNode} />}
...@@ -81,7 +83,7 @@ export default function Sidebar(props) { ...@@ -81,7 +83,7 @@ export default function Sidebar(props) {
)} )}
</div> </div>
<InPortal node={footprintResultPortalNode}> <InPortal node={footprintResultPortalNode}>
<FootprintResults changeLayout={handlePanelLayout} /> <FootprintResults target={props.target} queryString={queryString} changeLayout={handlePanelLayout} />
</InPortal> </InPortal>
</> </>
); );
......
import React from "react"; import React from "react";
import CircularProgress from '@mui/material/LinearProgress';
import SvgIcon from "@mui/material/SvgIcon"; import SvgIcon from "@mui/material/SvgIcon";
import loadingImage from "../../images/logos/geostac-logo.svg"; import loadingImage from "../../images/logos/geostac-logo.svg";
import LinearProgress from "@mui/material/LinearProgress";
export default function SplashScreen() { export default function SplashScreen() {
return( return(
...@@ -20,6 +22,7 @@ export default function SplashScreen() { ...@@ -20,6 +22,7 @@ export default function SplashScreen() {
}} }}
component={loadingImage} component={loadingImage}
/> />
<LinearProgress/>
</div> </div>
</div> </div>
) )
......
...@@ -116,6 +116,7 @@ export default L.Control.AstroDrawFilterControl = L.Control.Draw.extend({ ...@@ -116,6 +116,7 @@ export default L.Control.AstroDrawFilterControl = L.Control.Draw.extend({
geoJson = geoJson["geometry"]; geoJson = geoJson["geometry"];
this.wkt.read(JSON.stringify(geoJson)); this.wkt.read(JSON.stringify(geoJson));
window.postMessage(this.shapesToFootprint(this.wkt.components[0]), "*");
}, },
/** /**
......
...@@ -316,14 +316,12 @@ Controls the CSS for projection buttons when there is no available projection ...@@ -316,14 +316,12 @@ Controls the CSS for projection buttons when there is no available projection
} }
.resultContainer { .resultContainer {
width: 268px; width: 230px;
display: grid; display: grid;
grid-template: grid-template:
"ra rb" "ra rb"
"rc rc" "rc rc"
/ 20% 80%; / 20% 80%;
border-bottom: 3px double rgba(0, 0, 0, 0.4);
padding: 10px;
} }
.resultSub { .resultSub {
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment