The following are notes about the implementation of this code challenge.
First, clone this repo and install all dependencies:
git clone git@github.com:nicktripp/clarity_map.git
cd clarity_map
npm i
Now, start the app:
npm start
My version of Openmap works similarly to Clarity Openmap, in that you can zoom and scroll over the map, click nodes to view air quality information, and query over the names of these nodes in the search bar. However, unlike Clarity Openmap, searching the search bar also queries existing, real, world-wide location data, including monuments, parks, countries, cities, addresses, and more.
As you type in the search bar, the app autocompletes your results with a list of node/real-world result data.
Clicking a result from the results list will focus the map on that point.
Try typing the following test queries into the searchbar!
Auckland
Musick
Wellington
The code I wrote is in the following directory structure:
public/
index.html
src/
/components
App.js
Legend.js
/containers
Map.js
ResultList.js
Searchbar.js
VisibleResultList.js
/data
aqi.js
generateGeoJson.js
nodes.js
actions.js
index.css
index.js
initState.js
reducers.js
For clarity, I'll go through each.
This file sets up the Redux store initialized in /src/initState.js, and connects the application found in /src/components/App.js to the public /public/index.html. Standard React-Redux procedure.
Defines the initial values for the redux store describing the application state.
Defines pure actions that can transition the redux store to a different state. Hooked up to /src/reducers.js.
Based on the actions defined in ./actions.js, each reducer returns a part of the new Redux state.
This file contains my custom styling information for elements found all over the rest of the project.
This file is mostly pre-generated by create-react-app. The meat of this is filled out in src/index.js.
This directory holds simple React components - those that don't modify the Redux state.
Sets initial mapbox conditions, and defines a layout for other containers/components.
Defines a static Legend component that sits on the map overlay.
Defines helper functions to stylize click popups based on node data.
This directory holds complex React-Redux components - those that modify the Redux state based on input.
This large file handles mapbox Map behavior. It's mostly initializing callbacks for 1) map events like onClick, onLoad and 2) the map redrawing under new props (such as a new popup or new highlighted point to fly-to).
This file handles styling for our searchResults. To do this, it dynamically populates an antd Select dropdown with searchResults. Should one be selected, it clears the results and signals the map to fly to the selected point.
This file 1) defines the layout of the search bar overlay, 2) defines input behavior to send queries the geocoders defined in ./Map.js, and 3) specifies how to store the results of those queries back into the redux store.
This directory contains hard-coded data on nodes and AQI color indices, and contains some helper functions for transforming that data into different formats.
Contains AQI number->color data and a helper function to transform an AQI number into a corresponding AQI-level color.
Contains helper function to transform the simple, hardcoded node data found in nodes.js into GeoJSON layer data and Carmen GeoJSON data.
Contains hardcoded JSON node data. The data is full of made-up nodes at locations around Auckland, NZ.
This project proved to be a challenge, and I gained much from it. I thank you for reading this, and for this opportunity to display my skillset!
Name: Nick Tripp
Phone: 908-343-7885
Email: nick.e.tripp@gmail.com