From 9f5dc012b2709f9b65035fb470a1ec34cb82500b Mon Sep 17 00:00:00 2001 From: bracesproul Date: Tue, 29 Oct 2024 17:17:39 -0700 Subject: [PATCH] make editable --- src/components/artifacts/TextRenderer.tsx | 105 ++++++++++++++++++---- src/constants.ts | 2 +- 2 files changed, 87 insertions(+), 20 deletions(-) diff --git a/src/components/artifacts/TextRenderer.tsx b/src/components/artifacts/TextRenderer.tsx index 2d324196..1454783e 100644 --- a/src/components/artifacts/TextRenderer.tsx +++ b/src/components/artifacts/TextRenderer.tsx @@ -1,4 +1,4 @@ -import { useEffect, useRef, useState } from "react"; +import { Dispatch, SetStateAction, useEffect, useRef, useState } from "react"; import { ArtifactMarkdownV3 } from "@/types"; import "@blocknote/core/fonts/inter.css"; import { @@ -14,13 +14,44 @@ import { getArtifactContent } from "@/contexts/utils"; import { useGraphContext } from "@/contexts/GraphContext"; import React from "react"; import { TooltipIconButton } from "../ui/assistant-ui/tooltip-icon-button"; -import { Eye } from "lucide-react"; -import { cn } from "@/lib/utils"; +import { Eye, EyeOff } from "lucide-react"; +import { motion } from "framer-motion"; +import { Textarea } from "../ui/textarea"; const cleanText = (text: string) => { return text.replaceAll("\\\n", "\n"); }; +function ViewRawText({ + isRawView, + setIsRawView, +}: { + isRawView: boolean; + setIsRawView: Dispatch>; +}) { + return ( + + setIsRawView((p) => !p)} + > + {isRawView ? ( + + ) : ( + + )} + + + ); +} + export interface TextRendererProps { isEditing: boolean; isHovering: boolean; @@ -126,6 +157,18 @@ export function TextRendererComponent(props: TextRendererProps) { useEffect(() => { if (isRawView) { editor.blocksToMarkdownLossy(editor.document).then(setRawMarkdown); + } else if (!isRawView && rawMarkdown) { + try { + (async () => { + setManuallyUpdatingArtifact(true); + const markdownAsBlocks = + await editor.tryParseMarkdownToBlocks(rawMarkdown); + editor.replaceBlocks(editor.document, markdownAsBlocks); + setManuallyUpdatingArtifact(false); + })(); + } catch (_) { + setManuallyUpdatingArtifact(false); + } } }, [isRawView, editor]); @@ -170,29 +213,53 @@ export function TextRendererComponent(props: TextRendererProps) { }); }; + const onChangeRawMarkdown = (e: React.ChangeEvent) => { + const newRawMarkdown = e.target.value; + setRawMarkdown(newRawMarkdown); + setArtifact((prev) => { + if (!prev) { + return { + currentIndex: 1, + contents: [ + { + index: 1, + fullMarkdown: newRawMarkdown, + title: "Untitled", + type: "text", + }, + ], + }; + } else { + return { + ...prev, + contents: prev.contents.map((c) => { + if (c.index === prev.currentIndex) { + return { + ...c, + fullMarkdown: newRawMarkdown, + }; + } + return c; + }), + }; + } + }); + }; + return (
{props.isHovering && artifact && ( -
+
- setIsRawView((p) => !p)} - className={cn( - "transition-colors w-fit h-fit p-2", - isRawView && "bg-gray-100 text-gray-900" - )} - > - - +
)} {isRawView ? ( -
-          {rawMarkdown}
-        
+