diff --git a/src/components/Icons.jsx b/src/components/Icons.jsx index 0a8bc49..5a65614 100644 --- a/src/components/Icons.jsx +++ b/src/components/Icons.jsx @@ -102,6 +102,16 @@ export const IconBlogMarketing = () => ); +export const IconPortfolio = () => + svg( + <> + + + + + + ); + export const IconBuilding = () => svg( <> diff --git a/src/pages/portfolio/IntroTab.jsx b/src/pages/portfolio/IntroTab.jsx new file mode 100644 index 0000000..08d30f3 --- /dev/null +++ b/src/pages/portfolio/IntroTab.jsx @@ -0,0 +1,94 @@ +import { useState } from 'react'; + +const emptyIntro = { title: '', content: '', is_main: 0 }; + +export default function IntroTab({ introductions, editing, api, onRefresh }) { + const [form, setForm] = useState(null); + const [copiedId, setCopiedId] = useState(null); + + const save = async () => { + if (form.id) { + await api.editIntro(form.id, { title: form.title, content: form.content }); + } else { + await api.addIntro(form); + } + setForm(null); + onRefresh(); + }; + + const remove = async (id) => { + await api.removeIntro(id); + onRefresh(); + }; + + const setMain = async (id) => { + await api.setMainIntro(id); + onRefresh(); + }; + + const copyToClipboard = async (intro) => { + try { + await navigator.clipboard.writeText(intro.content); + setCopiedId(intro.id); + setTimeout(() => setCopiedId(null), 1500); + } catch { + /* 무시 */ + } + }; + + return ( +
+ {editing && ( +
+ +
+ )} + + {/* 작성/수정 폼 */} + {form && ( +
+ +