From ac05ecf1963bc6d11561b9eec89f27425ec56e39 Mon Sep 17 00:00:00 2001
From: Ahmad Mujahid <55625580+AhmadMuj@users.noreply.github.com>
Date: Sat, 22 Jun 2024 17:47:10 +0400
Subject: feature(web): Enhance the bookmark textarea in the list layout (#247)

* Allow the user to expand the textarea in the list mode to support larger notes

* Expand the textarea to a max of half the screen size in the list layout only

* Move onInput to a separate method

* Restoring the textfield to its original state after submitting

* Moving the reset form to the mutate onSuccess event to not reset the height on a fail request
---
 .../components/dashboard/bookmarks/EditorCard.tsx  | 31 ++++++++++++++++++++--
 1 file changed, 29 insertions(+), 2 deletions(-)

(limited to 'apps/web/components/dashboard/bookmarks/EditorCard.tsx')

diff --git a/apps/web/components/dashboard/bookmarks/EditorCard.tsx b/apps/web/components/dashboard/bookmarks/EditorCard.tsx
index 9899d5d3..3006a964 100644
--- a/apps/web/components/dashboard/bookmarks/EditorCard.tsx
+++ b/apps/web/components/dashboard/bookmarks/EditorCard.tsx
@@ -9,7 +9,10 @@ import { Textarea } from "@/components/ui/textarea";
 import { toast } from "@/components/ui/use-toast";
 import BookmarkAlreadyExistsToast from "@/components/utils/BookmarkAlreadyExistsToast";
 import { useClientConfig } from "@/lib/clientConfig";
-import { useBookmarkLayoutSwitch } from "@/lib/userLocalSettings/bookmarksLayout";
+import {
+  useBookmarkLayout,
+  useBookmarkLayoutSwitch,
+} from "@/lib/userLocalSettings/bookmarksLayout";
 import { cn } from "@/lib/utils";
 import { zodResolver } from "@hookform/resolvers/zod";
 import { useForm } from "react-hook-form";
@@ -48,6 +51,7 @@ export default function EditorCard({ className }: { className?: string }) {
     React.useState<MultiUrlImportState | null>(null);
 
   const demoMode = !!useClientConfig().demoMode;
+  const bookmarkLayout = useBookmarkLayout();
   const formSchema = z.object({
     text: z.string(),
   });
@@ -70,6 +74,9 @@ export default function EditorCard({ className }: { className?: string }) {
         });
       }
       form.reset();
+      if (inputRef?.current?.style) {
+        inputRef.current.style.height = "auto";
+      }
     },
     onError: (e) => {
       toast({ description: e.message, variant: "destructive" });
@@ -99,6 +106,21 @@ export default function EditorCard({ className }: { className?: string }) {
     setMultiUrlImportState({ urls, text });
   }
 
+  const onInput = (e: React.FormEvent<HTMLTextAreaElement>) => {
+    // Expand the textarea to a max of half the screen size in the list layout only
+    if (bookmarkLayout === "list") {
+      const target = e.target as HTMLTextAreaElement;
+      const maxHeight = window.innerHeight * 0.5;
+      target.style.height = "auto";
+
+      if (target.scrollHeight <= maxHeight) {
+        target.style.height = `${target.scrollHeight}px`;
+      } else {
+        target.style.height = `${maxHeight}px`;
+      }
+    }
+  };
+
   const onSubmit: SubmitHandler<z.infer<typeof formSchema>> = (data) => {
     const text = data.text.trim();
     try {
@@ -108,6 +130,7 @@ export default function EditorCard({ className }: { className?: string }) {
       mutate({ type: "text", text });
     }
   };
+
   const onError: SubmitErrorHandler<z.infer<typeof formSchema>> = (errors) => {
     toast({
       description: Object.values(errors)
@@ -163,7 +186,10 @@ export default function EditorCard({ className }: { className?: string }) {
             <Textarea
               ref={inputRef}
               disabled={isPending}
-              className="h-full w-full resize-none border-none text-lg focus-visible:ring-0"
+              className={cn(
+                "h-full w-full border-none text-lg focus-visible:ring-0",
+                { "resize-none": bookmarkLayout !== "list" },
+              )}
               placeholder={
                 "Paste a link or an image, write a note or drag and drop an image in here ..."
               }
@@ -181,6 +207,7 @@ export default function EditorCard({ className }: { className?: string }) {
                 }
                 handlePaste(e);
               }}
+              onInput={onInput}
               {...textFieldProps}
             />
           </FormControl>
-- 
cgit v1.2.3-70-g09d2

