code dump frontend
This commit is contained in:
171
frontend/routes/contact/index.tsx
Normal file
171
frontend/routes/contact/index.tsx
Normal file
@ -0,0 +1,171 @@
|
||||
import { Handlers, PageProps } from "$fresh/server.ts";
|
||||
import { Head } from "$fresh/runtime.ts";
|
||||
|
||||
interface FormState {
|
||||
name?: string;
|
||||
email?: string;
|
||||
message?: string;
|
||||
errors?: {
|
||||
name?: string;
|
||||
email?: string;
|
||||
message?: string;
|
||||
};
|
||||
submitted?: boolean;
|
||||
}
|
||||
|
||||
export default function Contact({ data }: PageProps<FormState>) {
|
||||
return (
|
||||
<div class="max-w-md mx-auto p-6 bg-[#313244] rounded-lg shadow-md">
|
||||
<Head>
|
||||
<title>Contact Us</title>
|
||||
</Head>
|
||||
|
||||
<h1 class="text-2xl font-bold mb-6 text-center">Contact Form</h1>
|
||||
|
||||
{/* Check if form was successfully submitted */}
|
||||
{data?.submitted && (
|
||||
<div
|
||||
class="bg-[#a6e3a1] text-[#cdd6f4] px-4 py-3 rounded relative"
|
||||
role="alert"
|
||||
>
|
||||
Your message has been sent successfully!
|
||||
</div>
|
||||
)}
|
||||
|
||||
<form method="POST" class="space-y-4">
|
||||
{/* Name Input */}
|
||||
<div>
|
||||
<label
|
||||
htmlFor="name"
|
||||
class="block text-[#cdd6f4] text-sm font-bold mb-2"
|
||||
>
|
||||
Name
|
||||
</label>
|
||||
<input
|
||||
type="text"
|
||||
id="name"
|
||||
name="name"
|
||||
required
|
||||
placeholder="Your Name"
|
||||
value={data?.name || ""}
|
||||
class={`w-full px-3 py-2 border rounded-md focus:outline-none focus:ring-2 focus:ring-blue-500
|
||||
${data?.errors?.name ? "border-red-500" : "border-gray-300"}`}
|
||||
/>
|
||||
{data?.errors?.name && (
|
||||
<p class="text-red-500 text-xs italic mt-1">{data.errors.name}</p>
|
||||
)}
|
||||
</div>
|
||||
|
||||
{/* Email Input */}
|
||||
<div>
|
||||
<label
|
||||
htmlFor="email"
|
||||
class="block text-[#cdd6f4] text-sm font-bold mb-2"
|
||||
>
|
||||
Email
|
||||
</label>
|
||||
<input
|
||||
type="email"
|
||||
id="email"
|
||||
name="email"
|
||||
required
|
||||
placeholder="your@email.com"
|
||||
value={data?.email || ""}
|
||||
class={`w-full px-3 py-2 border rounded-md focus:outline-none focus:ring-2 focus:ring-blue-500
|
||||
${data?.errors?.email ? "border-red-500" : "border-gray-300"}`}
|
||||
/>
|
||||
{data?.errors?.email && (
|
||||
<p class="text-red-500 text-xs italic mt-1">{data.errors.email}</p>
|
||||
)}
|
||||
</div>
|
||||
|
||||
{/* Message Textarea */}
|
||||
<div>
|
||||
<label
|
||||
htmlFor="message"
|
||||
class="block text-[#cdd6f4] text-sm font-bold mb-2"
|
||||
>
|
||||
Message
|
||||
</label>
|
||||
<textarea
|
||||
id="message"
|
||||
name="message"
|
||||
required
|
||||
placeholder="Write your message here..."
|
||||
rows={4}
|
||||
class={`w-full px-3 py-2 border rounded-md focus:outline-none focus:ring-2 focus:ring-blue-500
|
||||
${data?.errors?.message ? "border-red-500" : "border-gray-300"}`}
|
||||
>
|
||||
{data?.message || ""}
|
||||
</textarea>
|
||||
{data?.errors?.message && (
|
||||
<p class="text-red-500 text-xs italic mt-1">
|
||||
{data.errors.message}
|
||||
</p>
|
||||
)}
|
||||
</div>
|
||||
|
||||
{/* Submit Button */}
|
||||
<div>
|
||||
<button
|
||||
type="submit"
|
||||
class="w-full bg-[#89b4fa] text-[#cdd6f4] py-2 px-4 rounded-md focus:outline-none focus:ring-2 focus:ring-blue-500"
|
||||
>
|
||||
Send Message
|
||||
</button>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
// Server-side form handling
|
||||
export const handler: Handlers = {
|
||||
GET(_, ctx) {
|
||||
return ctx.render({});
|
||||
},
|
||||
async POST(req, ctx) {
|
||||
const formData = await req.formData();
|
||||
const state: FormState = {
|
||||
name: formData.get("name")?.toString(),
|
||||
email: formData.get("email")?.toString(),
|
||||
message: formData.get("message")?.toString(),
|
||||
};
|
||||
|
||||
// Validation logic
|
||||
const errors: FormState["errors"] = {};
|
||||
|
||||
if (!state.name || state.name.trim() === "") {
|
||||
errors.name = "Name is required";
|
||||
}
|
||||
|
||||
const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
|
||||
if (!state.email) {
|
||||
errors.email = "Email is required";
|
||||
} else if (!emailRegex.test(state.email)) {
|
||||
errors.email = "Invalid email format";
|
||||
}
|
||||
|
||||
if (!state.message || state.message.trim() === "") {
|
||||
errors.message = "Message is required";
|
||||
}
|
||||
|
||||
// If there are errors, return the form with error messages
|
||||
if (Object.keys(errors).length > 0) {
|
||||
return ctx.render({
|
||||
...state,
|
||||
errors,
|
||||
});
|
||||
}
|
||||
|
||||
// TODO: Implement actual form submission logic here
|
||||
// For example, send email, save to database, etc.
|
||||
console.log("Form submitted:", state);
|
||||
|
||||
// Return successful submission
|
||||
return ctx.render({
|
||||
...state,
|
||||
submitted: true,
|
||||
});
|
||||
},
|
||||
};
|
Reference in New Issue
Block a user