diff --git a/frontend/src/App.tsx b/frontend/src/App.tsx index 7f29cc3..05f76dc 100644 --- a/frontend/src/App.tsx +++ b/frontend/src/App.tsx @@ -14,6 +14,10 @@ import WriteBlog from "./Pages/WriteBlog"; import ReadBlog from "./Pages/ReadBlog"; import MyBlogsPage from "./Pages/MyBlogsPage"; import EditBlog from "./Pages/EditBlog"; +import PostFeature from "./Pages/PostFeature"; +import ProjectPage from "./Pages/ProjectPage"; + + function App() { const [currentUser, setCurrentUser] = useState<{ _id: string } | null>(null); @@ -49,7 +53,11 @@ function App() { } /> } /> } /> + } /> + } /> + + ); } diff --git a/frontend/src/Pages/PostFeature.tsx b/frontend/src/Pages/PostFeature.tsx new file mode 100644 index 0000000..30d80f3 --- /dev/null +++ b/frontend/src/Pages/PostFeature.tsx @@ -0,0 +1,202 @@ +import React, { useState } from 'react'; +import { useNavigate } from 'react-router-dom'; +import { ArrowLeft, X, AlertCircle, Github, ExternalLink } from 'lucide-react'; +import Navbar from '../components/NavBar'; +import Footer from '../components/Footer'; + +const PostFeature = () => { + const navigate = useNavigate(); + const [title, setTitle] = useState(''); + const [description, setDescription] = useState(''); + const [githubLink, setGithubLink] = useState(''); + const [liveLink, setLiveLink] = useState(''); + const [tags, setTags] = useState([]); + const [currentTag, setCurrentTag] = useState(''); + const [error, setError] = useState(''); + const [isSubmitting, setIsSubmitting] = useState(false); + + const handleTagKeyDown = (e: React.KeyboardEvent) => { + if (e.key === 'Enter') { + e.preventDefault(); + if (currentTag.trim() && tags.length < 6 && !tags.includes(currentTag.trim())) { + setTags([...tags, currentTag.trim()]); + setCurrentTag(''); + } + } else if (e.key === 'Backspace' && !currentTag && tags.length > 0) { + setTags(tags.slice(0, -1)); + } + }; + + const removeTag = (tagToRemove: string) => { + setTags(tags.filter(tag => tag !== tagToRemove)); + }; + + const handleSubmit = async (e: React.FormEvent) => { + e.preventDefault(); + setError(''); + + if (!title || !description || !githubLink) { + setError('Please fill in all required fields (Title, Description, Github Link)'); + return; + } + + setIsSubmitting(true); + + try { + const response = await fetch('/api/project/post', { + method: 'POST', + headers: { + 'Content-Type': 'application/json', + }, + body: JSON.stringify({ + title, + description, + tags, + githubLink, + liveLink, + }), + }); + + if (!response.ok) { + const data = await response.json(); + throw new Error(data.message || 'Failed to post project'); + } + + navigate('/'); // Navigate to home or projects page + } catch (err: any) { + setError(err.message || 'Something went wrong'); + } finally { + setIsSubmitting(false); + } + }; + + return ( +
+ + +
+
+ {/* Header */} +
+ +
+ +
+ {error && ( +
+ + ERROR: {error} +
+ )} + +
+ {/* Title Input */} +
+ + setTitle(e.target.value)} + placeholder="MY_AWESOME_PROJECT" + className="w-full bg-transparent border-b border-[#30363d] text-white text-4xl md:text-6xl font-extrabold pb-4 focus:outline-none focus:border-[#00ffff] transition-colors placeholder:text-[#30363d]" + /> +
+ + {/* Description Input */} +
+ +