@indirecttek/essentials-engine 1.1.3 → 1.1.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
|
@@ -16,7 +16,20 @@ const { config } = Astro.props;
|
|
|
16
16
|
<p class="text-center text-[color:var(--color-foreground)] opacity-80 mb-8 md:mb-12">
|
|
17
17
|
Get in touch with {config.businessName} today
|
|
18
18
|
</p>
|
|
19
|
-
|
|
19
|
+
|
|
20
|
+
<!-- Success Message (hidden by default) -->
|
|
21
|
+
<div id="contact-success" class="hidden bg-green-100 border border-green-400 text-green-700 px-4 py-3 rounded-md mb-6">
|
|
22
|
+
<p class="font-medium">Message sent successfully!</p>
|
|
23
|
+
<p class="text-sm">We'll get back to you within 24 hours.</p>
|
|
24
|
+
</div>
|
|
25
|
+
|
|
26
|
+
<!-- Error Message (hidden by default) -->
|
|
27
|
+
<div id="contact-error" class="hidden bg-red-100 border border-red-400 text-red-700 px-4 py-3 rounded-md mb-6">
|
|
28
|
+
<p class="font-medium">Something went wrong</p>
|
|
29
|
+
<p class="text-sm" id="contact-error-message">Please try again or contact us directly.</p>
|
|
30
|
+
</div>
|
|
31
|
+
|
|
32
|
+
<form id="contact-form" class="space-y-6">
|
|
20
33
|
<div class="grid grid-cols-1 md:grid-cols-2 gap-6">
|
|
21
34
|
<div>
|
|
22
35
|
<label
|
|
@@ -84,9 +97,11 @@ const { config } = Astro.props;
|
|
|
84
97
|
</div>
|
|
85
98
|
<button
|
|
86
99
|
type="submit"
|
|
87
|
-
|
|
100
|
+
id="contact-submit"
|
|
101
|
+
class="w-full bg-[color:var(--color-primary)] text-[color:var(--color-background)] py-3 md:py-4 rounded-md font-semibold text-lg hover:opacity-90 transition-opacity disabled:opacity-50 disabled:cursor-not-allowed"
|
|
88
102
|
>
|
|
89
|
-
Send Message
|
|
103
|
+
<span id="submit-text">Send Message</span>
|
|
104
|
+
<span id="submit-loading" class="hidden">Sending...</span>
|
|
90
105
|
</button>
|
|
91
106
|
</form>
|
|
92
107
|
<div class="mt-12 text-center space-y-2 text-[color:var(--color-foreground)] opacity-80">
|
|
@@ -104,3 +119,70 @@ const { config } = Astro.props;
|
|
|
104
119
|
</div>
|
|
105
120
|
</div>
|
|
106
121
|
</section>
|
|
122
|
+
|
|
123
|
+
<script>
|
|
124
|
+
const form = document.getElementById('contact-form') as HTMLFormElement;
|
|
125
|
+
const submitBtn = document.getElementById('contact-submit') as HTMLButtonElement;
|
|
126
|
+
const submitText = document.getElementById('submit-text') as HTMLSpanElement;
|
|
127
|
+
const submitLoading = document.getElementById('submit-loading') as HTMLSpanElement;
|
|
128
|
+
const successMsg = document.getElementById('contact-success') as HTMLDivElement;
|
|
129
|
+
const errorMsg = document.getElementById('contact-error') as HTMLDivElement;
|
|
130
|
+
const errorText = document.getElementById('contact-error-message') as HTMLParagraphElement;
|
|
131
|
+
|
|
132
|
+
form?.addEventListener('submit', async (e) => {
|
|
133
|
+
e.preventDefault();
|
|
134
|
+
|
|
135
|
+
// Hide any previous messages
|
|
136
|
+
successMsg.classList.add('hidden');
|
|
137
|
+
errorMsg.classList.add('hidden');
|
|
138
|
+
|
|
139
|
+
// Show loading state
|
|
140
|
+
submitBtn.disabled = true;
|
|
141
|
+
submitText.classList.add('hidden');
|
|
142
|
+
submitLoading.classList.remove('hidden');
|
|
143
|
+
|
|
144
|
+
const formData = new FormData(form);
|
|
145
|
+
const data = {
|
|
146
|
+
name: formData.get('name'),
|
|
147
|
+
email: formData.get('email'),
|
|
148
|
+
phone: formData.get('phone') || undefined,
|
|
149
|
+
message: formData.get('message'),
|
|
150
|
+
};
|
|
151
|
+
|
|
152
|
+
try {
|
|
153
|
+
const response = await fetch('/api/contact', {
|
|
154
|
+
method: 'POST',
|
|
155
|
+
headers: {
|
|
156
|
+
'Content-Type': 'application/json',
|
|
157
|
+
},
|
|
158
|
+
body: JSON.stringify(data),
|
|
159
|
+
});
|
|
160
|
+
|
|
161
|
+
const result = await response.json();
|
|
162
|
+
|
|
163
|
+
if (result.success) {
|
|
164
|
+
// Show success message
|
|
165
|
+
successMsg.classList.remove('hidden');
|
|
166
|
+
form.reset();
|
|
167
|
+
|
|
168
|
+
// Scroll to success message
|
|
169
|
+
successMsg.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
|
170
|
+
} else {
|
|
171
|
+
// Show error message
|
|
172
|
+
errorText.textContent = result.error || 'Please try again or contact us directly.';
|
|
173
|
+
errorMsg.classList.remove('hidden');
|
|
174
|
+
errorMsg.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
|
175
|
+
}
|
|
176
|
+
} catch (error) {
|
|
177
|
+
// Show generic error
|
|
178
|
+
errorText.textContent = 'Network error. Please check your connection and try again.';
|
|
179
|
+
errorMsg.classList.remove('hidden');
|
|
180
|
+
errorMsg.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
|
181
|
+
} finally {
|
|
182
|
+
// Reset button state
|
|
183
|
+
submitBtn.disabled = false;
|
|
184
|
+
submitText.classList.remove('hidden');
|
|
185
|
+
submitLoading.classList.add('hidden');
|
|
186
|
+
}
|
|
187
|
+
});
|
|
188
|
+
</script>
|