From 6fe10122707cdbb789f45b75bace7caec71ccb85 Mon Sep 17 00:00:00 2001 From: ecwu Date: Fri, 3 Jan 2025 00:33:02 +0800 Subject: [PATCH] add Navbar component and integrate into App layout --- src/components/navbar.tsx | 133 ++++++++++++++++++++++++++++++++++ src/pages/App.tsx | 147 +++++++------------------------------- 2 files changed, 159 insertions(+), 121 deletions(-) create mode 100644 src/components/navbar.tsx diff --git a/src/components/navbar.tsx b/src/components/navbar.tsx new file mode 100644 index 0000000..1229a1c --- /dev/null +++ b/src/components/navbar.tsx @@ -0,0 +1,133 @@ +import React from "react"; +import { Badge } from "./ui/badge"; +import { + Menubar, + MenubarContent, + MenubarItem, + MenubarMenu, + MenubarSeparator, + MenubarTrigger, + MenubarCheckboxItem, +} from "@/components/ui/menubar"; +import { + Popover, + PopoverContent, + PopoverTrigger, +} from "@/components/ui/popover"; +import { ModeToggle } from "@/components/mode-toggle"; +import { SidebarTrigger } from "@/components/ui/sidebar"; +import { Separator } from "@/components/ui/separator"; +import { + EllipsisIcon, + WholeWordIcon, + CircleDollarSignIcon, + RulerIcon, + ReceiptIcon, + WalletIcon, + ArrowUpDownIcon, + ScissorsIcon, +} from "lucide-react"; +import { AppContext } from "@/pages/App"; +import { models } from "@/types/models"; +import { getTotalCost } from "@/utils/totalCost"; +import { Tr } from "@/translate"; + +import { useContext } from "react"; + +const Navbar: React.FC = () => { + const ctx = useContext(AppContext); + if (!ctx) return
error
; + const { chatStore, setChatStore } = ctx; + + return ( +
+
+ + +

{chatStore.model}

+
+
+
+ + {chatStore.totalTokens.toString()} + + + + + + +

+ Tokens: {chatStore.totalTokens}/{chatStore.maxTokens} +

+

+ Cut(s): {chatStore.postBeginIndex}/ + {chatStore.history.filter(({ hide }) => !hide).length} +

+

+ Cost: ${chatStore.cost?.toFixed(4)} / $ + {getTotalCost().toFixed(2)} +

+
+
+
+
+ + + + {" "} + {chatStore.totalTokens} + + {chatStore.cost?.toFixed(4)} + + + + + Max Length: {chatStore.maxTokens} + + + + Price:{" "} + {models[chatStore.model]?.price?.prompt * 1000 * 1000}$ / + 1M input tokens + + + + Total: {getTotalCost().toFixed(2)}$ + + + + {chatStore.streamMode ? ( + <> + {Tr("STREAM")}· + {Tr("FETCH")} + + ) : ( + <> + {Tr("STREAM")}· + {Tr("FETCH")} + + )} + + + + {chatStore.postBeginIndex} / {chatStore.history.length} + + + Switch to Model (TODO): + gpt-4o + gpt-o1 + gpt-o1-mini + gpt-o3 + + + +
+
+ +
+
+
+ ); +}; + +export default Navbar; diff --git a/src/pages/App.tsx b/src/pages/App.tsx index dc0f33f..c1a0c90 100644 --- a/src/pages/App.tsx +++ b/src/pages/App.tsx @@ -115,6 +115,8 @@ import { import { Badge } from "@/components/ui/badge"; import { ModeToggle } from "@/components/mode-toggle"; +import Navbar from "@/components/navbar"; + export function App() { // init selected index const [selectedChatIndex, setSelectedChatIndex] = useState( @@ -356,7 +358,27 @@ export function App() { console.log("[PERFORMANCE!] reading localStorage"); return ( - <> +