Added deeplinks, added qr code login, added settings, other stuff
This commit is contained in:
parent
462fc19591
commit
8ff8bd9528
32 changed files with 917 additions and 78 deletions
|
|
@ -1,5 +1,5 @@
|
|||
import { Button } from "@tensamin/ui/cmp/button";
|
||||
import { ArrowLeft, House, Phone, User } from "lucide-react";
|
||||
import { ArrowLeft, House, Phone, Settings, User } from "lucide-react";
|
||||
import { useLocation, useNavigate, useSearch } from "@tanstack/react-router";
|
||||
import { useCall } from "@tensamin/call/context";
|
||||
import Wrapper from "@tensamin/user/wrapper";
|
||||
|
|
@ -22,6 +22,7 @@ export default function Navbar({ forMobile }: { forMobile: boolean }) {
|
|||
const { contacts } = useTTP();
|
||||
|
||||
const { pathname } = useLocation();
|
||||
|
||||
const { id } = useSearch({ strict: false });
|
||||
|
||||
const currentCalls = id ? contacts?.[id]?.calls || [] : [];
|
||||
|
|
@ -43,13 +44,23 @@ export default function Navbar({ forMobile }: { forMobile: boolean }) {
|
|||
<ArrowLeft className="size-4.5" />
|
||||
</SidebarTrigger>
|
||||
) : (
|
||||
<Button
|
||||
onClick={() => navigate({ to: "/" })}
|
||||
className="w-9 h-9 aspect-square rounded-lg"
|
||||
variant="outline"
|
||||
>
|
||||
<House className="size-4.5" />
|
||||
</Button>
|
||||
<>
|
||||
<Button
|
||||
onClick={() => navigate({ to: "/" })}
|
||||
className="w-9 h-9 aspect-square rounded-lg"
|
||||
variant="outline"
|
||||
>
|
||||
<House className="size-4.5" />
|
||||
</Button>
|
||||
<Button
|
||||
// @ts-expect-error TanStack router doesn't properly detect the settings route
|
||||
onClick={() => navigate({ to: "/settings" })}
|
||||
className="w-9 h-9 aspect-square rounded-lg"
|
||||
variant="outline"
|
||||
>
|
||||
<Settings className="size-4.5" />
|
||||
</Button>
|
||||
</>
|
||||
)}
|
||||
{pathname === "/chat" && (
|
||||
<Wrapper
|
||||
|
|
@ -126,22 +137,36 @@ export function MobileNavbar() {
|
|||
|
||||
return (
|
||||
<div className="z-51 w-full pb-[env(safe-area-inset-bottom)] bg-card border-t">
|
||||
<div className="z-51 w-full h-14 flex justify-center items-center gap-8">
|
||||
<div className="z-51 w-full h-15 grid grid-cols-3 items-center place-items-center px-5">
|
||||
<SidebarTrigger
|
||||
className="text-foreground w-12! h-12! aspect-square rounded-xl"
|
||||
className="text-foreground w-12! h-12! aspect-square rounded-xl flex flex-col gap-1"
|
||||
variant="link"
|
||||
>
|
||||
<User className="size-5.5" />
|
||||
<User className="size-4.5" />
|
||||
<p className="text-xs">Chats</p>
|
||||
</SidebarTrigger>
|
||||
<Button
|
||||
onClick={() => {
|
||||
navigate({ to: "/" });
|
||||
setOpenMobile(false);
|
||||
}}
|
||||
className="text-foreground w-12 h-12 aspect-square rounded-xl"
|
||||
className="text-foreground w-12 h-12 aspect-square rounded-xl flex flex-col gap-1"
|
||||
variant="link"
|
||||
>
|
||||
<House className="size-5.5" />
|
||||
<House className="size-4.5" />
|
||||
<p className="text-xs">Home</p>
|
||||
</Button>
|
||||
<Button
|
||||
onClick={() => {
|
||||
// @ts-expect-error TanStack router doesn't properly detect the settings route
|
||||
navigate({ to: "/settings" });
|
||||
setOpenMobile(false);
|
||||
}}
|
||||
className="text-foreground w-12 h-12 aspect-square rounded-xl flex flex-col gap-1"
|
||||
variant="link"
|
||||
>
|
||||
<Settings className="size-4.5" />
|
||||
<p className="text-xs">Settings</p>
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -6,6 +6,8 @@ import { log, toast } from "@tensamin/shared/log";
|
|||
import { File } from "lucide-react";
|
||||
import * as React from "react";
|
||||
import { z } from "zod";
|
||||
import { isTauri } from "@tauri-apps/api/core";
|
||||
import QrCodeScanner from "@tensamin/tauri/qrCodeScanner";
|
||||
|
||||
const fetchedUser = z.object({
|
||||
id: z.uuidv4(),
|
||||
|
|
@ -145,15 +147,46 @@ export default function Form() {
|
|||
[save],
|
||||
);
|
||||
|
||||
const isTauriEnv = isTauri();
|
||||
|
||||
return (
|
||||
<div className="flex md:flex-row flex-col gap-15">
|
||||
<div
|
||||
onClick={() => uploadRef.current?.click()}
|
||||
className="flex flex-col gap-3 cursor-pointer w-55 aspect-square bg-input/13 hover:bg-input/30 transition-all duration-300 ease-in-out border-3 items-center justify-center rounded-lg"
|
||||
>
|
||||
<File className="text-foreground" size={27} />
|
||||
<p className="text-md">Select .tu file</p>
|
||||
</div>
|
||||
{isTauriEnv ? (
|
||||
<>
|
||||
<QrCodeScanner
|
||||
onData={(data) => {
|
||||
if (!data.startsWith("tensamin://tu::")) {
|
||||
toast("error", "Invalid QR code");
|
||||
return;
|
||||
} else {
|
||||
const decoded = data.replace("tensamin://tu::", "");
|
||||
|
||||
try {
|
||||
const { userId, privateKey } = parseTuFileContent(decoded);
|
||||
save("session_id", Date.now());
|
||||
save("user_id", userId);
|
||||
save("private_key", privateKey);
|
||||
location.href = "/";
|
||||
} catch (error) {
|
||||
log(0, "login", "red", error);
|
||||
toast("error", "Failed to parse QR code data");
|
||||
}
|
||||
}
|
||||
}}
|
||||
/>
|
||||
<Button onClick={() => uploadRef.current?.click()}>
|
||||
Select .tu file
|
||||
</Button>
|
||||
</>
|
||||
) : (
|
||||
<div
|
||||
onClick={() => uploadRef.current?.click()}
|
||||
className="flex flex-col gap-3 cursor-pointer w-55 aspect-square bg-input/13 hover:bg-input/30 transition-all duration-300 ease-in-out border-3 items-center justify-center rounded-lg"
|
||||
>
|
||||
<File className="text-foreground" size={27} />
|
||||
<p className="text-md">Select .tu file</p>
|
||||
</div>
|
||||
)}
|
||||
<input
|
||||
accept=".tu"
|
||||
onChange={handleFileInputChange}
|
||||
|
|
|
|||
|
|
@ -10,9 +10,9 @@ import {
|
|||
import { isTauri } from "@tauri-apps/api/core";
|
||||
import { useIsMobile } from "@tensamin/ui/utils";
|
||||
import { MobileNavbar } from "./navbar";
|
||||
import { useLocation } from "@tanstack/react-router";
|
||||
|
||||
import SidebarBox from "@tensamin/call/sidebarBox";
|
||||
import { useShowMobileNavbar } from "@/routes/app/layout";
|
||||
|
||||
/**
|
||||
* Renders the conversation sidebar with account summary and conversation list.
|
||||
|
|
@ -20,7 +20,7 @@ import SidebarBox from "@tensamin/call/sidebarBox";
|
|||
*/
|
||||
export default function Sidebar() {
|
||||
const isMobile = useIsMobile();
|
||||
const location = useLocation();
|
||||
const showMobileNavbar = useShowMobileNavbar();
|
||||
|
||||
return (
|
||||
<SidebarRoot>
|
||||
|
|
@ -42,7 +42,7 @@ export default function Sidebar() {
|
|||
</div>
|
||||
</div>
|
||||
</SidebarContent>
|
||||
{isMobile && location.pathname === "/chat" && (
|
||||
{isMobile && !showMobileNavbar && (
|
||||
<SidebarFooter className="p-0!">
|
||||
<MobileNavbar />
|
||||
</SidebarFooter>
|
||||
|
|
|
|||
Loading…
Reference in a new issue