* feat: add YouTube video embed support for TipTap editor - Paste YouTube URLs to auto-embed videos with metadata - Edit video title and URL through dropdown menu - Convert embed back to plain URL link - Fetch video titles automatically via YouTube oEmbed API * fix: - reverted NewCardForm CSS properties back to max-h-48. - Added boolean prop to TipTap Edtior for YouTube embed. - Disabled YouTube embed feature for NewCardForm Editor * chore: lint * chore: translations * chore: update translations --------- Co-authored-by: Henry <henry_ball@hotmail.co.uk>
83 lines
1.7 KiB
TypeScript
83 lines
1.7 KiB
TypeScript
import type { NodeViewProps } from "@tiptap/react";
|
|
import { NodeViewWrapper } from "@tiptap/react";
|
|
|
|
import { extractVideoId } from "./utils";
|
|
import YouTubeCard from "./YouTubeCard";
|
|
|
|
export default function YouTubeNodeView({
|
|
node,
|
|
editor,
|
|
getPos,
|
|
deleteNode,
|
|
updateAttributes,
|
|
}: NodeViewProps) {
|
|
const { videoId, title, url, showEmbed } = node.attrs as {
|
|
videoId: string;
|
|
title: string;
|
|
url: string;
|
|
showEmbed: boolean;
|
|
};
|
|
|
|
const handleConvertToLink = () => {
|
|
const pos = getPos();
|
|
if (typeof pos !== "number") return;
|
|
|
|
const linkContent = {
|
|
type: "paragraph",
|
|
content: [
|
|
{
|
|
type: "text",
|
|
text: url,
|
|
marks: [
|
|
{
|
|
type: "link",
|
|
attrs: {
|
|
href: url,
|
|
target: "_blank",
|
|
},
|
|
},
|
|
],
|
|
},
|
|
],
|
|
};
|
|
|
|
editor
|
|
.chain()
|
|
.focus()
|
|
.deleteRange({ from: pos, to: pos + node.nodeSize })
|
|
.insertContentAt(pos, linkContent)
|
|
.run();
|
|
};
|
|
|
|
const handleDelete = () => {
|
|
deleteNode();
|
|
};
|
|
|
|
const handleUpdate = (newUrl: string, newTitle: string) => {
|
|
if (newUrl !== url) {
|
|
const newVideoId = extractVideoId(newUrl);
|
|
updateAttributes({
|
|
url: newUrl,
|
|
title: newTitle,
|
|
videoId: newVideoId,
|
|
});
|
|
} else {
|
|
updateAttributes({ title: newTitle });
|
|
}
|
|
};
|
|
|
|
return (
|
|
<NodeViewWrapper>
|
|
<YouTubeCard
|
|
videoId={videoId}
|
|
url={url}
|
|
title={title}
|
|
showEmbed={showEmbed}
|
|
onConvertToLink={handleConvertToLink}
|
|
onDelete={handleDelete}
|
|
onUpdate={handleUpdate}
|
|
/>
|
|
</NodeViewWrapper>
|
|
);
|
|
}
|