Loading app/src/components/container/MapContainer.jsx +16 −13 Original line number Diff line number Diff line import React, { Component } from "react"; import AstroMap from "../../js/AstroMap"; import Projection from "../../js/Projection"; import MousePosition from "../../js/MousePosition"; import ProjectionControl from "../../js/ProjectionControl"; import MousePositionControl from "../../js/MousePositionControl"; import Draw from "../../js/Draw"; import "leaflet"; //import newAutocomplete from "../../js/autocomplete/customIndex"; Loading Loading @@ -31,10 +31,12 @@ export default class MapContainer extends Component { */ componentDidMount() { let map = new AstroMap("map-container", this.props.target, {}); new Projection().addTo(map); new MousePosition({ map.addControl(new ProjectionControl()); map.addControl( new MousePositionControl({ numDigits: 3 }).addTo(map); }) ); let drawnItems = new L.FeatureGroup(); map.addLayer(drawnItems); Loading @@ -51,7 +53,7 @@ export default class MapContainer extends Component { targetMap: map }).addTo(map); new L.Control.Scale({ imperial: false }).addTo(map); map.addControl(new L.Control.Scale({ imperial: false })); //new newAutocomplete(); } Loading @@ -78,11 +80,12 @@ export default class MapContainer extends Component { // create new map with updated target let map = new AstroMap("map-container", this.props.target, {}); new Projection().addTo(map); new MousePosition({ numDigits: 2, targetPlanet: this.props.target }).addTo(map); map.addControl(new ProjectionControl()); map.addControl( new MousePositionControl({ numDigits: 3 }) ); let drawnItems = new L.FeatureGroup(); map.addLayer(drawnItems); Loading @@ -99,7 +102,7 @@ export default class MapContainer extends Component { targetMap: map }).addTo(map); new L.Control.Scale({ imperial: false }).addTo(map); map.addControl(new L.Control.Scale({ imperial: false })); } render() { Loading app/src/components/presentational/ConsoleProjectionButtons.jsx +1 −1 Original line number Diff line number Diff line Loading @@ -176,7 +176,7 @@ export default function ConsoleProjectionButtons() { <StyledTooltip title={ <Typography variant="subtitle1"> Switch to a cylindrical polar projection for the target body. Switch to a cylindrical projection for the target body. </Typography> } enterDelay={800} Loading app/src/js/AstroMap.js +100 −14 Original line number Diff line number Diff line import AstroProj from "./AstroProj"; import LayerCollection from "./LayerCollection"; import "leaflet-fullscreen"; // import "leaflet-fullscreen"; import L from "leaflet"; import "proj4"; import "proj4leaflet"; import { MY_JSON_MAPS } from "./layers"; /** * @class AstroMap * @aka L.Map.AstroMap Loading Loading @@ -35,25 +40,48 @@ export default L.Map.AstroMap = L.Map.extend({ this._mapDiv = mapDiv; this._target = target; this._astroProj = new AstroProj(); this._radii = this._astroProj.getRadii(this._target); this._radii = { a: "", c: "" }; // Set by layer collection or baselayerchange event this._currentLayer = null; // Store layers at map creation so we only need to create layers once. let cylLayerInfo = this.parseJSON("cylindrical"); if (Object.entries(cylLayerInfo["base"]).length == 0) { throw "No entry in the JSON for [" + this._target + "]. Cannot instantiate a map."; } // Could not work with _ this.layers = { northPolar: new LayerCollection( this._target, "north-polar stereographic" ), southPolar: new LayerCollection( this._target, "south-polar stereographic" ), cylindrical: new LayerCollection(this._target, "cylindrical") cylindrical: new LayerCollection("cylindrical", cylLayerInfo) }; this._hasNorthPolar = !this.layers["northPolar"].isEmpty(); this._hasSouthPolar = !this.layers["southPolar"].isEmpty(); let northLayerInfo = this.parseJSON("north-polar stereographic"); if (Object.entries(northLayerInfo["base"]).length == 0) { this._hasNorthPolar = false; } else { this._hasNorthPolar = true; this.layers["northPolar"] = new LayerCollection( "north-polar stereographic", northLayerInfo ); } let southLayerInfo = this.parseJSON("south-polar stereographic"); if (Object.entries(southLayerInfo["base"]).length == 0) { this._hasSouthPolar = false; } else { this._hasSouthPolar = true; this.layers["southPolar"] = new LayerCollection( "south-polar stereographic", southLayerInfo ); } this._defaultProj = L.extend({}, L.CRS.EPSG4326, { R: this._radii["a"] }); this.options["crs"] = this._defaultProj; Loading @@ -80,6 +108,54 @@ export default L.Map.AstroMap = L.Map.extend({ this.layers[name].addTo(this); }, /** * @function AstroMap.prototype.parseJSON * @description Parses the USGS JSON, creates layer objects for a particular target and projection, * and stores them in a JS object. * @param {String} [projection - Name of the projection to grab the layer information for. * @return {Object} - Dictionary containing the layer information in the format: {base: [], overlays: []} */ parseJSON: function(projection) { let layers = { base: [], overlays: [], wfs: [] }; let targets = MY_JSON_MAPS["targets"]; for (let i = 0; i < targets.length; i++) { let currentTarget = targets[i]; if (currentTarget["name"].toLowerCase() == this._target.toLowerCase()) { this._radii["a"] = parseFloat(currentTarget["aaxisradius"] * 1000); this._radii["c"] = parseFloat(currentTarget["caxisradius"] * 1000); let jsonLayers = currentTarget["webmap"]; for (let j = 0; j < jsonLayers.length; j++) { let currentLayer = jsonLayers[j]; if ( currentLayer["projection"].toLowerCase() != projection.toLowerCase() ) { continue; } if (currentLayer["type"] == "WMS") { // Base layer check if (currentLayer["transparent"] == "false") { layers["base"].push(currentLayer); } else { // Do not add "Show Feature Names" PNG layer. if (currentLayer["displayname"] != "Show Feature Names") { layers["overlays"].push(currentLayer); } } } else { layers["wfs"].push(currentLayer); } } } } return layers; }, /** * @function AstroMap.prototype.changeProjection * @description Changes the projection of the map and resets the center and view. Loading @@ -104,7 +180,7 @@ export default L.Map.AstroMap = L.Map.extend({ this._currentProj = "EPSG:4326"; this.setMaxZoom(8); } else { let proj = this._astroProj.getStringAndCode(this._target, name); let proj = this._astroProj.getStringAndCode(name, this._radii); newCRS = new L.Proj.CRS(proj["code"], proj["string"], { resolutions: [8192, 4096, 2048, 1024, 512, 256, 128] }); Loading Loading @@ -181,5 +257,15 @@ export default L.Map.AstroMap = L.Map.extend({ */ currentLayer: function() { return this._currentLayer; }, /** * @function AstroMap.prototype.radii * @description Returns the a and c radii of the target. * * @return {Dictionary} Radii of target in form {'a': . 'c': }. */ radii: function() { return this._radii; } }); app/src/js/AstroMath.js +11 −31 Original line number Diff line number Diff line import { MY_JSON_MAPS } from "./layers"; import "./MousePosition"; /** * @class AstroMath * @classdesc A helper class that can be used by any mapping application, not just Leaflet, to calculate different * longitude and latitude domains and ranges for a specific target. * It uses a JSON file in the background to store the targets and their associated radii. * @param {String} targetName - the name of the specific target. * @param {String} targetName - The name of the specific target. * @param {Dictionary} radii - The radii of the target in the form {"a": , "c": } */ export default class AstroMath { constructor(targetName) { constructor(targetName, radii) { this.targetName = targetName; let targets = MY_JSON_MAPS["targets"]; for (let i = 0; i < targets.length; i++) { let currentTarget = targets[i]; if ( currentTarget["name"].toLowerCase() == this.targetName.toLowerCase() ) { this.dMajorRadius = parseFloat(currentTarget["aaxisradius"] * 1000); this.dMinorRadius = parseFloat(currentTarget["caxisradius"] * 1000); break; } } this.majorRadius = radii["a"]; this.minorRadius = radii["c"]; } /** Loading @@ -33,7 +19,7 @@ export default class AstroMath { * @return {double} The Major radius value. */ getMajorRadius() { return this.dMajorRadius; return this.majorRadius; } /** Loading @@ -43,7 +29,7 @@ export default class AstroMath { * @return {double} The Minor radius value. */ getMinorRadius() { return this.dMinorRadius; return this.minorRadius; } /** Loading Loading @@ -81,7 +67,7 @@ export default class AstroMath { let convertedLatitude = 0; convertedLatitude = this.toRadians(lat); convertedLatitude = Math.atan( (this.dMajorRadius / this.dMinorRadius) ** 2 * Math.tan(convertedLatitude) (this.majorRadius / this.minorRadius) ** 2 * Math.tan(convertedLatitude) ); convertedLatitude = this.toDegrees(convertedLatitude); Loading @@ -104,19 +90,13 @@ export default class AstroMath { convertedLon -= 180; } if (convertedLon < 0) { if (projection == "EPSG:4326") { if (projection == "EPSG:4326") { convertedLon += 360; } else { } else { convertedLon += 180; } } else if (projection != "EPSG:4326") { } else if (projection != "EPSG:4326") { convertedLon += 180; } Loading app/src/js/AstroProj.js +2 −29 Original line number Diff line number Diff line Loading @@ -6,43 +6,16 @@ import { MY_JSON_MAPS } from "./layers"; * by the USGS. */ export default class AstroProj { /** * @function AstroProj.prototype.getRadii * @description Finds the a and c radii of a given target. * * @param {String} target - Name of the target. * * @return {Object} Radii Object in form: {'a': , 'c': }. */ getRadii(target) { var targets = MY_JSON_MAPS["targets"]; let radii = {}; for (let i = 0; i < targets.length; i++) { let currentTarget = targets[i]; if (currentTarget["name"].toLowerCase() == target.toLowerCase()) { radii["a"] = parseFloat(currentTarget["aaxisradius"] * 1000); radii["c"] = parseFloat(currentTarget["caxisradius"] * 1000); break; } } return radii; } /** * @function AstroProj.prototype.getStringAndCode * @description Returns the proj-string for a requested target and projection name. * * @param {String} target - Name of the target. * * @param {String} name - Name of the projection. * * @return {Object} Object storing the proj-string and code * in the form: {'code': , 'string'}. */ getStringAndCode(target, name) { let radii = this.getRadii(target); getStringAndCode(name, radii) { if (name == "northPolar") { return { code: "EPSG:32661", Loading Loading @@ -70,7 +43,7 @@ export default class AstroProj { "+proj=longlat +a=" + radii["a"] + " +b=" + radii["c"] + " +no_defs" }; } else { console.log("No projection found for the target and name given."); throw "No projection found for the projection [" + name + "] given."; } } } Loading
app/src/components/container/MapContainer.jsx +16 −13 Original line number Diff line number Diff line import React, { Component } from "react"; import AstroMap from "../../js/AstroMap"; import Projection from "../../js/Projection"; import MousePosition from "../../js/MousePosition"; import ProjectionControl from "../../js/ProjectionControl"; import MousePositionControl from "../../js/MousePositionControl"; import Draw from "../../js/Draw"; import "leaflet"; //import newAutocomplete from "../../js/autocomplete/customIndex"; Loading Loading @@ -31,10 +31,12 @@ export default class MapContainer extends Component { */ componentDidMount() { let map = new AstroMap("map-container", this.props.target, {}); new Projection().addTo(map); new MousePosition({ map.addControl(new ProjectionControl()); map.addControl( new MousePositionControl({ numDigits: 3 }).addTo(map); }) ); let drawnItems = new L.FeatureGroup(); map.addLayer(drawnItems); Loading @@ -51,7 +53,7 @@ export default class MapContainer extends Component { targetMap: map }).addTo(map); new L.Control.Scale({ imperial: false }).addTo(map); map.addControl(new L.Control.Scale({ imperial: false })); //new newAutocomplete(); } Loading @@ -78,11 +80,12 @@ export default class MapContainer extends Component { // create new map with updated target let map = new AstroMap("map-container", this.props.target, {}); new Projection().addTo(map); new MousePosition({ numDigits: 2, targetPlanet: this.props.target }).addTo(map); map.addControl(new ProjectionControl()); map.addControl( new MousePositionControl({ numDigits: 3 }) ); let drawnItems = new L.FeatureGroup(); map.addLayer(drawnItems); Loading @@ -99,7 +102,7 @@ export default class MapContainer extends Component { targetMap: map }).addTo(map); new L.Control.Scale({ imperial: false }).addTo(map); map.addControl(new L.Control.Scale({ imperial: false })); } render() { Loading
app/src/components/presentational/ConsoleProjectionButtons.jsx +1 −1 Original line number Diff line number Diff line Loading @@ -176,7 +176,7 @@ export default function ConsoleProjectionButtons() { <StyledTooltip title={ <Typography variant="subtitle1"> Switch to a cylindrical polar projection for the target body. Switch to a cylindrical projection for the target body. </Typography> } enterDelay={800} Loading
app/src/js/AstroMap.js +100 −14 Original line number Diff line number Diff line import AstroProj from "./AstroProj"; import LayerCollection from "./LayerCollection"; import "leaflet-fullscreen"; // import "leaflet-fullscreen"; import L from "leaflet"; import "proj4"; import "proj4leaflet"; import { MY_JSON_MAPS } from "./layers"; /** * @class AstroMap * @aka L.Map.AstroMap Loading Loading @@ -35,25 +40,48 @@ export default L.Map.AstroMap = L.Map.extend({ this._mapDiv = mapDiv; this._target = target; this._astroProj = new AstroProj(); this._radii = this._astroProj.getRadii(this._target); this._radii = { a: "", c: "" }; // Set by layer collection or baselayerchange event this._currentLayer = null; // Store layers at map creation so we only need to create layers once. let cylLayerInfo = this.parseJSON("cylindrical"); if (Object.entries(cylLayerInfo["base"]).length == 0) { throw "No entry in the JSON for [" + this._target + "]. Cannot instantiate a map."; } // Could not work with _ this.layers = { northPolar: new LayerCollection( this._target, "north-polar stereographic" ), southPolar: new LayerCollection( this._target, "south-polar stereographic" ), cylindrical: new LayerCollection(this._target, "cylindrical") cylindrical: new LayerCollection("cylindrical", cylLayerInfo) }; this._hasNorthPolar = !this.layers["northPolar"].isEmpty(); this._hasSouthPolar = !this.layers["southPolar"].isEmpty(); let northLayerInfo = this.parseJSON("north-polar stereographic"); if (Object.entries(northLayerInfo["base"]).length == 0) { this._hasNorthPolar = false; } else { this._hasNorthPolar = true; this.layers["northPolar"] = new LayerCollection( "north-polar stereographic", northLayerInfo ); } let southLayerInfo = this.parseJSON("south-polar stereographic"); if (Object.entries(southLayerInfo["base"]).length == 0) { this._hasSouthPolar = false; } else { this._hasSouthPolar = true; this.layers["southPolar"] = new LayerCollection( "south-polar stereographic", southLayerInfo ); } this._defaultProj = L.extend({}, L.CRS.EPSG4326, { R: this._radii["a"] }); this.options["crs"] = this._defaultProj; Loading @@ -80,6 +108,54 @@ export default L.Map.AstroMap = L.Map.extend({ this.layers[name].addTo(this); }, /** * @function AstroMap.prototype.parseJSON * @description Parses the USGS JSON, creates layer objects for a particular target and projection, * and stores them in a JS object. * @param {String} [projection - Name of the projection to grab the layer information for. * @return {Object} - Dictionary containing the layer information in the format: {base: [], overlays: []} */ parseJSON: function(projection) { let layers = { base: [], overlays: [], wfs: [] }; let targets = MY_JSON_MAPS["targets"]; for (let i = 0; i < targets.length; i++) { let currentTarget = targets[i]; if (currentTarget["name"].toLowerCase() == this._target.toLowerCase()) { this._radii["a"] = parseFloat(currentTarget["aaxisradius"] * 1000); this._radii["c"] = parseFloat(currentTarget["caxisradius"] * 1000); let jsonLayers = currentTarget["webmap"]; for (let j = 0; j < jsonLayers.length; j++) { let currentLayer = jsonLayers[j]; if ( currentLayer["projection"].toLowerCase() != projection.toLowerCase() ) { continue; } if (currentLayer["type"] == "WMS") { // Base layer check if (currentLayer["transparent"] == "false") { layers["base"].push(currentLayer); } else { // Do not add "Show Feature Names" PNG layer. if (currentLayer["displayname"] != "Show Feature Names") { layers["overlays"].push(currentLayer); } } } else { layers["wfs"].push(currentLayer); } } } } return layers; }, /** * @function AstroMap.prototype.changeProjection * @description Changes the projection of the map and resets the center and view. Loading @@ -104,7 +180,7 @@ export default L.Map.AstroMap = L.Map.extend({ this._currentProj = "EPSG:4326"; this.setMaxZoom(8); } else { let proj = this._astroProj.getStringAndCode(this._target, name); let proj = this._astroProj.getStringAndCode(name, this._radii); newCRS = new L.Proj.CRS(proj["code"], proj["string"], { resolutions: [8192, 4096, 2048, 1024, 512, 256, 128] }); Loading Loading @@ -181,5 +257,15 @@ export default L.Map.AstroMap = L.Map.extend({ */ currentLayer: function() { return this._currentLayer; }, /** * @function AstroMap.prototype.radii * @description Returns the a and c radii of the target. * * @return {Dictionary} Radii of target in form {'a': . 'c': }. */ radii: function() { return this._radii; } });
app/src/js/AstroMath.js +11 −31 Original line number Diff line number Diff line import { MY_JSON_MAPS } from "./layers"; import "./MousePosition"; /** * @class AstroMath * @classdesc A helper class that can be used by any mapping application, not just Leaflet, to calculate different * longitude and latitude domains and ranges for a specific target. * It uses a JSON file in the background to store the targets and their associated radii. * @param {String} targetName - the name of the specific target. * @param {String} targetName - The name of the specific target. * @param {Dictionary} radii - The radii of the target in the form {"a": , "c": } */ export default class AstroMath { constructor(targetName) { constructor(targetName, radii) { this.targetName = targetName; let targets = MY_JSON_MAPS["targets"]; for (let i = 0; i < targets.length; i++) { let currentTarget = targets[i]; if ( currentTarget["name"].toLowerCase() == this.targetName.toLowerCase() ) { this.dMajorRadius = parseFloat(currentTarget["aaxisradius"] * 1000); this.dMinorRadius = parseFloat(currentTarget["caxisradius"] * 1000); break; } } this.majorRadius = radii["a"]; this.minorRadius = radii["c"]; } /** Loading @@ -33,7 +19,7 @@ export default class AstroMath { * @return {double} The Major radius value. */ getMajorRadius() { return this.dMajorRadius; return this.majorRadius; } /** Loading @@ -43,7 +29,7 @@ export default class AstroMath { * @return {double} The Minor radius value. */ getMinorRadius() { return this.dMinorRadius; return this.minorRadius; } /** Loading Loading @@ -81,7 +67,7 @@ export default class AstroMath { let convertedLatitude = 0; convertedLatitude = this.toRadians(lat); convertedLatitude = Math.atan( (this.dMajorRadius / this.dMinorRadius) ** 2 * Math.tan(convertedLatitude) (this.majorRadius / this.minorRadius) ** 2 * Math.tan(convertedLatitude) ); convertedLatitude = this.toDegrees(convertedLatitude); Loading @@ -104,19 +90,13 @@ export default class AstroMath { convertedLon -= 180; } if (convertedLon < 0) { if (projection == "EPSG:4326") { if (projection == "EPSG:4326") { convertedLon += 360; } else { } else { convertedLon += 180; } } else if (projection != "EPSG:4326") { } else if (projection != "EPSG:4326") { convertedLon += 180; } Loading
app/src/js/AstroProj.js +2 −29 Original line number Diff line number Diff line Loading @@ -6,43 +6,16 @@ import { MY_JSON_MAPS } from "./layers"; * by the USGS. */ export default class AstroProj { /** * @function AstroProj.prototype.getRadii * @description Finds the a and c radii of a given target. * * @param {String} target - Name of the target. * * @return {Object} Radii Object in form: {'a': , 'c': }. */ getRadii(target) { var targets = MY_JSON_MAPS["targets"]; let radii = {}; for (let i = 0; i < targets.length; i++) { let currentTarget = targets[i]; if (currentTarget["name"].toLowerCase() == target.toLowerCase()) { radii["a"] = parseFloat(currentTarget["aaxisradius"] * 1000); radii["c"] = parseFloat(currentTarget["caxisradius"] * 1000); break; } } return radii; } /** * @function AstroProj.prototype.getStringAndCode * @description Returns the proj-string for a requested target and projection name. * * @param {String} target - Name of the target. * * @param {String} name - Name of the projection. * * @return {Object} Object storing the proj-string and code * in the form: {'code': , 'string'}. */ getStringAndCode(target, name) { let radii = this.getRadii(target); getStringAndCode(name, radii) { if (name == "northPolar") { return { code: "EPSG:32661", Loading Loading @@ -70,7 +43,7 @@ export default class AstroProj { "+proj=longlat +a=" + radii["a"] + " +b=" + radii["c"] + " +no_defs" }; } else { console.log("No projection found for the target and name given."); throw "No projection found for the projection [" + name + "] given."; } } }