diff --git a/src/ControlPanel.jsx b/src/ControlPanel.jsx index 98b0011..599aec0 100644 --- a/src/ControlPanel.jsx +++ b/src/ControlPanel.jsx @@ -4,71 +4,37 @@ import Toggle from 'react-toggle'; import propTypes from 'prop-types'; import Checkbox from './Checkbox'; import muniRoutesGeoJson from './res/muniRoutes.geo.json'; -// import Map from './Map'; - -const notAlpha = /[^a-zA-Z]/g; - -/* -Sort by putting letters before numbers and treat number strings as integers. -Calling Array.prototype.sort() without a compare function sorts elements as -strings by Unicode code point order, e.g. [2, 12, 13, 9, 1, 27].sort() returns -[1, 12, 13, 2, 27, 9] -*/ -function sortAlphaNumeric(a, b) { - const aRoute = a.properties.name; - const bRoute = b.properties.name; - const aInteger = parseInt(aRoute, 10); - const bInteger = parseInt(bRoute, 10); - const aAlpha = aRoute.replace(notAlpha, ''); - const bAlpha = bRoute.replace(notAlpha, ''); - - // special case for K/T and K-OWL - if (aRoute === 'K/T' && bRoute === 'K-OWL') return -1; - if (aRoute === 'K-OWL' && bRoute === 'K/T') return 1; - - if (Number.isNaN(aInteger) && Number.isNaN(bInteger)) { - return aAlpha < bAlpha ? -1 : 1; - } else if (Number.isNaN(aInteger)) { - return -1; - } else if (Number.isNaN(bInteger)) { - return 1; - } else if (aInteger === bInteger) { - return aAlpha < bAlpha ? -1 : 1; - } - return aInteger - bInteger; -} - +import { sortAlphaNumeric } from './Util'; // make a copy of routes and sort const sortedRoutes = muniRoutesGeoJson.features.slice(0).sort(sortAlphaNumeric); +const liveDataInterval = 15000; class ControlPanel extends Component { constructor() { super(); this.state = { currentStateTime: new Date(Date.now()), + liveMap: false, }; } setNewStateTime(newStateTime) { this.setState({ currentStateTime: newStateTime }); - this.props.relay.refetch( - { - startTime: Number(newStateTime) - 15000, - endTime: Number(newStateTime), - agency: 'muni', - }, - null, - (err) => { - if (err) { - console.warn(err); - } - }, - { force: true }, - ); + this.props.fetchData(newStateTime, liveDataInterval); + } + + handleLiveData() { + setTimeout(() => { + this.setNewStateTime(new Date()); + }, liveDataInterval); } render() { + const { liveMap } = this.state; + if (liveMap) { + this.handleLiveData(); + } return (
@@ -78,10 +44,17 @@ class ControlPanel extends Component { onChange={newTime => this.setNewStateTime(newTime)} />
+
+

Live Mode

+ this.setState({ liveMap: !liveMap })} + /> +

Stops

this.props.toggleStops()} />
@@ -104,9 +77,9 @@ class ControlPanel extends Component { } ControlPanel.propTypes = { - relay: propTypes.element.isRequired, filterRoutes: propTypes.element.isRequired, toggleStops: propTypes.element.isRequired, + fetchData: propTypes.element.isRequired, }; export default ControlPanel; diff --git a/src/Map.jsx b/src/Map.jsx index d90d13c..6d1c3ba 100644 --- a/src/Map.jsx +++ b/src/Map.jsx @@ -171,6 +171,23 @@ class Map extends Component { this.setState({ showStops: !this.state.showStops }); } + fetchData(newStateTime, liveDataInterval) { + this.props.relay.refetch( + { + startTime: Number(newStateTime) - liveDataInterval, + endTime: Number(newStateTime), + agency: 'muni', + }, + null, + (err) => { + if (err) { + console.warn(err); + } + }, + { force: true }, + ); + } + renderMap() { const onViewportChange = viewport => this.setState({ viewport }); const { trynState } = this.props.trynState || {}; @@ -243,7 +260,12 @@ class Map extends Component { {this.renderMap()}
- + + this.fetchData(newStateTime, liveDataInterval)} + />
@@ -256,6 +278,7 @@ Map.propTypes = { propTypes.string, propTypes.arrayOf(propTypes.object), ).isRequired, + relay: propTypes.element.isRequired, }; export default createRefetchContainer( diff --git a/src/Util.js b/src/Util.js new file mode 100644 index 0000000..5a29008 --- /dev/null +++ b/src/Util.js @@ -0,0 +1,51 @@ +/* +* Stop class used to handle info about selected stops +*/ +export class Stop { + constructor(stop) { + this.stop = stop; + } + isUndefined() { + return typeof this.stop === 'undefined'; + } + setCoordinates(coordinates) { + this.stop = { + lon: coordinates[0], + lat: coordinates[1], + }; + } + getCoordinateArray() { + return [this.stop.lon, this.stop.lat]; + } + /** + * sees if two stops are equal by evaluating their coordinates + */ + equals(stop) { + return this.stop.lon === stop.lon && this.stop.lat === stop.lat; + } +} + +export function sortAlphaNumeric(a, b) { + const notAlpha = /[^a-zA-Z]/g; + const aRoute = a.properties.name; + const bRoute = b.properties.name; + const aInteger = parseInt(aRoute, 10); + const bInteger = parseInt(bRoute, 10); + const aAlpha = aRoute.replace(notAlpha, ''); + const bAlpha = bRoute.replace(notAlpha, ''); + + // special case for K/T and K-OWL + if (aRoute === 'K/T' && bRoute === 'K-OWL') return -1; + if (aRoute === 'K-OWL' && bRoute === 'K/T') return 1; + + if (Number.isNaN(aInteger) && Number.isNaN(bInteger)) { + return aAlpha < bAlpha ? -1 : 1; + } else if (Number.isNaN(aInteger)) { + return -1; + } else if (Number.isNaN(bInteger)) { + return 1; + } else if (aInteger === bInteger) { + return aAlpha < bAlpha ? -1 : 1; + } + return aInteger - bInteger; +}