Neah/components/carnet/editor.tsx
2025-04-20 17:31:14 +02:00

129 lines
3.6 KiB
TypeScript

"use client";
import React, { useState, useEffect } from 'react';
import { Image, FileText, Link, List } from 'lucide-react';
interface Note {
id: string;
title: string;
content: string;
lastEdited: Date;
category?: string;
tags?: string[];
}
interface EditorProps {
note?: Note | null;
onSave?: (note: Note) => void;
currentFolder?: string;
}
export const Editor: React.FC<EditorProps> = ({ note, onSave, currentFolder = 'Notes' }) => {
const [title, setTitle] = useState(note?.title || '');
const [content, setContent] = useState(note?.content || '');
const [isSaving, setIsSaving] = useState(false);
useEffect(() => {
if (note) {
setTitle(note.title);
setContent(note.content);
}
}, [note]);
const handleTitleChange = (e: React.ChangeEvent<HTMLInputElement>) => {
setTitle(e.target.value);
};
const handleContentChange = (e: React.ChangeEvent<HTMLTextAreaElement>) => {
setContent(e.target.value);
};
const handleSave = async () => {
if (!title || !content) return;
setIsSaving(true);
try {
const endpoint = note?.id ? '/api/nextcloud/files' : '/api/nextcloud/files';
const method = note?.id ? 'PUT' : 'POST';
const response = await fetch(endpoint, {
method,
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
id: note?.id,
title,
content,
folder: currentFolder
}),
});
if (!response.ok) {
throw new Error('Failed to save note');
}
const savedNote = await response.json();
onSave?.({
id: savedNote.id,
title: savedNote.title,
content,
lastEdited: new Date(savedNote.lastModified),
category: note?.category,
tags: note?.tags
});
} catch (error) {
console.error('Error saving note:', error);
// TODO: Show error message to user
} finally {
setIsSaving(false);
}
};
return (
<div className="flex flex-col h-full bg-carnet-bg">
{/* Title Bar */}
<div className="p-4 border-b border-carnet-border">
<input
type="text"
value={title}
onChange={handleTitleChange}
placeholder="Titre"
className="w-full text-xl font-semibold text-carnet-text-primary placeholder-carnet-text-muted focus:outline-none bg-transparent"
/>
</div>
{/* Toolbar */}
<div className="px-4 py-2 border-b border-carnet-border">
<div className="flex space-x-1">
<button className="p-1.5 rounded hover:bg-carnet-hover">
<List className="h-4 w-4 text-carnet-text-muted" />
</button>
<button className="p-1.5 rounded hover:bg-carnet-hover">
<Link className="h-4 w-4 text-carnet-text-muted" />
</button>
<button className="p-1.5 rounded hover:bg-carnet-hover">
<Image className="h-4 w-4 text-carnet-text-muted" />
</button>
<button
className={`p-1.5 rounded hover:bg-carnet-hover ${isSaving ? 'opacity-50 cursor-not-allowed' : ''}`}
onClick={handleSave}
disabled={isSaving}
>
<FileText className="h-4 w-4 text-carnet-text-muted" />
</button>
</div>
</div>
{/* Editor Area */}
<div className="flex-1 p-4">
<textarea
value={content}
onChange={handleContentChange}
placeholder="Ecrire..."
className="w-full h-full resize-none focus:outline-none bg-transparent text-carnet-text-primary placeholder-carnet-text-muted"
/>
</div>
</div>
);
};