From 1f39cfb55b63561b056e2d2dd1afb5ac1fb70014 Mon Sep 17 00:00:00 2001 From: mertbagt Date: Thu, 2 Jul 2026 15:59:50 -0400 Subject: [PATCH 1/7] update browser tab title --- pages/legislators/[court]/[memberCode].tsx | 20 ++++++++++++++------ 1 file changed, 14 insertions(+), 6 deletions(-) diff --git a/pages/legislators/[court]/[memberCode].tsx b/pages/legislators/[court]/[memberCode].tsx index 5824626c9..d4dc9e441 100644 --- a/pages/legislators/[court]/[memberCode].tsx +++ b/pages/legislators/[court]/[memberCode].tsx @@ -1,8 +1,9 @@ import { GetServerSideProps } from "next" import { serverSideTranslations } from "next-i18next/serverSideTranslations" import { z } from "zod" -import { LegislatorProfilePage } from "components/LegislatorProfile" + import { flags } from "components/featureFlags" +import { LegislatorProfilePage } from "components/LegislatorProfile" import { createPage } from "components/page" const Query = z.object({ @@ -14,10 +15,10 @@ export default createPage<{ court: number memberCode: string }>({ - titleI18nKey: "titles.legislatorProfile", - Page: ({ court, memberCode }) => ( - - ) + titleI18nKey: "navigation.legislator", + Page: ({ court, memberCode }) => { + return + } }) export const getServerSideProps: GetServerSideProps = async ctx => { @@ -38,7 +39,14 @@ export const getServerSideProps: GetServerSideProps = async ctx => { return { props: { ...query.data, - ...(await serverSideTranslations(locale, ["auth", "common", "footer"])) + ...(await serverSideTranslations(locale, [ + "auth", + "common", + "footer", + "legislators", + "profile", + "testimony" + ])) } } } From 90f9273ec0b5a8c938a0b8a77eb5e271c99eb7e1 Mon Sep 17 00:00:00 2001 From: mertbagt Date: Thu, 2 Jul 2026 16:26:34 -0400 Subject: [PATCH 2/7] directory path --- .../LegislatorProfilePage.tsx | 33 +++++++++++++++++-- pages/legislators/[court]/[memberCode].tsx | 6 ++-- 2 files changed, 34 insertions(+), 5 deletions(-) diff --git a/components/LegislatorProfile/LegislatorProfilePage.tsx b/components/LegislatorProfile/LegislatorProfilePage.tsx index 34a0d4ed8..b32490447 100644 --- a/components/LegislatorProfile/LegislatorProfilePage.tsx +++ b/components/LegislatorProfile/LegislatorProfilePage.tsx @@ -1,8 +1,14 @@ +import { faChevronRight } from "@fortawesome/free-solid-svg-icons" +import { FontAwesomeIcon } from "@fortawesome/react-fontawesome" import ErrorPage from "next/error" +import { useTranslation } from "next-i18next" import styled from "styled-components" + +import { DistrictTab } from "./DistrictTab" + import { Col, Container, Row, Spinner } from "components/bootstrap" import { useDistrict, useMember } from "components/db" -import { DistrictTab } from "./DistrictTab" +import { Internal } from "components/links" const tabs = [ "Priorities", @@ -14,6 +20,12 @@ const tabs = [ "Votes" ] +const DirectoryPath = styled.div.attrs(props => ({ + className: `align-items-center d-flex flex-nowrap ${props.className}` +}))` + font-size: 12px; +` + const TabButton = styled.button` background: transparent; border: 0; @@ -42,6 +54,7 @@ export function LegislatorProfilePage({ member?.Branch, member?.District ) + const { t } = useTranslation("legislators") if (memberLoading) { return ( @@ -55,8 +68,24 @@ export function LegislatorProfilePage({ return } + console.log("member: ", member) + return ( - + + + + {t("home")} + + + + {/* update with link to legistators search page when online */} +
{t("legislators")}
+ {/* */} + + +
{member.Name}
+
+

{member.Name}

diff --git a/pages/legislators/[court]/[memberCode].tsx b/pages/legislators/[court]/[memberCode].tsx index d4dc9e441..5c6357718 100644 --- a/pages/legislators/[court]/[memberCode].tsx +++ b/pages/legislators/[court]/[memberCode].tsx @@ -16,9 +16,9 @@ export default createPage<{ memberCode: string }>({ titleI18nKey: "navigation.legislator", - Page: ({ court, memberCode }) => { - return - } + Page: ({ court, memberCode }) => ( + + ) }) export const getServerSideProps: GetServerSideProps = async ctx => { From 56e86034ccc95f5c64282fa34674df83cd591df3 Mon Sep 17 00:00:00 2001 From: mertbagt Date: Thu, 2 Jul 2026 20:54:02 -0400 Subject: [PATCH 3/7] legislator header refactored --- .../LegislatorComponents.tsx | 131 ++++++++ .../LegislatorProfilePage.tsx | 306 +++++++++++++++++- components/db/members.ts | 2 + 3 files changed, 433 insertions(+), 6 deletions(-) create mode 100644 components/LegislatorProfile/LegislatorComponents.tsx diff --git a/components/LegislatorProfile/LegislatorComponents.tsx b/components/LegislatorProfile/LegislatorComponents.tsx new file mode 100644 index 000000000..e420630f4 --- /dev/null +++ b/components/LegislatorProfile/LegislatorComponents.tsx @@ -0,0 +1,131 @@ +import { useTranslation } from "next-i18next" +import styled from "styled-components" + +export const formatPhoneNumber = (value: string) => { + if (!value) return value + + const phoneNumber = value.replace(/[^\d]/g, "") + const phoneNumberLength = phoneNumber.length + + // Format as (XXX) XXX-XXXX + if (phoneNumberLength < 4) return phoneNumber + if (phoneNumberLength < 7) { + return `(${phoneNumber.slice(0, 3)}) ${phoneNumber.slice(3)}` + } + return ` + (${phoneNumber.slice(0, 3)}) + ${phoneNumber.slice(3, 6)}- + ${phoneNumber.slice(6, 10)} + ` +} + +/** Party Labels **/ + +const DemocraticBubble = styled.div.attrs(props => ({ + className: `${props.className}` +}))` + background: #d1d6e7; + color: #1a3185; + font-size: 11px; + font-weight: 700; + padding: 1px 10px; + border-radius: 999px; + width: max-content; +` + +const DistrictBubble = styled.div.attrs(props => ({ + className: `ms-1 ${props.className}` +}))` + background: #fff3cd; + color: #856404; + font-size: 11px; + font-weight: 700; + padding: 1px 10px; + border-radius: 999px; + width: max-content; +` + +const IndependantBubble = styled.div.attrs(props => ({ + className: `${props.className}` +}))` + background: #bca0dc; + color: #3c1361; + font-size: 11px; + font-weight: 700; + padding: 1px 10px; + border-radius: 999px; + width: max-content; +` + +const RepublicanBubble = styled.div.attrs(props => ({ + className: `${props.className}` +}))` + background: #f29999; + color: #de0100; + font-size: 11px; + font-weight: 700; + padding: 1px 10px; + border-radius: 999px; + width: max-content; +` + +export function DistrictLabel(props: { district: string }) { + return {props.district} +} + +export function PartyLabel(props: { party: string }) { + const { t } = useTranslation("legislators") + + switch (props.party) { + case "Democrat": + return {t("party.democratic")} + case "Republican": + return {t("party.republican")} + default: + return ( + + {props.party} {t("party.party")} + + ) + } +} + +/** Social Media components **/ + +export function Bluesky() { + return ( + + + + ) +} + +export function LinkedIn() { + return ( + + + + ) +} + +export function Twitter() { + return ( + + + + ) +} diff --git a/components/LegislatorProfile/LegislatorProfilePage.tsx b/components/LegislatorProfile/LegislatorProfilePage.tsx index b32490447..9be5b4cf8 100644 --- a/components/LegislatorProfile/LegislatorProfilePage.tsx +++ b/components/LegislatorProfile/LegislatorProfilePage.tsx @@ -4,11 +4,44 @@ import ErrorPage from "next/error" import { useTranslation } from "next-i18next" import styled from "styled-components" +import * as links from "../links" + import { DistrictTab } from "./DistrictTab" +import { + Bluesky, + DistrictLabel, + formatPhoneNumber, + LinkedIn, + PartyLabel, + Twitter +} from "./LegislatorComponents" import { Col, Container, Row, Spinner } from "components/bootstrap" import { useDistrict, useMember } from "components/db" import { Internal } from "components/links" +import { CircleImage } from "components/shared/LabeledIcon" + +import { doc, getDoc } from "firebase/firestore" +import { useCallback, useEffect, useState } from "react" + +import { usePublicProfile } from "../db" +import { firestore } from "../firebase" + +// import { LegislatorSidebar } from "./SidebarComponents/LegislatorSidebar" +// import { LegislatorTabs } from "./TabComponents/LegislatorTabs" + +import { useAuth } from "components/auth" +import { useFlags } from "components/featureFlags" +import { FollowUserButton } from "components/shared/FollowButton" + +type ProfilePlaceholder = { + social?: { + blueSky?: string + linkedIn?: string + twitter?: string + } + website?: string +} const tabs = [ "Priorities", @@ -20,12 +53,80 @@ const tabs = [ "Votes" ] +const ButtonContainer = styled(Col).attrs(props => ({ + className: `col-12 justify-content-md-end ${props.className}`, + md: `3`, + sm: `4` +}))` + width: max-content; +` + const DirectoryPath = styled.div.attrs(props => ({ className: `align-items-center d-flex flex-nowrap ${props.className}` }))` font-size: 12px; ` +const HeaderBlock = styled.div.attrs(props => ({ + className: `d-flex flex-wrap justify-content-between ${props.className}` +}))` + background-color: white; + border: "1px #ced4da solid"; + border-radius: 5px; + margin-top: 8px; + padding: 16px; +` + +const HeaderName = styled.div` + font-size: 26px; + font-weight: 700; + color: #0b0a3e; +` + +const RoleLine = styled.div.attrs(props => ({ + className: `mb-2 ${props.className}` +}))` + color: #6c757d; + font-size: 14px; +` + +const PhoneNum = styled.span` + color: #6c757d; +` + +const SocialLine = styled.div.attrs(props => ({ + className: `d-flex flex-wrap mb-2 ${props.className}` +}))` + font-size: 12px; + text-decoration: none; +` + +const StatBlock = styled(Col).attrs(props => ({ + className: `d-flex col-4 flex-grow-1 ${props.className}`, + md: `2` +}))` + background-color: white; + border: 1px #ced4da solid; + border-radius: 5px; + margin-top: 4px; + padding: 16px; +` + +const StatLine = styled(Row).attrs(props => ({ + className: `text-nowrap ${props.className}` +}))` + font-size: 12px; +` + +const StatNum = styled.div.attrs(props => ({ + className: `mx-auto ${props.className}` +}))` + color: #1a3185; + font-size: 22px; + font-weight: 700; + width: max-content; +` + const TabButton = styled.button` background: transparent; border: 0; @@ -55,6 +156,23 @@ export function LegislatorProfilePage({ member?.District ) const { t } = useTranslation("legislators") + const { user } = useAuth() + + /* replace with profile info for legislators with Maple accounts */ + let profile: ProfilePlaceholder = { + // social: { + // blueSky: "blueskyTest", + // linkedIn: "linkedinTest", + // twitter: "twitterTest" + // }, + // website: "test.com" + social: { + blueSky: "", + linkedIn: "", + twitter: "" + }, + website: "" + } if (memberLoading) { return ( @@ -86,14 +204,190 @@ export function LegislatorProfilePage({
{member.Name}
- + + + {""} + + -

{member.Name}

-

- {member.Branch} - {member.District} -

+ + + {member.Name} + + + + + {member.Branch == "Senate" ? ( + {t("stateSenator")} + ) : ( + {t("stateRepresentative")} + )} + {/* · Town */} + + +
+ + {/* Incumbent Label */} + +
+ + +
+ + {member.EmailAddress} + +
+ + {profile.website ? ( +
+ · + + {profile.website} + +
+ ) : ( +
+ · + + {`malegislature.gov/Legislators/Profile/${member.MemberCode}`} + +
+ )} + + {member.PhoneNumber ? ( +
+ · + {formatPhoneNumber(member.PhoneNumber)} +
+ ) : ( + <> + )} + +
+ {profile?.social?.twitter || + profile?.social?.linkedIn || + profile?.social?.blueSky ? ( + · + ) : ( + <> + )} + + {profile?.social?.twitter ? ( + + + + ) : ( + <> + )} + {profile?.social?.linkedIn ? ( + + + + ) : ( + <> + )} + {profile?.social?.blueSky ? ( + + + + ) : ( + <> + )} +
+
-
+ + + {/* uncomment when legislator Maple accounts are linked to this page + + {user && legislatorAccountId ? ( +
+ +
+ ) : ( + <> + )} */} + + {t("contact")} + +
+ + +
+ + + ? + {t("termsServed")} + + + + + + {member.SponsoredBills.length ? ( + <>{member.SponsoredBills.length} + ) : ( + <>? + )} + + {t("billsSponsored")} + + + + + + {member.CoSponsoredBills.length ? ( + <>{member.CoSponsoredBills.length} + ) : ( + <>? + )} + + {t("cosponsored")} + + + + + ? + {t("fundsRaised")} + + +
+
+ CoSponsoredBills: Array } export type Member = { From 9718b06ceea52ed97a02f453adfebd3e3d9bf0c6 Mon Sep 17 00:00:00 2001 From: mertbagt Date: Sat, 4 Jul 2026 15:16:33 -0400 Subject: [PATCH 4/7] legislator tabs --- .../LegislatorProfilePage.tsx | 85 +++++------ .../LegislatorProfile/LegislatorTabs.tsx | 133 ++++++++++++++++++ .../TabComponents/BillsTab.tsx | 3 + .../{ => TabComponents}/DistrictTab.test.tsx | 0 .../{ => TabComponents}/DistrictTab.tsx | 0 .../TabComponents/DistrictTabOld.tsx | 3 + .../TabComponents/ElectionsTab.tsx | 3 + .../TabComponents/FinanceTab.tsx | 3 + .../TabComponents/PrioritiesTab.tsx | 3 + .../TabComponents/TestimonyTab.tsx | 3 + .../TestimonyTab_PendingProfileLink.tsx | 102 ++++++++++++++ .../TabComponents/VotesTab.tsx | 3 + components/LegislatorProfile/index.ts | 1 - 13 files changed, 294 insertions(+), 48 deletions(-) create mode 100644 components/LegislatorProfile/LegislatorTabs.tsx create mode 100644 components/LegislatorProfile/TabComponents/BillsTab.tsx rename components/LegislatorProfile/{ => TabComponents}/DistrictTab.test.tsx (100%) rename components/LegislatorProfile/{ => TabComponents}/DistrictTab.tsx (100%) create mode 100644 components/LegislatorProfile/TabComponents/DistrictTabOld.tsx create mode 100644 components/LegislatorProfile/TabComponents/ElectionsTab.tsx create mode 100644 components/LegislatorProfile/TabComponents/FinanceTab.tsx create mode 100644 components/LegislatorProfile/TabComponents/PrioritiesTab.tsx create mode 100644 components/LegislatorProfile/TabComponents/TestimonyTab.tsx create mode 100644 components/LegislatorProfile/TabComponents/TestimonyTab_PendingProfileLink.tsx create mode 100644 components/LegislatorProfile/TabComponents/VotesTab.tsx diff --git a/components/LegislatorProfile/LegislatorProfilePage.tsx b/components/LegislatorProfile/LegislatorProfilePage.tsx index 9be5b4cf8..4a0e22df5 100644 --- a/components/LegislatorProfile/LegislatorProfilePage.tsx +++ b/components/LegislatorProfile/LegislatorProfilePage.tsx @@ -6,7 +6,6 @@ import styled from "styled-components" import * as links from "../links" -import { DistrictTab } from "./DistrictTab" import { Bluesky, DistrictLabel, @@ -15,24 +14,15 @@ import { PartyLabel, Twitter } from "./LegislatorComponents" +// import { LegislatorSidebar } from "./SidebarComponents/LegislatorSidebar" +import { LegislatorTabs } from "./LegislatorTabs" +import { useAuth } from "components/auth" import { Col, Container, Row, Spinner } from "components/bootstrap" import { useDistrict, useMember } from "components/db" import { Internal } from "components/links" -import { CircleImage } from "components/shared/LabeledIcon" - -import { doc, getDoc } from "firebase/firestore" -import { useCallback, useEffect, useState } from "react" - -import { usePublicProfile } from "../db" -import { firestore } from "../firebase" - -// import { LegislatorSidebar } from "./SidebarComponents/LegislatorSidebar" -// import { LegislatorTabs } from "./TabComponents/LegislatorTabs" - -import { useAuth } from "components/auth" -import { useFlags } from "components/featureFlags" import { FollowUserButton } from "components/shared/FollowButton" +import { CircleImage } from "components/shared/LabeledIcon" type ProfilePlaceholder = { social?: { @@ -127,20 +117,20 @@ const StatNum = styled.div.attrs(props => ({ width: max-content; ` -const TabButton = styled.button` - background: transparent; - border: 0; - border-bottom: 5px solid transparent; - color: #68707a; - font-size: 1.35rem; - font-weight: 700; - padding: 1.35rem 1.9rem 1.15rem; - - &.active { - border-bottom-color: #18358f; - color: #18358f; - } -` +// const TabButton = styled.button` +// background: transparent; +// border: 0; +// border-bottom: 5px solid transparent; +// color: #68707a; +// font-size: 1.35rem; +// font-weight: 700; +// padding: 1.35rem 1.9rem 1.15rem; + +// &.active { +// border-bottom-color: #18358f; +// color: #18358f; +// } +// ` export function LegislatorProfilePage({ court, @@ -156,7 +146,7 @@ export function LegislatorProfilePage({ member?.District ) const { t } = useTranslation("legislators") - const { user } = useAuth() + // const { user } = useAuth() **uncomment when Following Button in enabled** /* replace with profile info for legislators with Maple accounts */ let profile: ProfilePlaceholder = { @@ -186,7 +176,7 @@ export function LegislatorProfilePage({ return } - console.log("member: ", member) + console.log("district: ", district) return ( @@ -196,7 +186,7 @@ export function LegislatorProfilePage({ - {/* update with link to legistators search page when online */} + {/* update with link to legistators search page when that is created */}
{t("legislators")}
{/* */} @@ -358,25 +348,13 @@ export function LegislatorProfilePage({ - - {member.SponsoredBills.length ? ( - <>{member.SponsoredBills.length} - ) : ( - <>? - )} - + {member.SponsoredBills.length} {t("billsSponsored")} - - {member.CoSponsoredBills.length ? ( - <>{member.CoSponsoredBills.length} - ) : ( - <>? - )} - + {member.CoSponsoredBills.length} {t("cosponsored")} @@ -388,7 +366,20 @@ export function LegislatorProfilePage({
-
+ + + + + {/* */} +
Sidebar
+ + + + {/*
-
+
*/} ) } diff --git a/components/LegislatorProfile/LegislatorTabs.tsx b/components/LegislatorProfile/LegislatorTabs.tsx new file mode 100644 index 000000000..b969ad04c --- /dev/null +++ b/components/LegislatorProfile/LegislatorTabs.tsx @@ -0,0 +1,133 @@ +import { useTranslation } from "next-i18next" +import { TabPane } from "react-bootstrap" +import TabContainer from "react-bootstrap/TabContainer" +import styled from "styled-components" + +import { Container, Nav } from "../bootstrap" + +import { BillsTab } from "./TabComponents/BillsTab" +import { DistrictTab } from "./TabComponents/DistrictTab" +import { ElectionsTab } from "./TabComponents/ElectionsTab" +import { FinanceTab } from "./TabComponents/FinanceTab" +import { PrioritiesTab } from "./TabComponents/PrioritiesTab" +import { TestimonyTab } from "./TabComponents/TestimonyTab" +import { VotesTab } from "./TabComponents/VotesTab" + +import { District } from "components/db" +import { + StyledTabContent, + TabNavWrapper, + TabType +} from "components/EditProfilePage/StyledEditProfileComponents" + +const tabCategory = [ + "priorities", + "bills", + "elections", + "finance", + "district", + "testimony", + "votes" +] +type TabCategories = (typeof tabCategory)[number] + +const TabNavLink = styled(Nav.Link).attrs(props => ({ + className: `rounded-top m-0 p-0 ${props.className}` +}))` + color: #6c757d; + + &.active { + color: #1a3185; + font-weight: bold; + } +` + +const TabNavItem = ({ + tab, + i: i, + className +}: { + tab: TabType + i: number + className?: string +}) => { + return ( + + +

+ {tab.title} +

+
+
+
+ ) +} + +export function LegislatorTabs({ + district, + districtLoading, + tabCategory +}: { + district?: District | undefined + districtLoading?: boolean + tabCategory?: TabCategories +}) { + const { t } = useTranslation("legislators") + + const tabs = [ + { + title: t("tabs.priorities"), + eventKey: "priorities", + content: + }, + { + title: t("tabs.bills"), + eventKey: "bills", + content: + }, + { + title: t("tabs.elections"), + eventKey: "elections", + content: + }, + { + title: t("tabs.finance"), + eventKey: "finance", + content: + }, + { + title: t("tabs.district"), + eventKey: "district", + content: + }, + { + title: t("tabs.testimony"), + eventKey: "testimony", + content: + }, + { + title: t("tabs.votes"), + eventKey: "votes", + content: + } + ] + + return ( + + + + {tabs.map((t, i) => ( + + ))} + + + {tabs.map(t => ( + + {t.content} + + ))} + + + + ) +} diff --git a/components/LegislatorProfile/TabComponents/BillsTab.tsx b/components/LegislatorProfile/TabComponents/BillsTab.tsx new file mode 100644 index 000000000..7ccfc2ebd --- /dev/null +++ b/components/LegislatorProfile/TabComponents/BillsTab.tsx @@ -0,0 +1,3 @@ +export function BillsTab() { + return
- Bills
+} diff --git a/components/LegislatorProfile/DistrictTab.test.tsx b/components/LegislatorProfile/TabComponents/DistrictTab.test.tsx similarity index 100% rename from components/LegislatorProfile/DistrictTab.test.tsx rename to components/LegislatorProfile/TabComponents/DistrictTab.test.tsx diff --git a/components/LegislatorProfile/DistrictTab.tsx b/components/LegislatorProfile/TabComponents/DistrictTab.tsx similarity index 100% rename from components/LegislatorProfile/DistrictTab.tsx rename to components/LegislatorProfile/TabComponents/DistrictTab.tsx diff --git a/components/LegislatorProfile/TabComponents/DistrictTabOld.tsx b/components/LegislatorProfile/TabComponents/DistrictTabOld.tsx new file mode 100644 index 000000000..b2a70fa19 --- /dev/null +++ b/components/LegislatorProfile/TabComponents/DistrictTabOld.tsx @@ -0,0 +1,3 @@ +export function DistrictTab() { + return
- District
+} diff --git a/components/LegislatorProfile/TabComponents/ElectionsTab.tsx b/components/LegislatorProfile/TabComponents/ElectionsTab.tsx new file mode 100644 index 000000000..6fea4cfbf --- /dev/null +++ b/components/LegislatorProfile/TabComponents/ElectionsTab.tsx @@ -0,0 +1,3 @@ +export function ElectionsTab() { + return
- Elections
+} diff --git a/components/LegislatorProfile/TabComponents/FinanceTab.tsx b/components/LegislatorProfile/TabComponents/FinanceTab.tsx new file mode 100644 index 000000000..95f840dbb --- /dev/null +++ b/components/LegislatorProfile/TabComponents/FinanceTab.tsx @@ -0,0 +1,3 @@ +export function FinanceTab() { + return
- Finance
+} diff --git a/components/LegislatorProfile/TabComponents/PrioritiesTab.tsx b/components/LegislatorProfile/TabComponents/PrioritiesTab.tsx new file mode 100644 index 000000000..33c98c008 --- /dev/null +++ b/components/LegislatorProfile/TabComponents/PrioritiesTab.tsx @@ -0,0 +1,3 @@ +export function PrioritiesTab() { + return
- Priorities
+} diff --git a/components/LegislatorProfile/TabComponents/TestimonyTab.tsx b/components/LegislatorProfile/TabComponents/TestimonyTab.tsx new file mode 100644 index 000000000..e00fd7e0d --- /dev/null +++ b/components/LegislatorProfile/TabComponents/TestimonyTab.tsx @@ -0,0 +1,3 @@ +export function TestimonyTab() { + return
- Testimony
+} diff --git a/components/LegislatorProfile/TabComponents/TestimonyTab_PendingProfileLink.tsx b/components/LegislatorProfile/TabComponents/TestimonyTab_PendingProfileLink.tsx new file mode 100644 index 000000000..da1e672a3 --- /dev/null +++ b/components/LegislatorProfile/TabComponents/TestimonyTab_PendingProfileLink.tsx @@ -0,0 +1,102 @@ +import { useMemo } from "react" +import { useTranslation } from "next-i18next" +import styled from "styled-components" + +import { useAuth } from "components/auth" +import { usePublishedTestimonyListing } from "components/db/testimony/usePublishedTestimonyListing" +import { NoResults } from "components/search/NoResults" +import { TestimonyItem } from "components/TestimonyCard/TestimonyItem" + +const DisclaimerBlock = styled.div` + align-items: flex-start; + background-color: #f0f4ff; + border: "1px #d1d6e7 solid"; + border-radius: 5px; + color: #1a3185; + display: flex; + font-size: 13px; + gap: 10px; + line-height: 1.6; + margin-top: 14px; + margin-bottom: 14px; + padding: 12px 16px; +` + +const TestimonyBlock = styled.div` + background-color: white; + border: "1px #ced4da solid"; + border-radius: 5px; + font-size: 11px; + margin-bottom: 14px; + padding: 0px 16px; +` + +function Disclaimer({ fullname }: { fullname?: string }) { + const { t } = useTranslation("legislators") + + return ( + + + + + + +
+ {fullname} {t("canSubmit")} +
+
+ ) +} + +export function Testimony({ + fullname, + pageId +}: { + fullname?: string + pageId?: string +}) { + const { t } = useTranslation("testimony") + const { user } = useAuth() + + const testimony = usePublishedTestimonyListing({ + uid: pageId + }) + + const allTestimonies = useMemo(() => { + const legislatorTestimonies = testimony.items.result ?? [] + + // Combine and sort by publishedAt (newest first), then take 4 most recent + return [...legislatorTestimonies] + .sort((a, b) => b.publishedAt.toMillis() - a.publishedAt.toMillis()) + .slice(0, 4) + }, [testimony.items.result]) + + return ( + <> + + {allTestimonies.length > 0 ? ( +
+ {allTestimonies.map(testimony => ( + + + + ))} +
+ ) : ( + {t("viewTestimony.noTestimonies")} + )} + + ) +} diff --git a/components/LegislatorProfile/TabComponents/VotesTab.tsx b/components/LegislatorProfile/TabComponents/VotesTab.tsx new file mode 100644 index 000000000..3c6625cd2 --- /dev/null +++ b/components/LegislatorProfile/TabComponents/VotesTab.tsx @@ -0,0 +1,3 @@ +export function VotesTab() { + return
- Votes
+} diff --git a/components/LegislatorProfile/index.ts b/components/LegislatorProfile/index.ts index 056729577..01fb5e8c3 100644 --- a/components/LegislatorProfile/index.ts +++ b/components/LegislatorProfile/index.ts @@ -1,2 +1 @@ -export * from "./DistrictTab" export * from "./LegislatorProfilePage" From 81ecbf92d46a785ac560de2123cba14128f76c88 Mon Sep 17 00:00:00 2001 From: mertbagt Date: Sat, 4 Jul 2026 15:26:22 -0400 Subject: [PATCH 5/7] refactor sidebar --- .../LegislatorProfilePage.tsx | 27 +- .../LegislatorProfile/LegislatorSidebar.tsx | 14 + .../SidebarComponents/Biography.tsx | 0 .../SidebarComponents/OtherTestimony.tsx | 0 .../SidebarComponents/UpcomingHearings.tsx | 0 .../legislator/LegislatorComponents.tsx | 131 ------- components/legislator/LegislatorPage.tsx | 356 ------------------ .../SidebarComponents/LegislatorSidebar.tsx | 14 - components/legislator/TabComponents/Bills.tsx | 3 - .../legislator/TabComponents/District.tsx | 3 - .../legislator/TabComponents/Elections.tsx | 3 - .../legislator/TabComponents/Finance.tsx | 3 - .../TabComponents/LegislatorTabs.tsx | 132 ------- .../legislator/TabComponents/Priorities.tsx | 3 - .../legislator/TabComponents/Testimony.tsx | 103 ----- components/legislator/TabComponents/Votes.tsx | 3 - components/legislator/index.ts | 1 - pages/legislators/profile.tsx | 59 --- 18 files changed, 16 insertions(+), 839 deletions(-) create mode 100644 components/LegislatorProfile/LegislatorSidebar.tsx rename components/{legislator => LegislatorProfile}/SidebarComponents/Biography.tsx (100%) rename components/{legislator => LegislatorProfile}/SidebarComponents/OtherTestimony.tsx (100%) rename components/{legislator => LegislatorProfile}/SidebarComponents/UpcomingHearings.tsx (100%) delete mode 100644 components/legislator/LegislatorComponents.tsx delete mode 100644 components/legislator/LegislatorPage.tsx delete mode 100644 components/legislator/SidebarComponents/LegislatorSidebar.tsx delete mode 100644 components/legislator/TabComponents/Bills.tsx delete mode 100644 components/legislator/TabComponents/District.tsx delete mode 100644 components/legislator/TabComponents/Elections.tsx delete mode 100644 components/legislator/TabComponents/Finance.tsx delete mode 100644 components/legislator/TabComponents/LegislatorTabs.tsx delete mode 100644 components/legislator/TabComponents/Priorities.tsx delete mode 100644 components/legislator/TabComponents/Testimony.tsx delete mode 100644 components/legislator/TabComponents/Votes.tsx delete mode 100644 components/legislator/index.ts delete mode 100644 pages/legislators/profile.tsx diff --git a/components/LegislatorProfile/LegislatorProfilePage.tsx b/components/LegislatorProfile/LegislatorProfilePage.tsx index 4a0e22df5..27bbc9434 100644 --- a/components/LegislatorProfile/LegislatorProfilePage.tsx +++ b/components/LegislatorProfile/LegislatorProfilePage.tsx @@ -14,7 +14,7 @@ import { PartyLabel, Twitter } from "./LegislatorComponents" -// import { LegislatorSidebar } from "./SidebarComponents/LegislatorSidebar" +import { LegislatorSidebar } from "./LegislatorSidebar" import { LegislatorTabs } from "./LegislatorTabs" import { useAuth } from "components/auth" @@ -374,32 +374,9 @@ export function LegislatorProfilePage({ /> - {/* */} -
Sidebar
+ - - {/*
- {tabs.map(label => ( - - {label} - - ))} -
-
- -
*/} ) } diff --git a/components/LegislatorProfile/LegislatorSidebar.tsx b/components/LegislatorProfile/LegislatorSidebar.tsx new file mode 100644 index 000000000..db445f89b --- /dev/null +++ b/components/LegislatorProfile/LegislatorSidebar.tsx @@ -0,0 +1,14 @@ +import { Biography } from "./SidebarComponents/Biography" +import { OtherTestimony } from "./SidebarComponents/OtherTestimony" +import { UpcomingHearings } from "./SidebarComponents/UpcomingHearings" + +export function LegislatorSidebar() { + return ( + <> + Sidebar Components + + + + + ) +} diff --git a/components/legislator/SidebarComponents/Biography.tsx b/components/LegislatorProfile/SidebarComponents/Biography.tsx similarity index 100% rename from components/legislator/SidebarComponents/Biography.tsx rename to components/LegislatorProfile/SidebarComponents/Biography.tsx diff --git a/components/legislator/SidebarComponents/OtherTestimony.tsx b/components/LegislatorProfile/SidebarComponents/OtherTestimony.tsx similarity index 100% rename from components/legislator/SidebarComponents/OtherTestimony.tsx rename to components/LegislatorProfile/SidebarComponents/OtherTestimony.tsx diff --git a/components/legislator/SidebarComponents/UpcomingHearings.tsx b/components/LegislatorProfile/SidebarComponents/UpcomingHearings.tsx similarity index 100% rename from components/legislator/SidebarComponents/UpcomingHearings.tsx rename to components/LegislatorProfile/SidebarComponents/UpcomingHearings.tsx diff --git a/components/legislator/LegislatorComponents.tsx b/components/legislator/LegislatorComponents.tsx deleted file mode 100644 index e420630f4..000000000 --- a/components/legislator/LegislatorComponents.tsx +++ /dev/null @@ -1,131 +0,0 @@ -import { useTranslation } from "next-i18next" -import styled from "styled-components" - -export const formatPhoneNumber = (value: string) => { - if (!value) return value - - const phoneNumber = value.replace(/[^\d]/g, "") - const phoneNumberLength = phoneNumber.length - - // Format as (XXX) XXX-XXXX - if (phoneNumberLength < 4) return phoneNumber - if (phoneNumberLength < 7) { - return `(${phoneNumber.slice(0, 3)}) ${phoneNumber.slice(3)}` - } - return ` - (${phoneNumber.slice(0, 3)}) - ${phoneNumber.slice(3, 6)}- - ${phoneNumber.slice(6, 10)} - ` -} - -/** Party Labels **/ - -const DemocraticBubble = styled.div.attrs(props => ({ - className: `${props.className}` -}))` - background: #d1d6e7; - color: #1a3185; - font-size: 11px; - font-weight: 700; - padding: 1px 10px; - border-radius: 999px; - width: max-content; -` - -const DistrictBubble = styled.div.attrs(props => ({ - className: `ms-1 ${props.className}` -}))` - background: #fff3cd; - color: #856404; - font-size: 11px; - font-weight: 700; - padding: 1px 10px; - border-radius: 999px; - width: max-content; -` - -const IndependantBubble = styled.div.attrs(props => ({ - className: `${props.className}` -}))` - background: #bca0dc; - color: #3c1361; - font-size: 11px; - font-weight: 700; - padding: 1px 10px; - border-radius: 999px; - width: max-content; -` - -const RepublicanBubble = styled.div.attrs(props => ({ - className: `${props.className}` -}))` - background: #f29999; - color: #de0100; - font-size: 11px; - font-weight: 700; - padding: 1px 10px; - border-radius: 999px; - width: max-content; -` - -export function DistrictLabel(props: { district: string }) { - return {props.district} -} - -export function PartyLabel(props: { party: string }) { - const { t } = useTranslation("legislators") - - switch (props.party) { - case "Democrat": - return {t("party.democratic")} - case "Republican": - return {t("party.republican")} - default: - return ( - - {props.party} {t("party.party")} - - ) - } -} - -/** Social Media components **/ - -export function Bluesky() { - return ( - - - - ) -} - -export function LinkedIn() { - return ( - - - - ) -} - -export function Twitter() { - return ( - - - - ) -} diff --git a/components/legislator/LegislatorPage.tsx b/components/legislator/LegislatorPage.tsx deleted file mode 100644 index fbf6b9113..000000000 --- a/components/legislator/LegislatorPage.tsx +++ /dev/null @@ -1,356 +0,0 @@ -import { doc, getDoc } from "firebase/firestore" -import { faChevronRight } from "@fortawesome/free-solid-svg-icons" -import { FontAwesomeIcon } from "@fortawesome/react-fontawesome" -import { useTranslation } from "next-i18next" -import ErrorPage from "next/error" -import { useCallback, useEffect, useState } from "react" -import styled from "styled-components" - -import { Col, Container, Row, Spinner } from "../bootstrap" -import { usePublicProfile } from "../db" -import { firestore } from "../firebase" -import * as links from "../links" - -import { - Bluesky, - DistrictLabel, - formatPhoneNumber, - LinkedIn, - PartyLabel, - Twitter -} from "./LegislatorComponents" -import { LegislatorSidebar } from "./SidebarComponents/LegislatorSidebar" -import { LegislatorTabs } from "./TabComponents/LegislatorTabs" - -import { useAuth } from "components/auth" -import { useFlags } from "components/featureFlags" -import { Internal } from "components/links" -import { FollowUserButton } from "components/shared/FollowButton" -import { CircleImage } from "components/shared/LabeledIcon" - -const DirectoryPath = styled.div.attrs(props => ({ - className: `align-items-center d-flex flex-nowrap ${props.className}` -}))` - font-size: 12px; -` - -const ButtonContainer = styled(Col).attrs(props => ({ - className: `col-12 justify-content-md-end ${props.className}`, - md: `3`, - sm: `4` -}))` - width: max-content; -` - -const HeaderBlock = styled.div` - background-color: white; - border: "1px #ced4da solid"; - border-radius: 5px; - margin-top: 8px; - padding: 16px; -` - -const HeaderName = styled.div` - font-size: 26px; - font-weight: 700; - color: #0b0a3e; -` - -const RoleLine = styled.div.attrs(props => ({ - className: `mb-2 ${props.className}` -}))` - color: #6c757d; - font-size: 14px; -` - -const PhoneNum = styled.span` - color: #6c757d; -` - -const SocialLine = styled.div.attrs(props => ({ - className: `d-flex flex-wrap mb-2 ${props.className}` -}))` - font-size: 12px; - text-decoration: none; -` - -const StatBlock = styled(Col).attrs(props => ({ - className: `d-flex col-4 flex-grow-1 ${props.className}`, - md: `2` -}))` - background-color: white; - border: 1px #ced4da solid; - border-radius: 5px; - margin-top: 4px; - padding: 16px; -` - -const StatLine = styled(Row).attrs(props => ({ - className: `text-nowrap ${props.className}` -}))` - font-size: 12px; -` - -const StatNum = styled.div.attrs(props => ({ - className: `mx-auto ${props.className}` -}))` - color: #1a3185; - font-size: 22px; - font-weight: 700; - width: max-content; -` - -export function LegislatorPage(props: { id: string }) { - const { t } = useTranslation("legislators") - const { result: profile, loading } = usePublicProfile(props.id) - const { legislators } = useFlags() - const { user } = useAuth() - - // eventually this should be replaced with a profile prop array that - // contains a list of courts the legislator served on - const viableCourts = "194" - - const [branch, setBranch] = useState("") - const [cosponsoredBills, setCosponsoredBills] = useState>([""]) - const [district, setDistrict] = useState("") - const [email, setEmail] = useState("") - const [party, setParty] = useState("") - const [phoneNumber, setPhoneNumber] = useState("") - const [sponsoredBills, setSponsoredBills] = useState>([""]) - - const memberData = useCallback(async () => { - const member = await getDoc( - doc( - firestore, - `generalCourts/${viableCourts}/members/${profile?.memberId}` - ) - ) - const docData = member.data() - - setBranch(docData?.content.Branch) - setCosponsoredBills(docData?.content.CoSponsoredBills) - setDistrict(docData?.content.District) - setEmail(docData?.content.EmailAddress) - setParty(docData?.content.Party) - setPhoneNumber(docData?.content.PhoneNumber) - setSponsoredBills(docData?.content.SponsoredBills) - }, [district, party, phoneNumber]) - - useEffect(() => { - profile ? memberData() : null - }, [memberData, profile]) - - if (loading) { - return ( - - - - ) - } - if (!legislators) { - return - } - if (!profile) { - return - } - - return ( - - - - {t("home")} - - -
{t("legislators")}
- -
{profile.fullName}
-
- - - - {""} - - - - - {profile.fullName} - - - - - {branch == "Senate" ? ( - {t("stateSenator")} - ) : ( - {t("stateRepresentative")} - )} - {/* · Town */} - - -
- - {/* Incumbent Label */} - -
- - -
- - {email} - -
- - {profile.website ? ( -
- · - - {profile.website} - -
- ) : ( -
- · - - {`malegislature.gov/Legislators/Profile/${profile.memberId}`} - -
- )} - - {phoneNumber ? ( -
- · - {formatPhoneNumber(phoneNumber)} -
- ) : ( - <> - )} - -
- {profile?.social?.twitter || - profile?.social?.linkedIn || - profile?.social?.blueSky ? ( - · - ) : ( - <> - )} - - {profile?.social?.twitter ? ( - - - - ) : ( - <> - )} - {profile?.social?.linkedIn ? ( - - - - ) : ( - <> - )} - {profile?.social?.blueSky ? ( - - - - ) : ( - <> - )} -
-
- - - - {user ? ( -
- -
- ) : ( - <> - )} - - {t("contact")} - -
-
- -
- - - ? - {t("termsServed")} - - - - - - {sponsoredBills?.length ? <>{sponsoredBills.length} : <>?} - - {t("billsSponsored")} - - - - - - {cosponsoredBills?.length ? ( - <>{cosponsoredBills.length} - ) : ( - <>? - )} - - {t("cosponsored")} - - - - - ? - {t("fundsRaised")} - - -
- - - - - - - - - -
- ) -} diff --git a/components/legislator/SidebarComponents/LegislatorSidebar.tsx b/components/legislator/SidebarComponents/LegislatorSidebar.tsx deleted file mode 100644 index 39f77168e..000000000 --- a/components/legislator/SidebarComponents/LegislatorSidebar.tsx +++ /dev/null @@ -1,14 +0,0 @@ -import { Biography } from "./Biography" -import { OtherTestimony } from "./OtherTestimony" -import { UpcomingHearings } from "./UpcomingHearings" - -export function LegislatorSidebar() { - return ( - <> - Sidebar Components - - - - - ) -} diff --git a/components/legislator/TabComponents/Bills.tsx b/components/legislator/TabComponents/Bills.tsx deleted file mode 100644 index 61d6b5918..000000000 --- a/components/legislator/TabComponents/Bills.tsx +++ /dev/null @@ -1,3 +0,0 @@ -export function Bills() { - return
- Bills
-} diff --git a/components/legislator/TabComponents/District.tsx b/components/legislator/TabComponents/District.tsx deleted file mode 100644 index 06025fbff..000000000 --- a/components/legislator/TabComponents/District.tsx +++ /dev/null @@ -1,3 +0,0 @@ -export function District() { - return
- District
-} diff --git a/components/legislator/TabComponents/Elections.tsx b/components/legislator/TabComponents/Elections.tsx deleted file mode 100644 index c20356658..000000000 --- a/components/legislator/TabComponents/Elections.tsx +++ /dev/null @@ -1,3 +0,0 @@ -export function Elections() { - return
- Elections
-} diff --git a/components/legislator/TabComponents/Finance.tsx b/components/legislator/TabComponents/Finance.tsx deleted file mode 100644 index f1431f05f..000000000 --- a/components/legislator/TabComponents/Finance.tsx +++ /dev/null @@ -1,3 +0,0 @@ -export function Finance() { - return
- Finance
-} diff --git a/components/legislator/TabComponents/LegislatorTabs.tsx b/components/legislator/TabComponents/LegislatorTabs.tsx deleted file mode 100644 index 332f41747..000000000 --- a/components/legislator/TabComponents/LegislatorTabs.tsx +++ /dev/null @@ -1,132 +0,0 @@ -import { useTranslation } from "next-i18next" -import { TabPane } from "react-bootstrap" -import TabContainer from "react-bootstrap/TabContainer" -import styled from "styled-components" - -import { Container, Nav } from "../../bootstrap" - -import { Bills } from "./Bills" -import { District } from "./District" -import { Elections } from "./Elections" -import { Finance } from "./Finance" -import { Priorities } from "./Priorities" -import { Testimony } from "./Testimony" -import { Votes } from "./Votes" - -import { - StyledTabContent, - TabNavWrapper, - TabType -} from "components/EditProfilePage/StyledEditProfileComponents" - -const tabCategory = [ - "priorities", - "bills", - "elections", - "finance", - "district", - "testimony", - "votes" -] -type TabCategories = (typeof tabCategory)[number] - -const TabNavLink = styled(Nav.Link).attrs(props => ({ - className: `rounded-top m-0 p-0 ${props.className}` -}))` - color: #6c757d; - - &.active { - color: #1a3185; - font-weight: bold; - } -` - -const TabNavItem = ({ - tab, - i: i, - className -}: { - tab: TabType - i: number - className?: string -}) => { - return ( - - -

- {tab.title} -

-
-
-
- ) -} - -export function LegislatorTabs({ - fullname, - pageId, - tabCategory -}: { - fullname?: string - pageId?: string - tabCategory?: TabCategories -}) { - const { t } = useTranslation("legislators") - - const tabs = [ - { - title: t("tabs.priorities"), - eventKey: "priorities", - content: - }, - { - title: t("tabs.bills"), - eventKey: "bills", - content: - }, - { - title: t("tabs.elections"), - eventKey: "elections", - content: - }, - { - title: t("tabs.finance"), - eventKey: "finance", - content: - }, - { - title: t("tabs.district"), - eventKey: "district", - content: - }, - { - title: t("tabs.testimony"), - eventKey: "testimony", - content: - }, - { - title: t("tabs.votes"), - eventKey: "votes", - content: - } - ] - - return ( - - - - {tabs.map((t, i) => ( - - ))} - - - {tabs.map(t => ( - - {t.content} - - ))} - - - - ) -} diff --git a/components/legislator/TabComponents/Priorities.tsx b/components/legislator/TabComponents/Priorities.tsx deleted file mode 100644 index 534f54540..000000000 --- a/components/legislator/TabComponents/Priorities.tsx +++ /dev/null @@ -1,3 +0,0 @@ -export function Priorities() { - return
- Priorities
-} diff --git a/components/legislator/TabComponents/Testimony.tsx b/components/legislator/TabComponents/Testimony.tsx deleted file mode 100644 index 6f5c0e40b..000000000 --- a/components/legislator/TabComponents/Testimony.tsx +++ /dev/null @@ -1,103 +0,0 @@ -import { useMemo } from "react" -import { useTranslation } from "next-i18next" -import styled from "styled-components" - -import { useAuth } from "components/auth" -import { SmartDisclaimer } from "components/bill/SmartDisclaimer" -import { usePublishedTestimonyListing } from "components/db/testimony/usePublishedTestimonyListing" -import { NoResults } from "components/search/NoResults" -import { TestimonyItem } from "components/TestimonyCard/TestimonyItem" - -const DisclaimerBlock = styled.div` - align-items: flex-start; - background-color: #f0f4ff; - border: "1px #d1d6e7 solid"; - border-radius: 5px; - color: #1a3185; - display: flex; - font-size: 13px; - gap: 10px; - line-height: 1.6; - margin-top: 14px; - margin-bottom: 14px; - padding: 12px 16px; -` - -const TestimonyBlock = styled.div` - background-color: white; - border: "1px #ced4da solid"; - border-radius: 5px; - font-size: 11px; - margin-bottom: 14px; - padding: 0px 16px; -` - -function Disclaimer({ fullname }: { fullname?: string }) { - const { t } = useTranslation("legislators") - - return ( - - - - - - -
- {fullname} {t("canSubmit")} -
-
- ) -} - -export function Testimony({ - fullname, - pageId -}: { - fullname?: string - pageId?: string -}) { - const { t } = useTranslation("testimony") - const { user } = useAuth() - - const testimony = usePublishedTestimonyListing({ - uid: pageId - }) - - const allTestimonies = useMemo(() => { - const legislatorTestimonies = testimony.items.result ?? [] - - // Combine and sort by publishedAt (newest first), then take 4 most recent - return [...legislatorTestimonies] - .sort((a, b) => b.publishedAt.toMillis() - a.publishedAt.toMillis()) - .slice(0, 4) - }, [testimony.items.result]) - - return ( - <> - - {allTestimonies.length > 0 ? ( -
- {allTestimonies.map(testimony => ( - - - - ))} -
- ) : ( - {t("viewTestimony.noTestimonies")} - )} - - ) -} diff --git a/components/legislator/TabComponents/Votes.tsx b/components/legislator/TabComponents/Votes.tsx deleted file mode 100644 index ecdfb5f01..000000000 --- a/components/legislator/TabComponents/Votes.tsx +++ /dev/null @@ -1,3 +0,0 @@ -export function Votes() { - return
- Votes
-} diff --git a/components/legislator/index.ts b/components/legislator/index.ts deleted file mode 100644 index 13355a639..000000000 --- a/components/legislator/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from "./LegislatorPage" diff --git a/pages/legislators/profile.tsx b/pages/legislators/profile.tsx deleted file mode 100644 index 2e3b29d76..000000000 --- a/pages/legislators/profile.tsx +++ /dev/null @@ -1,59 +0,0 @@ -import { useTranslation } from "next-i18next" -import { useEffect, useState } from "react" -import { Spinner } from "react-bootstrap" - -import { LegislatorPage } from "components/legislator" -import { createPage } from "components/page" -import { createGetStaticTranslationProps } from "components/translations" - -export default createPage<{ court: string }>({ - titleI18nKey: "navigation.legislator", - Page: () => { - const { id, loading } = useProfileRouting() - const { t } = useTranslation("profile") - - return ( -
- {loading ? ( -
- -
- ) : id ? ( - - ) : ( -
{t("noLegislator")}
- )} -
- ) - } -}) - -const useProfileRouting = () => { - const [id, setId] = useState("od") - const [loading, setLoading] = useState(true) - - useEffect(() => { - if (window) { - const urlParams = new URLSearchParams(window.location?.search) - const urlid = urlParams.get("id") - - if (typeof urlid === "string") { - setId(urlid) - } - if (urlid !== undefined) { - setLoading(false) - } - } - }, [id]) - - return { id, loading } -} - -export const getStaticProps = createGetStaticTranslationProps([ - "auth", - "common", - "footer", - "legislators", - "profile", - "testimony" -]) From 2e18f8cd10456d25c269d36a8433a2b7611ebc00 Mon Sep 17 00:00:00 2001 From: mertbagt Date: Sat, 4 Jul 2026 16:04:27 -0400 Subject: [PATCH 6/7] tab containers --- .../LegislatorComponents.tsx | 8 +++++++ .../LegislatorProfilePage.tsx | 21 ++----------------- .../LegislatorProfile/LegislatorSidebar.tsx | 1 - .../SidebarComponents/Biography.tsx | 4 +++- .../SidebarComponents/OtherTestimony.tsx | 4 +++- .../SidebarComponents/UpcomingHearings.tsx | 4 +++- .../TabComponents/BillsTab.tsx | 4 +++- .../TabComponents/DistrictTab.tsx | 15 ++++++------- .../TabComponents/DistrictTabOld.tsx | 3 --- .../TabComponents/ElectionsTab.tsx | 4 +++- .../TabComponents/FinanceTab.tsx | 4 +++- .../TabComponents/PrioritiesTab.tsx | 4 +++- .../TabComponents/TestimonyTab.tsx | 4 +++- .../TestimonyTab_PendingProfileLink.tsx | 15 ++++--------- .../TabComponents/VotesTab.tsx | 4 +++- 15 files changed, 47 insertions(+), 52 deletions(-) delete mode 100644 components/LegislatorProfile/TabComponents/DistrictTabOld.tsx diff --git a/components/LegislatorProfile/LegislatorComponents.tsx b/components/LegislatorProfile/LegislatorComponents.tsx index e420630f4..1f25f37ab 100644 --- a/components/LegislatorProfile/LegislatorComponents.tsx +++ b/components/LegislatorProfile/LegislatorComponents.tsx @@ -19,6 +19,14 @@ export const formatPhoneNumber = (value: string) => { ` } +export const TabBlock = styled.div` + background-color: white; + border: 1px #b8c0c9 solid; + border-radius: 5px; + margin-bottom: 10px; + padding: 16px; +` + /** Party Labels **/ const DemocraticBubble = styled.div.attrs(props => ({ diff --git a/components/LegislatorProfile/LegislatorProfilePage.tsx b/components/LegislatorProfile/LegislatorProfilePage.tsx index 27bbc9434..9cf3805c1 100644 --- a/components/LegislatorProfile/LegislatorProfilePage.tsx +++ b/components/LegislatorProfile/LegislatorProfilePage.tsx @@ -61,7 +61,7 @@ const HeaderBlock = styled.div.attrs(props => ({ className: `d-flex flex-wrap justify-content-between ${props.className}` }))` background-color: white; - border: "1px #ced4da solid"; + border: 1px #b8c0c9 solid; border-radius: 5px; margin-top: 8px; padding: 16px; @@ -96,7 +96,7 @@ const StatBlock = styled(Col).attrs(props => ({ md: `2` }))` background-color: white; - border: 1px #ced4da solid; + border: 1px #b8c0c9 solid; border-radius: 5px; margin-top: 4px; padding: 16px; @@ -117,21 +117,6 @@ const StatNum = styled.div.attrs(props => ({ width: max-content; ` -// const TabButton = styled.button` -// background: transparent; -// border: 0; -// border-bottom: 5px solid transparent; -// color: #68707a; -// font-size: 1.35rem; -// font-weight: 700; -// padding: 1.35rem 1.9rem 1.15rem; - -// &.active { -// border-bottom-color: #18358f; -// color: #18358f; -// } -// ` - export function LegislatorProfilePage({ court, memberCode @@ -176,8 +161,6 @@ export function LegislatorProfilePage({ return } - console.log("district: ", district) - return ( diff --git a/components/LegislatorProfile/LegislatorSidebar.tsx b/components/LegislatorProfile/LegislatorSidebar.tsx index db445f89b..96cf42c9d 100644 --- a/components/LegislatorProfile/LegislatorSidebar.tsx +++ b/components/LegislatorProfile/LegislatorSidebar.tsx @@ -5,7 +5,6 @@ import { UpcomingHearings } from "./SidebarComponents/UpcomingHearings" export function LegislatorSidebar() { return ( <> - Sidebar Components diff --git a/components/LegislatorProfile/SidebarComponents/Biography.tsx b/components/LegislatorProfile/SidebarComponents/Biography.tsx index 90cf3f5e0..e190ac443 100644 --- a/components/LegislatorProfile/SidebarComponents/Biography.tsx +++ b/components/LegislatorProfile/SidebarComponents/Biography.tsx @@ -1,3 +1,5 @@ +import { TabBlock } from "../LegislatorComponents" + export function Biography() { - return
- Biography
+ return - Biography } diff --git a/components/LegislatorProfile/SidebarComponents/OtherTestimony.tsx b/components/LegislatorProfile/SidebarComponents/OtherTestimony.tsx index 8b3940014..4cf43f2b2 100644 --- a/components/LegislatorProfile/SidebarComponents/OtherTestimony.tsx +++ b/components/LegislatorProfile/SidebarComponents/OtherTestimony.tsx @@ -1,3 +1,5 @@ +import { TabBlock } from "../LegislatorComponents" + export function OtherTestimony() { - return
- Other Testimony
+ return - Other Testimony } diff --git a/components/LegislatorProfile/SidebarComponents/UpcomingHearings.tsx b/components/LegislatorProfile/SidebarComponents/UpcomingHearings.tsx index 69e68cb05..c3da92690 100644 --- a/components/LegislatorProfile/SidebarComponents/UpcomingHearings.tsx +++ b/components/LegislatorProfile/SidebarComponents/UpcomingHearings.tsx @@ -1,3 +1,5 @@ +import { TabBlock } from "../LegislatorComponents" + export function UpcomingHearings() { - return
- Upcoming Hearings
+ return - Upcoming Hearings } diff --git a/components/LegislatorProfile/TabComponents/BillsTab.tsx b/components/LegislatorProfile/TabComponents/BillsTab.tsx index 7ccfc2ebd..bde7d1cb7 100644 --- a/components/LegislatorProfile/TabComponents/BillsTab.tsx +++ b/components/LegislatorProfile/TabComponents/BillsTab.tsx @@ -1,3 +1,5 @@ +import { TabBlock } from "../LegislatorComponents" + export function BillsTab() { - return
- Bills
+ return - Bills } diff --git a/components/LegislatorProfile/TabComponents/DistrictTab.tsx b/components/LegislatorProfile/TabComponents/DistrictTab.tsx index a00f706b4..10365ca1c 100644 --- a/components/LegislatorProfile/TabComponents/DistrictTab.tsx +++ b/components/LegislatorProfile/TabComponents/DistrictTab.tsx @@ -1,6 +1,7 @@ import { FontAwesomeIcon } from "@fortawesome/react-fontawesome" import { faLocationDot } from "@fortawesome/free-solid-svg-icons" import styled from "styled-components" +import { TabBlock } from "../LegislatorComponents" import type { District } from "components/db" const MapPreview = styled.div` @@ -12,8 +13,8 @@ const MapPreview = styled.div` ` const DistrictCard = styled.section` - border: 1px solid #d9dee5; - border-radius: 8px; + border: 1px #b8c0c9 solid; + border-radius: 5px; overflow: hidden; ` @@ -55,15 +56,11 @@ export function DistrictTab({ loading?: boolean }) { if (loading) { - return
Loading district...
+ return Loading district... } if (!district) { - return ( -
- District details are not available yet. -
- ) + return District details are not available yet. } const chips = subdivisionChips(district) @@ -71,7 +68,7 @@ export function DistrictTab({ return ( <> - +

{district.district} District

diff --git a/components/LegislatorProfile/TabComponents/DistrictTabOld.tsx b/components/LegislatorProfile/TabComponents/DistrictTabOld.tsx deleted file mode 100644 index b2a70fa19..000000000 --- a/components/LegislatorProfile/TabComponents/DistrictTabOld.tsx +++ /dev/null @@ -1,3 +0,0 @@ -export function DistrictTab() { - return

- District
-} diff --git a/components/LegislatorProfile/TabComponents/ElectionsTab.tsx b/components/LegislatorProfile/TabComponents/ElectionsTab.tsx index 6fea4cfbf..1bb6bfccf 100644 --- a/components/LegislatorProfile/TabComponents/ElectionsTab.tsx +++ b/components/LegislatorProfile/TabComponents/ElectionsTab.tsx @@ -1,3 +1,5 @@ +import { TabBlock } from "../LegislatorComponents" + export function ElectionsTab() { - return
- Elections
+ return - Elections } diff --git a/components/LegislatorProfile/TabComponents/FinanceTab.tsx b/components/LegislatorProfile/TabComponents/FinanceTab.tsx index 95f840dbb..4c263d26a 100644 --- a/components/LegislatorProfile/TabComponents/FinanceTab.tsx +++ b/components/LegislatorProfile/TabComponents/FinanceTab.tsx @@ -1,3 +1,5 @@ +import { TabBlock } from "../LegislatorComponents" + export function FinanceTab() { - return
- Finance
+ return - Finance } diff --git a/components/LegislatorProfile/TabComponents/PrioritiesTab.tsx b/components/LegislatorProfile/TabComponents/PrioritiesTab.tsx index 33c98c008..000d6d564 100644 --- a/components/LegislatorProfile/TabComponents/PrioritiesTab.tsx +++ b/components/LegislatorProfile/TabComponents/PrioritiesTab.tsx @@ -1,3 +1,5 @@ +import { TabBlock } from "../LegislatorComponents" + export function PrioritiesTab() { - return
- Priorities
+ return - Priorities } diff --git a/components/LegislatorProfile/TabComponents/TestimonyTab.tsx b/components/LegislatorProfile/TabComponents/TestimonyTab.tsx index e00fd7e0d..eb3bc6e04 100644 --- a/components/LegislatorProfile/TabComponents/TestimonyTab.tsx +++ b/components/LegislatorProfile/TabComponents/TestimonyTab.tsx @@ -1,3 +1,5 @@ +import { TabBlock } from "../LegislatorComponents" + export function TestimonyTab() { - return
- Testimony
+ return - Testimony } diff --git a/components/LegislatorProfile/TabComponents/TestimonyTab_PendingProfileLink.tsx b/components/LegislatorProfile/TabComponents/TestimonyTab_PendingProfileLink.tsx index da1e672a3..12b8174fd 100644 --- a/components/LegislatorProfile/TabComponents/TestimonyTab_PendingProfileLink.tsx +++ b/components/LegislatorProfile/TabComponents/TestimonyTab_PendingProfileLink.tsx @@ -2,6 +2,8 @@ import { useMemo } from "react" import { useTranslation } from "next-i18next" import styled from "styled-components" +import { TabBlock } from "../LegislatorComponents" + import { useAuth } from "components/auth" import { usePublishedTestimonyListing } from "components/db/testimony/usePublishedTestimonyListing" import { NoResults } from "components/search/NoResults" @@ -22,15 +24,6 @@ const DisclaimerBlock = styled.div` padding: 12px 16px; ` -const TestimonyBlock = styled.div` - background-color: white; - border: "1px #ced4da solid"; - border-radius: 5px; - font-size: 11px; - margin-bottom: 14px; - padding: 0px 16px; -` - function Disclaimer({ fullname }: { fullname?: string }) { const { t } = useTranslation("legislators") @@ -85,13 +78,13 @@ export function Testimony({ {allTestimonies.length > 0 ? (
{allTestimonies.map(testimony => ( - + - + ))}
) : ( diff --git a/components/LegislatorProfile/TabComponents/VotesTab.tsx b/components/LegislatorProfile/TabComponents/VotesTab.tsx index 3c6625cd2..09e0558a4 100644 --- a/components/LegislatorProfile/TabComponents/VotesTab.tsx +++ b/components/LegislatorProfile/TabComponents/VotesTab.tsx @@ -1,3 +1,5 @@ +import { TabBlock } from "../LegislatorComponents" + export function VotesTab() { - return
- Votes
+ return - Votes } From f4780c115c684b2752295361b188b2556ca5e006 Mon Sep 17 00:00:00 2001 From: mertbagt Date: Sat, 4 Jul 2026 16:11:10 -0400 Subject: [PATCH 7/7] resposive margings --- components/LegislatorProfile/LegislatorProfilePage.tsx | 6 +++--- components/LegislatorProfile/LegislatorTabs.tsx | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/components/LegislatorProfile/LegislatorProfilePage.tsx b/components/LegislatorProfile/LegislatorProfilePage.tsx index 9cf3805c1..2f8d127e2 100644 --- a/components/LegislatorProfile/LegislatorProfilePage.tsx +++ b/components/LegislatorProfile/LegislatorProfilePage.tsx @@ -349,14 +349,14 @@ export function LegislatorProfilePage({
- - + + - + diff --git a/components/LegislatorProfile/LegislatorTabs.tsx b/components/LegislatorProfile/LegislatorTabs.tsx index b969ad04c..40c264453 100644 --- a/components/LegislatorProfile/LegislatorTabs.tsx +++ b/components/LegislatorProfile/LegislatorTabs.tsx @@ -113,7 +113,7 @@ export function LegislatorTabs({ ] return ( - + {tabs.map((t, i) => (