diff --git a/__tests__/components/viewers/__snapshots__/nearby-view.js.snap b/__tests__/components/viewers/__snapshots__/nearby-view.js.snap index 65c9368a3..629be1f50 100644 --- a/__tests__/components/viewers/__snapshots__/nearby-view.js.snap +++ b/__tests__/components/viewers/__snapshots__/nearby-view.js.snap @@ -35,6 +35,7 @@ exports[`components > viewers > nearby view renders nothing on a blank page 1`] fetchNearby={[Function]} homeTimezone="America/Los_Angeles" nearby={Array []} + routeSortComparator={[Function]} setHighlightedLocation={[Function]} setLocation={[Function]} setMainPanelContent={[Function]} @@ -57,44 +58,50 @@ exports[`components > viewers > nearby view renders nothing on a blank page 1`] title="components.NearbyView.header" /> -

- - components.NearbyView.nearbyListIntro - -

+ + components.NearbyView.nearbyListIntro + + +
    -
    @@ -4069,6 +4076,7 @@ exports[`components > viewers > nearby view renders proper scooter dates 1`] = ` }, ] } + routeSortComparator={[Function]} setHighlightedLocation={[Function]} setLocation={[Function]} setMainPanelContent={[Function]} @@ -4091,44 +4099,50 @@ exports[`components > viewers > nearby view renders proper scooter dates 1`] = ` title="components.NearbyView.header" /> -

    - - components.NearbyView.nearbyListIntro - -

    + + components.NearbyView.nearbyListIntro + + +
      -
    1. viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.realtime" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > viewers > nearby view renders proper scooter dates 1`] = ` title="components.StopTimeCell.scheduled" > viewers > nearby view renders proper scooter dates 1`] = ` > { + const { currentPosition } = this.props + if (!currentPosition.coords) return true + const latChanged = + Math.abs( + position?.coords?.latitude - currentPosition?.coords?.latitude + ) >= 0.001 + const lonChanged = + Math.abs( + position?.coords?.longitude - currentPosition?.coords?.longitude + ) >= 0.001 + + return latChanged || lonChanged + } + /* eslint-disable-next-line complexity */ componentDidUpdate(prevProps) { const { @@ -179,11 +197,13 @@ class ResponsiveWebapp extends Component { if (isMobile()) { // Test location availability on load getCurrentPosition(intl) - // Also, watch for changes in position on mobile + // Watch for position changing on mobile navigator.geolocation.watchPosition( // On success (position) => { - receivedPositionResponse({ position }) + if (this.positionShouldUpdate(position)) { + receivedPositionResponse({ position }) + } }, // On error (error) => { @@ -426,10 +446,12 @@ class RouterWrapperWithAuth0 extends Component { } const mapStateToWrapperProps = (state) => { - const { homeTimezone, map, persistence, reactRouter } = state.otp.config + const { homeTimezone, location, map, persistence, reactRouter } = + state.otp.config return { auth0Config: getAuth0Config(persistence), autoFly: map.autoFlyOnTripFormUpdate, + currentPosition: location?.currentPosition, defaultLocale: getDefaultLocale(state.otp.config, state.user.loggedInUser), homeTimezone, locale: state.otp.ui.locale, diff --git a/lib/components/mobile/navigation-bar.js b/lib/components/mobile/navigation-bar.js index 1e7b0079c..a31e75d02 100644 --- a/lib/components/mobile/navigation-bar.js +++ b/lib/components/mobile/navigation-bar.js @@ -64,7 +64,7 @@ class MobileNavigationBar extends Component { const backButtonText = intl.formatMessage({ id: 'common.forms.back' }) return ( -
      +
      diff --git a/lib/components/viewers/nearby/nearby-view.tsx b/lib/components/viewers/nearby/nearby-view.tsx index 1405f9eae..be54085ae 100644 --- a/lib/components/viewers/nearby/nearby-view.tsx +++ b/lib/components/viewers/nearby/nearby-view.tsx @@ -2,14 +2,21 @@ import { connect } from 'react-redux' import { FormattedMessage, useIntl } from 'react-intl' import { Location } from '@opentripplanner/types' import { MapRef, useMap } from 'react-map-gl' -import React, { useCallback, useEffect, useMemo, useRef, useState } from 'react' +import coreUtils from '@opentripplanner/core-utils' +import React, { useCallback, useEffect, useMemo, useState } from 'react' import * as apiActions from '../../../actions/api' import * as mapActions from '../../../actions/map' import * as uiActions from '../../../actions/ui' import { AppReduxState } from '../../../util/state-types' import { getCurrentServiceWeek } from '../../../util/current-service-week' -import { SetLocationHandler, ZoomToPlaceHandler } from '../../util/types' +import { NearbyViewConfig } from '../../../util/config-types' +import { + PatternStopTime, + SetLocationHandler, + ZoomToPlaceHandler +} from '../../util/types' +import InvisibleA11yLabel from '../../util/invisible-a11y-label' import Loading from '../../narrative/loading' import MobileContainer from '../../mobile/container' import MobileNavigationBar from '../../mobile/navigation-bar' @@ -23,11 +30,11 @@ import { } from './styled' import FromToPicker from './from-to-picker' import RentalStation from './rental-station' -import Stop from './stop' +import Stop, { fullTimestamp, patternArrayforStops } from './stop' import Vehicle from './vehicle-rent' import VehicleParking from './vehicle-parking' -const AUTO_REFRESH_INTERVAL = 15000 +const AUTO_REFRESH_INTERVAL = 15000000 // TODO: use lonlat package type LatLonObj = { lat: number; lon: number } @@ -48,9 +55,12 @@ type Props = { hideBackButton?: boolean location: string mobile?: boolean + // Todo: type nearby results nearby: any + nearbyViewConfig?: NearbyViewConfig nearbyViewCoords?: LatLonObj radius?: number + routeSortComparator: (a: PatternStopTime, b: PatternStopTime) => number setHighlightedLocation: (location: Location | null) => void setLocation: SetLocationHandler setMainPanelContent: (content: number) => void @@ -117,8 +127,10 @@ function NearbyView({ location, mobile, nearby, + nearbyViewConfig, nearbyViewCoords, radius, + routeSortComparator, setHighlightedLocation, setMainPanelContent, setViewedNearbyCoords, @@ -127,7 +139,6 @@ function NearbyView({ const map = useMap().default const intl = useIntl() const [loading, setLoading] = useState(true) - const firstItemRef = useRef(null) const finalNearbyCoords = useMemo( () => getNearbyCoordsFromUrlOrLocationOrMapCenter( @@ -179,9 +190,11 @@ function NearbyView({ }, [map, setViewedNearbyCoords, setHighlightedLocation]) useEffect(() => { - if (typeof firstItemRef.current?.scrollIntoView === 'function') { - firstItemRef.current?.scrollIntoView({ behavior: 'smooth' }) - } + window.scrollTo({ + behavior: 'smooth', + left: 0, + top: 0 + }) if (finalNearbyCoords) { fetchNearby(finalNearbyCoords, radius, currentServiceWeek) setLoading(true) @@ -222,9 +235,19 @@ function NearbyView({ .flat(Infinity) ) ) + + // If configured, filter out stops that don't have any patterns + const filteredNearby = nearby?.filter((n: any) => { + if (n.place.__typename === 'Stop' && nearbyViewConfig?.hideEmptyStops) { + const patternArray = patternArrayforStops(n.place, routeSortComparator) + return !(patternArray?.length === 0) + } + return true + }) + const nearbyItemList = - nearby?.map && - nearby?.map((n: any) => ( + filteredNearby?.map && + filteredNearby?.map((n: any) => (
    2. { if (!staleData) { setLoading(false) + } else if (staleData) { + // If there's stale data, fetch again + setLoading(true) + finalNearbyCoords && + fetchNearby(finalNearbyCoords, radius, currentServiceWeek) } }, [nearby, staleData]) @@ -273,19 +301,17 @@ function NearbyView({ /> )} {nearby && ( -

      + -

      + )} - {/* This is used to scroll to top */} -
      {loading && ( @@ -295,7 +321,7 @@ function NearbyView({ !staleData && (nearby.error ? ( intl.formatMessage({ id: 'components.NearbyView.error' }) - ) : nearby.length > 0 ? ( + ) : filteredNearby?.length > 0 ? ( nearbyItemList ) : ( @@ -308,7 +334,8 @@ function NearbyView({ const mapStateToProps = (state: AppReduxState) => { const { config, location, transitIndex, ui } = state.otp - const { map, routeViewer } = config + const { map, nearbyView: nearbyViewConfig, routeViewer } = config + const transitOperators = config?.transitOperators || [] const { nearbyViewCoords } = ui const { nearby } = transitIndex const { entityId } = state.router.location.query @@ -321,6 +348,20 @@ const mapStateToProps = (state: AppReduxState) => { ? getCurrentServiceWeek() : undefined + // TODO: Refine so we don't have this same thing in stops.tsx + // Default sort: departure time + let routeSortComparator = (a: PatternStopTime, b: PatternStopTime) => + fullTimestamp(a.stoptimes?.[0]) - fullTimestamp(b.stoptimes?.[0]) + + if (nearbyViewConfig?.useRouteViewSort) { + routeSortComparator = (a: PatternStopTime, b: PatternStopTime) => + coreUtils.route.makeRouteComparator(transitOperators)( + // @ts-expect-error core-utils types are wrong! + a.pattern.route, + b.pattern.route + ) + } + return { currentPosition, currentServiceWeek, @@ -330,8 +371,10 @@ const mapStateToProps = (state: AppReduxState) => { homeTimezone: config.homeTimezone, location: state.router.location.hash, nearby: nearby?.data, + nearbyViewConfig, nearbyViewCoords, - radius: config.nearbyView?.radius + radius: config.nearbyView?.radius, + routeSortComparator } } diff --git a/lib/components/viewers/nearby/stop.tsx b/lib/components/viewers/nearby/stop.tsx index c98d288c1..973f8ddb3 100644 --- a/lib/components/viewers/nearby/stop.tsx +++ b/lib/components/viewers/nearby/stop.tsx @@ -16,7 +16,7 @@ import StopCardHeader from './stop-card-header' const { getUserTimezone } = coreUtils.time -const fullTimestamp = (stoptime: StopTime) => +export const fullTimestamp = (stoptime: StopTime) => (stoptime.serviceDay || 0) + (stoptime.realtimeDeparture || 0) type Props = { @@ -27,14 +27,11 @@ type Props = { stopData: StopData & { nearbyRoutes?: string[] } } -const Stop = ({ - fromToSlot, - homeTimezone, - nearbyViewConfig, - routeSortComparator, - stopData -}: Props): JSX.Element => { - const patternRows = (stopData.stoptimesForPatterns || []) +export const patternArrayforStops = ( + stopData: StopData & { nearbyRoutes?: string[] }, + routeSortComparator: (a: PatternStopTime, b: PatternStopTime) => number +): Array | undefined => { + return stopData?.stoptimesForPatterns ?.reduce((acc, cur) => { const currentHeadsign = extractHeadsignFromPattern(cur.pattern) const dupe = acc.findIndex((p) => { @@ -65,30 +62,40 @@ const Stop = ({ return acc }, []) .sort(routeSortComparator) - .map((st: any, index: number) => { - const sortedStopTimes = st.stoptimes.sort( - (a: StopTime, b: StopTime) => fullTimestamp(a) - fullTimestamp(b) - ) - if ( - // NearbyRoutes if present is populated with a list of routes that appear - // in the current service period. - stopData.nearbyRoutes && - !stopData.nearbyRoutes.includes(st?.pattern?.route?.gtfsId) - ) { - return <> - } - return ( - - ) - }) +} + +const Stop = ({ + fromToSlot, + homeTimezone, + nearbyViewConfig, + routeSortComparator, + stopData +}: Props): JSX.Element => { + const patternArray = patternArrayforStops(stopData, routeSortComparator) + const patternRows = patternArray?.map((st: any, index: number) => { + const sortedStopTimes = st.stoptimes.sort( + (a: StopTime, b: StopTime) => fullTimestamp(a) - fullTimestamp(b) + ) + if ( + // NearbyRoutes if present is populated with a list of routes that appear + // in the current service period. + stopData.nearbyRoutes && + !stopData.nearbyRoutes.includes(st?.pattern?.route?.gtfsId) + ) { + return <> + } + return ( + + ) + }) const inHomeTimezone = homeTimezone && homeTimezone === getUserTimezone() const timezoneWarning = !inHomeTimezone && ( @@ -96,8 +103,6 @@ const Stop = ({ ) - if (nearbyViewConfig?.hideEmptyStops && patternRows.length === 0) return <> - return ( li:last-of-type { + margin-bottom: 1em; + } + + & > li:first-of-type { + margin-top: 1em; + } + + @media (max-width: 768px) { + min-height: calc(100vh - 50px); + } ` export const Card = styled.div` diff --git a/package.json b/package.json index 79c052fed..f211c743e 100644 --- a/package.json +++ b/package.json @@ -51,7 +51,7 @@ "@opentripplanner/humanize-distance": "^1.2.0", "@opentripplanner/icons": "3.0.1", "@opentripplanner/location-field": "3.1.1", - "@opentripplanner/itinerary-body": "6.1.0", + "@opentripplanner/itinerary-body": "6.1.1", "@opentripplanner/location-icon": "^1.4.1", "@opentripplanner/map-popup": "5.1.1", "@opentripplanner/otp2-tile-overlay": "2.1.1", diff --git a/yarn.lock b/yarn.lock index 1c1df6718..1f29a0b0f 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2403,7 +2403,7 @@ maplibre-gl "^2.1.9" react-map-gl "^7.0.15" -"@opentripplanner/building-blocks@2.1.0": +"@opentripplanner/building-blocks@2.1.0", "@opentripplanner/building-blocks@^2.0.0": version "2.1.0" resolved "https://registry.yarnpkg.com/@opentripplanner/building-blocks/-/building-blocks-2.1.0.tgz#20d688dbc7a152256f571562199981099bde7820" integrity sha512-Vnc/W2EGybIbzXXofthGVW8HN1o5ThW1+XjWquVlKlSb2xxruWscstz9frOWlbHg239SEdTpZUuaARwMWflVaA== @@ -2415,12 +2415,7 @@ resolved "https://registry.yarnpkg.com/@opentripplanner/building-blocks/-/building-blocks-1.2.3.tgz#404e8f9038867d66d55f51adf8855b1326c51ed5" integrity sha512-I0AxiZrTZu+e7+av4u0tHW2ijqpxH0AkLHrhf75BHf1Ep2FOGxaul/v+8UT18mNYiM5eHNstOX3XiXaDjtCUaw== -"@opentripplanner/building-blocks@^2.0.0": - version "2.0.0" - resolved "https://registry.yarnpkg.com/@opentripplanner/building-blocks/-/building-blocks-2.0.0.tgz#8282c01dff7db5c7e809f6ea91cb52df559a2f9d" - integrity sha512-N07rDaZL8fp552eI9/0j1udKjc0uOpvO0Wv1P19Ge0a4roques463MJgWJ026fbopRCi3uwbc/gYTlh4/ske9A== - -"@opentripplanner/core-utils@12.0.1": +"@opentripplanner/core-utils@12.0.1", "@opentripplanner/core-utils@^12.0.0": version "12.0.1" resolved "https://registry.yarnpkg.com/@opentripplanner/core-utils/-/core-utils-12.0.1.tgz#2bafb78133393213b4943c76fec5d46436c0fb6d" integrity sha512-QUTxEcpiOnbqaoiu6RQngTLlQHjSHO4PCMJqR9IRiaei08FnlTx2jgpvIaRla6u7tRNr12YCzptc37+a10ryww== @@ -2456,24 +2451,6 @@ lodash.isequal "^4.5.0" qs "^6.9.1" -"@opentripplanner/core-utils@^12.0.0": - version "12.0.0" - resolved "https://registry.yarnpkg.com/@opentripplanner/core-utils/-/core-utils-12.0.0.tgz#cc40af92620b207f4dce817d08f99def0cdaea7a" - integrity sha512-udLF8XU+k7gxZ+yyyw7ASz6/4D540zYIv8a9GbUL61TF8HmgGhcMk3XOgBnm5jdOukuaNNpOFE4J3oJc5QsSBQ== - dependencies: - "@conveyal/lonlat" "^1.4.1" - "@mapbox/polyline" "^1.1.0" - "@opentripplanner/geocoder" "^3.0.2" - "@styled-icons/foundation" "^10.34.0" - "@turf/along" "^6.0.1" - chroma-js "^2.4.2" - date-fns "^2.28.0" - date-fns-tz "^1.2.2" - graphql "^16.6.0" - lodash.clonedeep "^4.5.0" - lodash.isequal "^4.5.0" - qs "^6.9.1" - "@opentripplanner/endpoints-overlay@3.0.1": version "3.0.1" resolved "https://registry.yarnpkg.com/@opentripplanner/endpoints-overlay/-/endpoints-overlay-3.0.1.tgz#b6b8e2f08ae41fbaad475fc0f0fe3e72d7d36463" @@ -2518,7 +2495,7 @@ resolved "https://registry.yarnpkg.com/@opentripplanner/humanize-distance/-/humanize-distance-1.2.0.tgz#71cf5d5d1b756adef15300edbba0995ccd4b35ee" integrity sha512-x0QRXMDhypFeazZ6r6vzrdU8vhiV56nZ/WX6zUbxpgp6T9Oclw0gwR2Zdw6DZiiFpSYVNeVNxVzZwsu6NRGjcA== -"@opentripplanner/icons@3.0.1": +"@opentripplanner/icons@3.0.1", "@opentripplanner/icons@^3.0.0": version "3.0.1" resolved "https://registry.yarnpkg.com/@opentripplanner/icons/-/icons-3.0.1.tgz#62cf5ffd9ad42c5ba2ac64cf91e9f10c8300ff1e" integrity sha512-pu96GWVR2ef6aMPPJRjdzHkIVlENGa3LRlqNaW3PEZQLjycsCsT1ZpJ6+zKwVfZsgoMl1L8mx2qjLO4RUZzGAA== @@ -2534,18 +2511,10 @@ "@opentripplanner/core-utils" "^11.4.4" prop-types "^15.7.2" -"@opentripplanner/icons@^3.0.0": - version "3.0.0" - resolved "https://registry.yarnpkg.com/@opentripplanner/icons/-/icons-3.0.0.tgz#f7293fd4dd2625eace3a4c82ecd573d6000d85d3" - integrity sha512-naSCdCsPwSyEiP7Vf6oN6dpgwpFIkeQFXfTJG7lp1Dg9emLTAYzRx/f+45e9Bh0zP0aA4DsN4VgHBQllyu82qQ== - dependencies: - "@opentripplanner/core-utils" "^11.4.4" - prop-types "^15.7.2" - -"@opentripplanner/itinerary-body@6.1.0": - version "6.1.0" - resolved "https://registry.yarnpkg.com/@opentripplanner/itinerary-body/-/itinerary-body-6.1.0.tgz#8a1399e8dc15b6918ede51a0f263519e4b891415" - integrity sha512-nv42+hJavdVS5nHtKLDv1Um04patzGD+/xh3zApgxpB9xG/D2Zy4JBqbyMtZ1eHKF4JYkmm+NsAq/7043WPXGA== +"@opentripplanner/itinerary-body@6.1.1", "@opentripplanner/itinerary-body@^6.0.0": + version "6.1.1" + resolved "https://registry.yarnpkg.com/@opentripplanner/itinerary-body/-/itinerary-body-6.1.1.tgz#7b7b2af038a683f785d43245c336180f1b324436" + integrity sha512-ULMwZSGBkAGtuJfBO7vjtTEsXvS06l65FSMTcxarY1322G7dvFUMOKmMJ626EdwCGUcw9J1R7JfS0uV3uUv2Ag== dependencies: "@opentripplanner/core-utils" "^12.0.0" "@opentripplanner/humanize-distance" "^1.2.0" @@ -2582,24 +2551,6 @@ version "3.1.1" resolved "https://registry.yarnpkg.com/@opentripplanner/location-field/-/location-field-3.1.1.tgz#0658df4cfd47866153c8ae33fd60e991cdf94df0" integrity sha512-Q9yhi3AVlnj8izrpJvxN+uVBjjtEDyFXUsJ0VhE9zevVpGzCh/gcGNzJY5EnP2IRDd/Szx6dPUogt3XJlHkHTQ== - -"@opentripplanner/itinerary-body@^6.0.0": - version "6.0.3" - resolved "https://registry.yarnpkg.com/@opentripplanner/itinerary-body/-/itinerary-body-6.0.3.tgz#84573d20ac9cc1fc7f2d2e032fac5a072ac3e142" - integrity sha512-1qrH8hpR5Rr9KMGNnajI7GJyuoV+rogmyGqd5Z5DErZGp4luVzksIsnyW1IbxRslnV3bqKll+DH8lTXy4QIyZg== - dependencies: - "@opentripplanner/core-utils" "^12.0.0" - "@opentripplanner/humanize-distance" "^1.2.0" - "@opentripplanner/icons" "^3.0.0" - "@opentripplanner/location-icon" "^1.4.1" - "@styled-icons/fa-solid" "^10.34.0" - "@styled-icons/foundation" "^10.34.0" - date-fns "^2.28.0" - date-fns-tz "^1.2.2" - flat "^5.0.2" - react-animate-height "^3.0.4" - react-resize-detector "^4.2.1" - string-similarity "^4.0.4" dependencies: "@conveyal/geocoder-arcgis-geojson" "^0.0.3" "@opentripplanner/core-utils" "^12.0.0" @@ -2617,7 +2568,7 @@ "@styled-icons/fa-regular" "^10.34.0" "@styled-icons/fa-solid" "^10.34.0" -"@opentripplanner/map-popup@5.1.1": +"@opentripplanner/map-popup@5.1.1", "@opentripplanner/map-popup@^v5.1.0": version "5.1.1" resolved "https://registry.yarnpkg.com/@opentripplanner/map-popup/-/map-popup-5.1.1.tgz#f4699b63a2ba0fae6263f2417c5b85f5ffc204cb" integrity sha512-HifqZFmrBy3FmARVKZwUnad8U/L8ftBm2PcSck4oGQ768E7TKhqyzXz+GzkO39TyKNU5yiNgmQEbss8elZuJ/g== @@ -2639,17 +2590,6 @@ "@opentripplanner/from-to-location-picker" "^2.1.14" flat "^5.0.2" -"@opentripplanner/map-popup@^v5.1.0": - version "5.1.0" - resolved "https://registry.yarnpkg.com/@opentripplanner/map-popup/-/map-popup-5.1.0.tgz#cf6374bf7b69af69c026ec414a84719078c56e9e" - integrity sha512-EShoMyFZa7Zb2ZZrJhEsJfuCAvs2jfQe5QstU+AEk5Jm1zc8LzU6PsXmizQ/RMVi6zIYLhlBoZ3u458tTA3VQA== - dependencies: - "@opentripplanner/base-map" "^4.0.0" - "@opentripplanner/building-blocks" "^2.0.0" - "@opentripplanner/core-utils" "^12.0.0" - "@opentripplanner/from-to-location-picker" "^3.0.0" - flat "^5.0.2" - "@opentripplanner/otp2-tile-overlay@2.1.1": version "2.1.1" resolved "https://registry.yarnpkg.com/@opentripplanner/otp2-tile-overlay/-/otp2-tile-overlay-2.1.1.tgz#3bd2f26caa01181eb4ca90bbd05ce784f9b05a7a" @@ -4329,9 +4269,9 @@ acorn@^7.0.0, acorn@^7.1.0, acorn@^7.1.1, acorn@^7.4.0: integrity sha512-nQyp0o1/mNdbTO1PO6kHkwSrmgZ0MT/jCCpNiwbUjGoRN4dlBhqJtoQuCnEOKzgTVwg0ZWiCoQy6SxMebQVh8A== acorn@^8.2.4: - version "8.4.1" - resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.4.1.tgz#56c36251fc7cabc7096adc18f05afe814321a28c" - integrity sha512-asabaBSkEKosYKMITunzX177CXxQ4Q8BSSzMTKD+FefUhipQC70gfW5SiUDhYQ3vk8G+81HqQk7Fv9OXwwn9KA== + version "8.14.0" + resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.14.0.tgz#063e2c70cac5fb4f6467f0b11152e04c682795b0" + integrity sha512-cl669nCJTZBsL97OF4kUQm5g5hC2uihk0NxY3WENAC0TYdILVkAyHymAntgxGkl7K+t0cXIrH5siy5S4XkFycA== address@1.1.2, address@^1.0.1: version "1.1.2" @@ -15617,17 +15557,7 @@ react-transition-group@^2.0.0, react-transition-group@^2.2.0: prop-types "^15.6.2" react-lifecycles-compat "^3.0.4" -react-transition-group@^4.3.0: - version "4.4.2" - resolved "https://registry.yarnpkg.com/react-transition-group/-/react-transition-group-4.4.2.tgz#8b59a56f09ced7b55cbd53c36768b922890d5470" - integrity sha512-/RNYfRAMlZwDSr6z4zNKV6xu53/e2BuaBbGhbyYIXTrmgu/bGHzmqOs7mJSJBHy9Ud+ApHx3QjrkKSp1pxvlFg== - dependencies: - "@babel/runtime" "^7.5.5" - dom-helpers "^5.0.1" - loose-envify "^1.4.0" - prop-types "^15.6.2" - -react-transition-group@^4.4.5: +react-transition-group@^4.3.0, react-transition-group@^4.4.5: version "4.4.5" resolved "https://registry.yarnpkg.com/react-transition-group/-/react-transition-group-4.4.5.tgz#e53d4e3f3344da8521489fbef8f2581d42becdd1" integrity sha512-pZcd1MCJoiKiBR2NRxeCRg13uCXbydPnmB4EOeRrY7480qNWO8IIgQG6zlDkm6uRMsURXPuKq0GWtiM59a5Q6g== @@ -19036,7 +18966,7 @@ write-file-atomic@^3.0.0, write-file-atomic@^3.0.3: signal-exit "^3.0.2" typedarray-to-buffer "^3.1.5" -ws@7.4.6, ws@^7.4.6: +ws@7.4.6: version "7.4.6" resolved "https://registry.yarnpkg.com/ws/-/ws-7.4.6.tgz#5654ca8ecdeee47c33a9a4bf6d28e2be2980377c" integrity sha512-YmhHDO4MzaDLB+M9ym/mDA5z0naX8j7SIlT8f8z+I0VtzsRbekxEutHSme7NPS2qE8StCYQNUnfWdXta/Yu85A== @@ -19048,6 +18978,11 @@ ws@^6.2.1: dependencies: async-limiter "~1.0.0" +ws@^7.4.6: + version "7.5.10" + resolved "https://registry.yarnpkg.com/ws/-/ws-7.5.10.tgz#58b5c20dc281633f6c19113f39b349bd8bd558d9" + integrity sha512-+dbF1tHwZpXcbOJdVOkzLDxZP1ailvSxM6ZweXTegylPny803bFhA+vqBYw4s31NSAk4S2Qz+AKXK9a4wkdjcQ== + ws@^8.0.0: version "8.5.0" resolved "https://registry.yarnpkg.com/ws/-/ws-8.5.0.tgz#bfb4be96600757fe5382de12c670dab984a1ed4f"