42 lines
1.3 KiB
TypeScript
42 lines
1.3 KiB
TypeScript
"use client";
|
|
|
|
import { type ComponentProps, memo } from "react";
|
|
import { Streamdown } from "streamdown";
|
|
import { cn } from "@/lib/utils";
|
|
import { ImagePreview } from "@/components/image-preview";
|
|
import { VideoPreview } from "@/components/video-preview";
|
|
|
|
type ResponseProps = ComponentProps<typeof Streamdown> & {
|
|
onImageEdit?: (imageUrl: string) => void;
|
|
};
|
|
|
|
export const Response = memo(
|
|
({ className, onImageEdit, ...props }: ResponseProps) => (
|
|
<Streamdown
|
|
className={cn(
|
|
"size-full [&>*:first-child]:mt-0 [&>*:last-child]:mb-0 [&_code]:whitespace-pre-wrap [&_code]:break-words [&_pre]:max-w-full [&_pre]:overflow-x-auto",
|
|
className
|
|
)}
|
|
components={{
|
|
img: ({ src, alt }: { src?: string; alt?: string }) => {
|
|
if (!src) {
|
|
return null;
|
|
}
|
|
return <ImagePreview src={src} alt={alt} onImageEdit={onImageEdit} />;
|
|
},
|
|
video: ({ src, alt }: { src?: string; alt?: string }) => {
|
|
if (!src) {
|
|
return null;
|
|
}
|
|
return <VideoPreview src={src} alt={alt} />;
|
|
},
|
|
}}
|
|
{...props}
|
|
/>
|
|
),
|
|
(prevProps: ResponseProps, nextProps: ResponseProps) =>
|
|
prevProps.children === nextProps.children && prevProps.onImageEdit === nextProps.onImageEdit
|
|
);
|
|
|
|
Response.displayName = "Response";
|