From b73c3669f78a532f133c3c1508e3f5f878ff33d1 Mon Sep 17 00:00:00 2001 From: Mahen Date: Mon, 13 Apr 2026 11:58:08 +0700 Subject: [PATCH] style: enhance final dark mode visibiliity for all pages --- src/app/globals.css | 6 + src/app/layout.tsx | 5 +- src/app/page.tsx | 8 +- src/app/profile/page.tsx | 18 +- src/components/auth/LoginForm.tsx | 142 +++++++--- src/components/dashboards/AnalysisClient.tsx | 8 +- src/components/dashboards/BrandFilter.tsx | 8 +- src/components/dashboards/DashboardClient.tsx | 24 +- src/components/dashboards/ExportExcel.tsx | 4 +- src/components/dashboards/Header.tsx | 26 +- src/components/dashboards/ModelInfo.tsx | 2 +- src/components/dashboards/ProfileCard.tsx | 187 ------------- src/components/dashboards/ProfileClient.tsx | 250 ++++++++++++++++-- src/components/dashboards/ProfileModal.tsx | 54 ++-- src/components/dashboards/ReviewTable.tsx | 39 +-- src/components/dashboards/SentimentBadge.tsx | 8 +- src/components/dashboards/WordCloud.tsx | 4 +- .../skeletons/ModelInfoSkeleton.tsx | 41 ++- src/components/ui/button.tsx | 4 +- src/components/ui/pagination.tsx | 2 +- src/components/ui/select.tsx | 2 +- src/context/ThemeContext.tsx | 41 +++ src/hooks/useDashboard.ts | 3 - src/types/index.ts | 1 + src/utils/datas.ts | 6 +- 25 files changed, 542 insertions(+), 351 deletions(-) delete mode 100644 src/components/dashboards/ProfileCard.tsx create mode 100644 src/context/ThemeContext.tsx diff --git a/src/app/globals.css b/src/app/globals.css index b5665e7..592a136 100644 --- a/src/app/globals.css +++ b/src/app/globals.css @@ -93,6 +93,12 @@ @apply bg-background text-foreground antialiased; font-feature-settings: "cv02", "cv03", "cv04", "cv11"; } + + body[data-scroll-locked] { + margin-right: 0 !important; + padding-right: 0 !important; + overflow: overlay !important; + } } @layer utilities { diff --git a/src/app/layout.tsx b/src/app/layout.tsx index b636f5d..bc623a1 100644 --- a/src/app/layout.tsx +++ b/src/app/layout.tsx @@ -2,6 +2,7 @@ import type { Metadata } from "next"; import { Inter } from "next/font/google"; import "./globals.css"; import Providers from "./providers"; +import { ThemeProvider } from "../context/ThemeContext"; export const metadata: Metadata = { title: "Create Next App", @@ -18,7 +19,9 @@ export default function RootLayout({ return ( - {children} + + {children} + ); diff --git a/src/app/page.tsx b/src/app/page.tsx index 53f6844..11f4605 100644 --- a/src/app/page.tsx +++ b/src/app/page.tsx @@ -9,11 +9,5 @@ export default async function Home() { if (session) { redirect("/dashboard"); } - return ( -
-
- -
-
- ); + return ; } diff --git a/src/app/profile/page.tsx b/src/app/profile/page.tsx index 2ad00d4..215a471 100644 --- a/src/app/profile/page.tsx +++ b/src/app/profile/page.tsx @@ -1,13 +1,17 @@ -import Footer from "@/src/components/dashboards/Footer"; -import { Header } from "@/src/components/dashboards/Header"; import ProfileClient from "@/src/components/dashboards/ProfileClient"; +import { getAnotherUserData } from "./lib/action"; export default async function ProfilePage() { + const user = await getAnotherUserData(); return ( -
-
- - -
+ ); } diff --git a/src/components/auth/LoginForm.tsx b/src/components/auth/LoginForm.tsx index 6e827d7..631e871 100644 --- a/src/components/auth/LoginForm.tsx +++ b/src/components/auth/LoginForm.tsx @@ -2,46 +2,116 @@ import { signIn } from "next-auth/react"; import { Button } from "../ui/button"; -import { - Card, - CardContent, - CardDescription, - CardHeader, - CardTitle, -} from "../ui/card"; -import { Field, FieldGroup } from "../ui/field"; import { FcGoogle } from "react-icons/fc"; -import { BarChart3 } from "lucide-react"; +import { BarChart3, Moon, Sun } from "lucide-react"; +import { useTheme } from "@/src/context/ThemeContext"; export function LoginForm() { + const { darkMode, toggleDarkMode } = useTheme(); return ( - - -
- -
- Login to SENTILAISES. - - Masuk dengan menggunakan akun Google Anda untuk mengakses beranda - SENTILAISES. - -
- -
- - - - - -
-
-
+ + +

+ SENTILAISES. +

+

+ Platform analisis sentimen ulasan laptop berbasis AI. Masuk + untuk mulai mengeksplorasi data. +

+ + +
+
+
+
+
+ + Masuk dengan + +
+
+ + + +

+ Dengan masuk, kamu menyetujui{" "} + + Syarat & Ketentuan + {" "} + dan{" "} + + Kebijakan Privasi + {" "} + kami. +

+
+ + +

+ © {new Date().getFullYear()} SENTILAISES. Dibuat untuk analisis yang + lebih cerdas. +

+ + + // + // ); } diff --git a/src/components/dashboards/AnalysisClient.tsx b/src/components/dashboards/AnalysisClient.tsx index c6ff93b..f37167d 100644 --- a/src/components/dashboards/AnalysisClient.tsx +++ b/src/components/dashboards/AnalysisClient.tsx @@ -28,7 +28,7 @@ export default function AnalysisClient({ isDark }: { isDark: boolean }) {
@@ -138,7 +138,7 @@ export default function AnalysisClient({ isDark }: { isDark: boolean }) { type="button" variant="destructive" onClick={handleCancel} - className="w-full bg-sentiment-negative text-white md:w-max px-6 py-3 mt-6 rounded-md transition-colors disabled:bg-gray-400" + className="w-full bg-sentiment-negative/10 text-sentiment-negative md:w-max px-6 py-3 mt-6 rounded-md transition-colors disabled:bg-gray-400" > Cancel @@ -148,7 +148,7 @@ export default function AnalysisClient({ isDark }: { isDark: boolean }) { type="submit" hidden={loading} disabled={!isValid} - className={`w-full md:w-max bg-primary text-white px-6 py-3 mt-6 rounded-md transition-colors disabled:bg-gray-400`} + className={`w-full md:w-max ${isDark ? "bg-gray-900 hover:bg-card hover:text-black" : "bg-primary text-white"} px-6 py-3 mt-6 rounded-md transition-colors disabled:bg-gray-400`} > {loading ? "Menganalisis..." : "Analisis Sekarang"} diff --git a/src/components/dashboards/BrandFilter.tsx b/src/components/dashboards/BrandFilter.tsx index e7a05c8..7ff3862 100644 --- a/src/components/dashboards/BrandFilter.tsx +++ b/src/components/dashboards/BrandFilter.tsx @@ -10,7 +10,7 @@ import { SelectValue, } from "../ui/select"; -export function BrandFilter() { +export function BrandFilter({ isDark }: { isDark: boolean }) { const { isLoading, totalCount, selectedBrand, validBrands, handleSelect } = useBrandFilter(); @@ -36,12 +36,12 @@ export function BrandFilter() { Semua ({totalCount.toLocaleString()}) @@ -49,7 +49,7 @@ export function BrandFilter() { {brand.name} ({brand.count.toLocaleString()}) diff --git a/src/components/dashboards/DashboardClient.tsx b/src/components/dashboards/DashboardClient.tsx index bfb0e56..2268491 100644 --- a/src/components/dashboards/DashboardClient.tsx +++ b/src/components/dashboards/DashboardClient.tsx @@ -7,7 +7,6 @@ import { Frown, Meh, MessageSquareText, - Moon, Smile, Sparkles, } from "lucide-react"; @@ -22,6 +21,7 @@ import AnalysisClient from "./AnalysisClient"; import Footer from "./Footer"; import { Button } from "../ui/button"; import ExportExcel from "./ExportExcel"; +import { useTheme } from "@/src/context/ThemeContext"; export default function DashboardClient() { const { @@ -31,15 +31,10 @@ export default function DashboardClient() { neutralCount, loading, modelData, - darkMode, - setDarkMode, percentage, scrollToResult, } = useDashboards(); - - const toggleDarkMode = () => { - setDarkMode((prevMode) => !prevMode); - }; + const { darkMode, toggleDarkMode } = useTheme(); return (

Analisis Sentimen Ulasan Laptop @@ -62,7 +56,7 @@ export default function DashboardClient() {
{loading ? ( - + ) : modelData.length > 0 ? ( ) : ( @@ -168,18 +162,18 @@ export default function DashboardClient() {
-

Ulasan Terbaru

+

Riwayat Ulasan

Hasil klasifikasi sentimen ulasan produk laptop

- - + +

- +
diff --git a/src/components/dashboards/ExportExcel.tsx b/src/components/dashboards/ExportExcel.tsx index 164fae9..0b4dc78 100644 --- a/src/components/dashboards/ExportExcel.tsx +++ b/src/components/dashboards/ExportExcel.tsx @@ -4,7 +4,7 @@ import { useReviewTable } from "@/src/hooks/useReviewTable"; import { useSearchParams } from "next/navigation"; import { downloadAllData } from "@/src/services/report.service"; -export default function ExportExcel() { +export default function ExportExcel({ isDark }: { isDark: boolean }) { const searchParams = useSearchParams(); const selectedBrand = searchParams.get("brand"); const { isLoading, data } = useReviewTable(10, selectedBrand); @@ -13,7 +13,7 @@ export default function ExportExcel() { -
-
- - - -
-
-
- - Tentang Saya -
-
-

- {bio || - "Belum ada deskripsi profil. Ceritakan sedikit tentang aktivitas dan kebutuhan laptop Anda."} -

-
-
- -
-
-
-
- - Preferensi Merek -
-
- {brands.length > 0 ? ( - brands.map((brand, i) => ( - - {brand} - - )) - ) : ( - - None - - )} -
-
- - - -
-
- - Sistem Operasi -
-
- {preferenceOS ? ( - - {preferenceOS} - - ) : ( - - None - - )} -
-
-
- -
-
- - Rentang Anggaran -
- - {budgetMin || budgetMax ? ( -
-

Dari

-

- {formatRupiah(budgetMin)} -

-
-

Hingga

-

- {formatRupiah(budgetMax)} -

-
- ) : ( -
-

Anggaran Belum Diatur.

-
- )} -
-
-
- - {showModal && ( - - )} - - ); -} diff --git a/src/components/dashboards/ProfileClient.tsx b/src/components/dashboards/ProfileClient.tsx index 0d785ab..07bd0af 100644 --- a/src/components/dashboards/ProfileClient.tsx +++ b/src/components/dashboards/ProfileClient.tsx @@ -1,34 +1,236 @@ +"use client"; import { ArrowLeft } from "lucide-react"; import Link from "next/link"; -import { getAnotherUserData } from "@/src/app/profile/lib/action"; -import ProfileCard from "./ProfileCard"; import Footer from "./Footer"; +import { motion } from "framer-motion"; +import Image from "next/image"; +import { Pencil, Wallet, Laptop, User, Monitor, Fan } from "lucide-react"; +import { ProfileClientProps } from "@/src/types"; +import { Button } from "../ui/button"; +import { Separator } from "../ui/separator"; +import { formatRupiah, toTitleCase } from "@/src/utils/datas"; +import { brandItems, OSItems, professionItems } from "@/src/utils/const"; +import { ProfileModal } from "./ProfileModal"; +import { useProfileClient } from "@/src/hooks/useProfileClient"; +import { Header } from "./Header"; +import { useDashboards } from "@/src/hooks/useDashboard"; +import { useTheme } from "@/src/context/ThemeContext"; -export default async function ProfileClient() { - const user = await getAnotherUserData(); +export default function ProfileClient(props: ProfileClientProps) { + const { + session, + router, + showModal, + name, + bio, + profession, + brands, + preferenceOS, + profileDatas, + budgetMin, + budgetMax, + setShowModal, + handleOptimisticUpdate, + } = useProfileClient(props); + const { darkMode, toggleDarkMode, mounted } = useTheme(); + + const isDark = mounted && darkMode; return ( -
-
- - - Back to Dashboard - -
+
+
- -
+
+
+ + + + Back to Dashboard + + +
+ + +
+
+
+
+ User Avatar +
+
+ +
+ {name && ( +

+ {name || "Guest User"} +

+ )} +

+ {session?.data?.user?.email || "Belum ada email"} +

+ + {profession && ( + + + + {toTitleCase(profession)} + + + )} +
+
+ + +
+
+ + + +
+
+
+ + Tentang Saya +
+
+

+ {bio || + "Belum ada deskripsi profil. Ceritakan sedikit tentang aktivitas dan kebutuhan laptop Anda."} +

+
+
+ +
+
+
+
+ + Preferensi Merek +
+
+ {brands.length > 0 ? ( + brands.map((brand, i) => ( + + {brand} + + )) + ) : ( + + None + + )} +
+
+ + + +
+
+ + Sistem Operasi +
+
+ {preferenceOS ? ( + + {preferenceOS} + + ) : ( + + None + + )} +
+
+
+ +
+
+ + Rentang Anggaran +
+ + {budgetMin || budgetMax ? ( +
+

Dari

+

+ {formatRupiah(budgetMin)} +

+
+

Hingga

+

+ {formatRupiah(budgetMax)} +

+
+ ) : ( +
+

+ Anggaran Belum Diatur. +

+
+ )} +
+
+
+ + {showModal && ( + + )} +
+
+
); } diff --git a/src/components/dashboards/ProfileModal.tsx b/src/components/dashboards/ProfileModal.tsx index 225763a..8953314 100644 --- a/src/components/dashboards/ProfileModal.tsx +++ b/src/components/dashboards/ProfileModal.tsx @@ -15,6 +15,7 @@ import { } from "../ui/select"; import { Button } from "../ui/button"; import { useProfileModal } from "@/src/hooks/useProfileModal"; +import { useEffect } from "react"; export const ProfileModal = ({ setShowModal, @@ -24,6 +25,7 @@ export const ProfileModal = ({ userData, onOptimisticUpdate, router, + darkMode, }: ExtendedModalProps) => { const { control, errors, isSubmitting, onSubmit, register, handleSubmit } = useProfileModal({ @@ -33,16 +35,36 @@ export const ProfileModal = ({ setShowModal, }); + useEffect(() => { + const observer = new MutationObserver(() => { + if (document.body.style.marginRight) { + document.body.style.marginRight = "0px"; + } + if (document.body.style.paddingRight) { + document.body.style.paddingRight = "0px"; + } + }); + + observer.observe(document.body, { + attributes: true, + attributeFilter: ["style"], + }); + + return () => observer.disconnect(); + }, []); + return ( e.stopPropagation()} + style={{ isolation: "isolate" }} >
@@ -93,12 +115,12 @@ export const ProfileModal = ({ onValueChange={field.onChange} > {professionItems.map((item) => { @@ -107,7 +129,7 @@ export const ProfileModal = ({
@@ -139,14 +161,12 @@ export const ProfileModal = ({ onValueChange={field.onChange} > {brandItems.map((item) => { @@ -155,7 +175,7 @@ export const ProfileModal = ({
@@ -189,14 +209,12 @@ export const ProfileModal = ({ onValueChange={field.onChange} > {OSItems.map((item) => { @@ -205,7 +223,7 @@ export const ProfileModal = ({
@@ -273,7 +291,11 @@ export const ProfileModal = ({ Cancel - diff --git a/src/components/dashboards/ReviewTable.tsx b/src/components/dashboards/ReviewTable.tsx index a0d189b..5fd2057 100644 --- a/src/components/dashboards/ReviewTable.tsx +++ b/src/components/dashboards/ReviewTable.tsx @@ -24,7 +24,7 @@ import { import { useSearchParams } from "next/navigation"; import { getVisiblePages } from "@/src/utils/datas"; -export function ReviewTable() { +export function ReviewTable({ isDark }: { isDark: boolean }) { const searchParams = useSearchParams(); const selectedBrand = searchParams.get("brand"); const { currentData, isLoading, pagination } = useReviewTable( @@ -36,8 +36,10 @@ export function ReviewTable() { if (isLoading) { return ( -
- +
+

Memuat data ulasan...

); @@ -45,10 +47,14 @@ export function ReviewTable() { return (
-
- +
+
- + Produk Ulasan & Kata Kunci @@ -90,11 +96,13 @@ export function ReviewTable() {
- + {review.product?.brand?.name || "Generic"}
- + {review.product?.name || "Unknown Product"}
@@ -102,7 +110,7 @@ export function ReviewTable() {
-

+

{review.content}

@@ -112,7 +120,7 @@ export function ReviewTable() { {k} @@ -123,7 +131,7 @@ export function ReviewTable() { - + {review.createdAt ? new Date(review.createdAt).toLocaleDateString( "id-ID", @@ -138,11 +146,11 @@ export function ReviewTable() { - {getSentimentBadge(review.sentiment ?? null)} + {getSentimentBadge(review.sentiment ?? null, isDark)} - + {review.confidenceScore ? `${(review.confidenceScore * 100).toFixed(1)}%` : "-"} @@ -168,7 +176,7 @@ export function ReviewTable() { className={ currentPage === 1 ? "pointer-events-none opacity-50" - : "cursor-pointer hover:bg-[#F8FBFF] hover:text-primary" + : `text-card cursor-pointer hover:bg-[#F8FBFF] hover:text-primary ${isDark ? "hover:bg-gray-900 hover:text-card" : "text-black"} transition-all duration-500` } /> @@ -185,6 +193,7 @@ export function ReviewTable() { pagination.goToPage(page as number); }} isActive={currentPage === page} + className={`transition-all duration-500 ${isDark ? "text-white hover:bg-gray-200 hover:text-black focus:bg-gray-200 focus:text-black" : "text-black hover:bg-primary hover:text-card bg-transparent"}`} > {page} @@ -202,7 +211,7 @@ export function ReviewTable() { className={ currentPage === totalPages ? "pointer-events-none opacity-50" - : "cursor-pointer hover:bg-primary hover:text-card" + : `cursor-pointer ${isDark ? "text-white hover:bg-gray-200 hover:text-black" : "text-black hover:bg-primary hover:text-card"} transition-all duration-500` } /> diff --git a/src/components/dashboards/SentimentBadge.tsx b/src/components/dashboards/SentimentBadge.tsx index a1da21d..283dd77 100644 --- a/src/components/dashboards/SentimentBadge.tsx +++ b/src/components/dashboards/SentimentBadge.tsx @@ -2,11 +2,11 @@ import { Review } from "@/src/types"; import { Badge } from "../ui/badge"; import { cn } from "@/lib/utils"; -const getSentimentBadge = (sentiment: Review["sentiment"]) => { +const getSentimentBadge = (sentiment: Review["sentiment"], isDark: boolean) => { const styles: Record = { - POSITIVE: "sentiment-positive", - NEGATIVE: "sentiment-negative", - NEUTRAL: "sentiment-neutral", + POSITIVE: ` ${isDark ? "text-sentiment-positive bg-sentiment-positive/10" : "text-sentiment-positive bg-sentiment-positive/10"}`, + NEGATIVE: ` ${isDark ? "text-sentiment-negative bg-sentiment-negative/10" : "text-sentiment-negative bg-sentiment-negative/10"}`, + NEUTRAL: ` ${isDark ? "text-sentiment-neutral bg-sentiment-neutral/10" : "text-sentiment-neutral bg-sentiment-neutral/10"}`, }; const labels: Record = { diff --git a/src/components/dashboards/WordCloud.tsx b/src/components/dashboards/WordCloud.tsx index e38064c..1a3c051 100644 --- a/src/components/dashboards/WordCloud.tsx +++ b/src/components/dashboards/WordCloud.tsx @@ -10,7 +10,9 @@ export function WordCloud({ isDark }: { isDark: boolean }) { return (
{isEmpty ? ( -
+
diff --git a/src/components/skeletons/ModelInfoSkeleton.tsx b/src/components/skeletons/ModelInfoSkeleton.tsx index 73b1fe8..46aa5b7 100644 --- a/src/components/skeletons/ModelInfoSkeleton.tsx +++ b/src/components/skeletons/ModelInfoSkeleton.tsx @@ -1,8 +1,10 @@ import { ChevronDown } from "lucide-react"; -export function ModelInfoSkeleton() { +export function ModelInfoSkeleton({ isDark }: { isDark: boolean }) { return ( -
+
@@ -10,12 +12,18 @@ export function ModelInfoSkeleton() {
-
+
-
-
+
+
@@ -25,25 +33,32 @@ export function ModelInfoSkeleton() { className="flex items-center gap-3 rounded-lg border border-border/40 bg-secondary/50 p-3" >
-
+
-
-
+
+
))}
- {/* Footer info */}
{[1, 2, 3].map((i) => (
- {/* label */} -
- {/* value */} -
+
+
))}
diff --git a/src/components/ui/button.tsx b/src/components/ui/button.tsx index b45e2b5..b35bfda 100644 --- a/src/components/ui/button.tsx +++ b/src/components/ui/button.tsx @@ -19,7 +19,9 @@ const buttonVariants = cva( ghost: "hover:bg-accent hover:text-accent-foreground dark:hover:bg-accent/50", link: "text-primary underline-offset-4 hover:underline", - primary: "bg-primary text-card" + primary: "bg-primary text-card", + darkMode: + "bg-gray-800 text-white hover:bg-gray-900 border border-gray-700", }, size: { default: "h-9 px-4 py-2 has-[>svg]:px-3", diff --git a/src/components/ui/pagination.tsx b/src/components/ui/pagination.tsx index 448b84e..26770ee 100644 --- a/src/components/ui/pagination.tsx +++ b/src/components/ui/pagination.tsx @@ -55,7 +55,7 @@ function PaginationLink({ data-active={isActive} className={cn( buttonVariants({ - variant: isActive ? "primary" : "ghost", + variant: isActive ? "darkMode" : "ghost", size, }), className, diff --git a/src/components/ui/select.tsx b/src/components/ui/select.tsx index a0944e6..25b14c7 100644 --- a/src/components/ui/select.tsx +++ b/src/components/ui/select.tsx @@ -44,7 +44,7 @@ function SelectTrigger({ > {children} - + ); diff --git a/src/context/ThemeContext.tsx b/src/context/ThemeContext.tsx new file mode 100644 index 0000000..5803a5c --- /dev/null +++ b/src/context/ThemeContext.tsx @@ -0,0 +1,41 @@ +"use client"; + +import { createContext, useContext, useEffect, useState } from "react"; + +interface ThemeContextType { + darkMode: boolean; + toggleDarkMode: () => void; + mounted: boolean; +} + +const ThemeContext = createContext(undefined); + +export const ThemeProvider = ({ children }: { children: React.ReactNode }) => { + const [darkMode, setDarkMode] = useState(false); + const [mounted, setMounted] = useState(false); + + useEffect(() => { + const stored = localStorage.getItem("theme"); + setDarkMode(stored === "dark"); + setMounted(true); + }, []); + + useEffect(() => { + if (!mounted) return; + localStorage.setItem("theme", darkMode ? "dark" : "light"); + }, [darkMode, mounted]); + + const toggleDarkMode = () => setDarkMode((prev) => !prev); + + return ( + + {children} + + ); +}; + +export const useTheme = () => { + const context = useContext(ThemeContext); + if (!context) throw new Error("useTheme must be used within ThemeProvider"); + return context; +}; diff --git a/src/hooks/useDashboard.ts b/src/hooks/useDashboard.ts index 9c7baab..09c2165 100644 --- a/src/hooks/useDashboard.ts +++ b/src/hooks/useDashboard.ts @@ -16,7 +16,6 @@ export const useDashboards = () => { negative: 0, neutral: 0, }); - const [darkMode, setDarkMode] = useState(false); useEffect(() => { async function fetchStats() { @@ -85,8 +84,6 @@ export const useDashboards = () => { selectedBrand, loading, modelData, - darkMode, - setDarkMode, setSelectedBrand, percentage, scrollToResult, diff --git a/src/types/index.ts b/src/types/index.ts index 2e75582..b119c31 100644 --- a/src/types/index.ts +++ b/src/types/index.ts @@ -299,6 +299,7 @@ export interface ExtendedModalProps extends ProfileModalProps { userData: any; onOptimisticUpdate: (data: ProfileFormData) => void; router: any; + darkMode: boolean; } export interface ProfileState { diff --git a/src/utils/datas.ts b/src/utils/datas.ts index c6b615c..939ca7e 100644 --- a/src/utils/datas.ts +++ b/src/utils/datas.ts @@ -19,11 +19,11 @@ export const setWordCloud = ({ maxValue, minValue }: WordCloudConfig) => { const getColor = (sentiment: WordItem["sentiment"]) => { switch (sentiment) { case "POSITIVE": - return "text-sentiment-positive hover:bg-sentiment-positive-light"; + return "text-sentiment-positive hover:bg-sentiment-positive/10"; case "NEGATIVE": - return "text-sentiment-negative hover:bg-sentiment-negative-light"; + return "text-sentiment-negative hover:bg-sentiment-negative/10"; case "NEUTRAL": - return "text-sentiment-neutral hover:bg-sentiment-neutral-light"; + return "text-sentiment-neutral hover:bg-sentiment-neutral/10"; default: return "hover:bg-primary hover:text-card"; }