Skip to content

Commit

Permalink
basic map functionality implementation using google maps api, hardcod…
Browse files Browse the repository at this point in the history
…ed geocoordinates
  • Loading branch information
jamesdoh0109 committed Oct 5, 2024
1 parent 68a3aec commit 912d326
Show file tree
Hide file tree
Showing 7 changed files with 165 additions and 20 deletions.
96 changes: 96 additions & 0 deletions frontend/plan/components/modals/MapModal.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
import React, { useState, useEffect } from "react";
import { GeoLocation } from "../../types";
import {
APIProvider,
Map,
Marker,
useMap,
useMapsLibrary,
} from "@vis.gl/react-google-maps";

interface MapModalProps {
src: GeoLocation;
tgt?: GeoLocation;
}

interface DirectionsProps {
src: GeoLocation;
tgt: GeoLocation;
}

const MapModal = ({ src, tgt }: MapModalProps) => {
const { latitude: centerLat, longitude: centerLng } = tgt
? {
latitude: (src.latitude + tgt.latitude) / 2,
longitude: (src.longitude + tgt.longitude) / 2,
}
: src;

return (
<APIProvider
apiKey={process.env.NEXT_PUBLIC_GOOGLE_MAPS_API_KEY as string}
>
<Map
style={{ height: "300px" }}
defaultCenter={{ lat: centerLat, lng: centerLng }}
defaultZoom={15}
gestureHandling={"greedy"}
disableDefaultUI={true}
>
{tgt ? (
<Directions src={src} tgt={tgt} />
) : (
<Marker
position={{ lat: src.latitude, lng: src.longitude }}
/>
)}
</Map>
</APIProvider>
);
};

function Directions({ src, tgt }: DirectionsProps) {
const map = useMap();
const routesLibrary = useMapsLibrary("routes");
const [directionsService, setDirectionsService] = useState<
google.maps.DirectionsService
>();
const [directionsRenderer, setDirectionsRenderer] = useState<
google.maps.DirectionsRenderer
>();
const [routes, setRoutes] = useState<google.maps.DirectionsRoute[]>([]);

const leg = routes[0]?.legs[0];

useEffect(() => {
if (!routesLibrary || !map) return;
setDirectionsService(new routesLibrary.DirectionsService());
setDirectionsRenderer(new routesLibrary.DirectionsRenderer({ map }));
}, [routesLibrary, map]);

useEffect(() => {
if (!directionsService || !directionsRenderer) return;

directionsService
.route({
origin: `${src.latitude}, ${src.longitude}`,
destination: `${tgt.latitude}, ${tgt.longitude}`,
travelMode: google.maps.TravelMode.WALKING,
provideRouteAlternatives: false,
})
.then((response) => {
directionsRenderer.setDirections(response);
setRoutes(response.routes);
});
}, [directionsService, directionsRenderer]);

if (!leg) return null;

return (
<div style={{ position: "absolute" }}>
<h2>{leg.duration?.text}</h2>
</div>
);
}

export default MapModal;
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,6 @@ const ModalCardBody = styled.section`
flex-grow: 1;
flex-shrink: 1;
overflow: auto;
padding: 20px;
padding-left: 2rem;
padding-right: 2rem;
padding-bottom: 1.5rem;
Expand Down
7 changes: 7 additions & 0 deletions frontend/plan/components/modals/model_content_generator.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import React from "react";
import dynamic from "next/dynamic";
import {
renameSchedule,
downloadSchedule,
Expand Down Expand Up @@ -28,6 +29,10 @@ import AlertFormModal from "./AlertFormModal";
* @returns A component
*/
export const generateModalInterior = (reduxState) => {
const Map = dynamic(() => import("./MapModal"), {
ssr: false,
});

switch (reduxState.modals.modalKey) {
case "SEMESTER_FETCH_ERROR":
return (
Expand Down Expand Up @@ -102,6 +107,8 @@ export const generateModalInterior = (reduxState) => {
return (
<AlertFormModal contactInfo={reduxState.alerts.contactInfo} />
);
case "MAP":
return <Map />;
default:
return null;
}
Expand Down
20 changes: 11 additions & 9 deletions frontend/plan/components/selector/Section.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ interface SectionProps {
add: () => void;
remove: () => void;
};
toggleMap: {
open: () => void;
};
inCart: boolean;
alerts: {
add: () => void;
Expand Down Expand Up @@ -130,7 +133,7 @@ const HoverSwitch = styled.div`
}
`;

export default function Section({ section, cart, inCart, alerts, inAlerts }: SectionProps) {
export default function Section({ section, cart, inCart, toggleMap, alerts, inAlerts }: SectionProps) {
const { instructors, meetings, status } = section;

const { schedules, scheduleSelected } = useSelector(
Expand Down Expand Up @@ -225,7 +228,9 @@ export default function Section({ section, cart, inCart, alerts, inAlerts }: Sec
style={{ color: "#c6c6c6" }}
/>
&nbsp;
{cleanedRooms.join(", ")}
<span onClick={toggleMap.open} style={{ color: "#878ED8", textDecoration: "underline", cursor: "pointer" }}>
{cleanedRooms.join(", ")}
</span>
</div>
) : null}
</div>
Expand All @@ -246,17 +251,14 @@ export default function Section({ section, cart, inCart, alerts, inAlerts }: Sec
</div>
{status === "C" ? (
<div className={`popover is-popover-left`}>
<AlertButton
alerts={alerts}
inAlerts={inAlerts}
/>

{inAlerts ||
<AlertButton alerts={alerts} inAlerts={inAlerts} />

{inAlerts || (
<span className="popover-content">
{" "}
Course is closed. Sign up for an alert!{" "}
</span>
}
)}
</div>
) : (
<div />
Expand Down
55 changes: 45 additions & 10 deletions frontend/plan/components/selector/SectionList.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,13 @@ import styled from "styled-components";
import { connect } from "react-redux";
import Section from "./Section";
import { Section as SectionType, Alert as AlertType } from "../../types";
import { addCartItem, openModal, deleteAlertItem, removeCartItem, deactivateAlertItem } from "../../actions";
import {
addCartItem,
openModal,
deleteAlertItem,
removeCartItem,
deactivateAlertItem,
} from "../../actions";

interface SectionListProps {
sections: SectionType[];
Expand All @@ -22,8 +28,9 @@ interface SectionListDispatchProps {
) => { add: () => void; remove: () => void };
manageAlerts: (
section: SectionType,
alerts: AlertType[],
alerts: AlertType[]
) => { add: () => void; remove: () => void };
toggleMap: (section: SectionType) => { open: () => void };
onContactInfoChange: (email: string, phone: string) => void;
}

Expand All @@ -37,15 +44,18 @@ function SectionList({
sections,
cartSections,
manageCart,
toggleMap,
alerts,
manageAlerts,
view,
}: SectionListProps & SectionListStateProps & SectionListDispatchProps) {
const isInCart = ({ id }: SectionType) => cartSections.indexOf(id) !== -1;
const isInAlerts = ({ id }: SectionType) => alerts
.filter((alert: AlertType) => alert.cancelled === false)
.map((alert: AlertType) => alert.section)
.indexOf(id) !== -1;
const isInAlerts = ({ id }: SectionType) =>
alerts
.filter((alert: AlertType) => alert.cancelled === false)
.map((alert: AlertType) => alert.section)
.indexOf(id) !== -1;
console.log(sections);
return (
<ResultsContainer>
<ul>
Expand All @@ -55,6 +65,7 @@ function SectionList({
section={s}
cart={manageCart(s)}
inCart={isInCart(s)}
toggleMap={toggleMap(s)}
alerts={manageAlerts(s, alerts)}
inAlerts={isInAlerts(s)}
/>
Expand All @@ -77,13 +88,37 @@ const mapDispatchToProps = (dispatch: (payload: any) => void) => ({
}),
manageAlerts: (section: SectionType, alerts: AlertType[]) => ({
add: () => {
const alertId = alerts.find((a: AlertType) => a.section === section.id)?.id;
dispatch(openModal("ALERT_FORM", { sectionId: section.id, alertId: alertId }, "Sign up for Alerts"))
const alertId = alerts.find(
(a: AlertType) => a.section === section.id
)?.id;
dispatch(
openModal(
"ALERT_FORM",
{ sectionId: section.id, alertId: alertId },
"Sign up for Alerts"
)
);
},
remove: () => {
const alertId = alerts.find((a: AlertType) => a.section === section.id)?.id;
const alertId = alerts.find(
(a: AlertType) => a.section === section.id
)?.id;
dispatch(deactivateAlertItem(section.id, alertId));
}
},
}),
toggleMap: (section: SectionType) => ({
open: () => {
dispatch(
openModal(
"MAP",
{
src: { latitude: 39.95302, longitude: -75.19815 },
// tgt: { latitude: 39.95184, longitude: -75.19092 },
}, // hard-coded for now
`LOCATION FOR ${section.id}`
)
);
},
}),
});

Expand Down
1 change: 1 addition & 0 deletions frontend/plan/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
"@types/react-dom": "^18.2.0",
"@types/react-swipeable-views": "^0.13.0",
"@typescript-eslint/parser": "^4.7.0",
"@vis.gl/react-google-maps": "^1.3.0",
"awesome-debounce-promise": "^2.1.0",
"bulma": "^0.7.5",
"bulma-extensions": "^6.2.7",
Expand Down
5 changes: 5 additions & 0 deletions frontend/plan/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -227,4 +227,9 @@ export type FilterType =

export interface ColorsMap {
[key: string]: Color
}

export type GeoLocation = {
latitude: number;
longitude: number;
}

0 comments on commit 912d326

Please sign in to comment.