Compare commits
4 Commits
21ac410780
...
0c656d21a2
| Author | SHA1 | Date |
|---|---|---|
|
|
0c656d21a2 | |
|
|
4f59f775ae | |
|
|
7f37a5667b | |
|
|
d688c5890a |
|
|
@ -0,0 +1,78 @@
|
||||||
|
import { useState, useEffect, ReactNode } from 'react';
|
||||||
|
|
||||||
|
export default function GlowEffect({ children }: { children: ReactNode }) {
|
||||||
|
const [isPropertyRegistered, setIsPropertyRegistered] = useState(false);
|
||||||
|
|
||||||
|
// Register CSS property in component body (before render)
|
||||||
|
if (typeof window !== 'undefined' && 'CSS' in window && 'registerProperty' in CSS) {
|
||||||
|
try {
|
||||||
|
CSS.registerProperty({
|
||||||
|
name: '--form-angle',
|
||||||
|
syntax: '<angle>',
|
||||||
|
initialValue: '0deg',
|
||||||
|
inherits: false,
|
||||||
|
});
|
||||||
|
} catch (e) {
|
||||||
|
// Property may already be registered
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
// Trigger second render to add style tag
|
||||||
|
setIsPropertyRegistered(true);
|
||||||
|
}, []);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
{isPropertyRegistered && (
|
||||||
|
<style>{`
|
||||||
|
@keyframes form-glow-rotate {
|
||||||
|
to {
|
||||||
|
--form-angle: 360deg;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.email-form-wrapper {
|
||||||
|
background: linear-gradient(#0a0612, #0a0612) padding-box,
|
||||||
|
conic-gradient(from var(--form-angle, 0deg),
|
||||||
|
rgba(99, 102, 241, 0.5),
|
||||||
|
rgba(139, 92, 246, 1),
|
||||||
|
rgba(99, 102, 241, 0.5),
|
||||||
|
rgba(236, 72, 153, 0.8),
|
||||||
|
rgba(99, 102, 241, 0.5),
|
||||||
|
rgba(34, 211, 238, 1),
|
||||||
|
rgba(99, 102, 241, 0.5)
|
||||||
|
) border-box;
|
||||||
|
animation: form-glow-rotate 12s linear infinite;
|
||||||
|
}
|
||||||
|
|
||||||
|
.email-form-wrapper::before {
|
||||||
|
content: '';
|
||||||
|
position: absolute;
|
||||||
|
inset: -3px;
|
||||||
|
border-radius: 15px;
|
||||||
|
background: conic-gradient(from var(--form-angle, 0deg),
|
||||||
|
rgba(99, 102, 241, 0.2),
|
||||||
|
rgba(139, 92, 246, 0.7),
|
||||||
|
rgba(99, 102, 241, 0.2),
|
||||||
|
rgba(236, 72, 153, 0.5),
|
||||||
|
rgba(99, 102, 241, 0.2),
|
||||||
|
rgba(34, 211, 238, 0.7),
|
||||||
|
rgba(99, 102, 241, 0.2)
|
||||||
|
);
|
||||||
|
filter: blur(18px);
|
||||||
|
opacity: 0.75;
|
||||||
|
z-index: -1;
|
||||||
|
animation: form-glow-rotate 12s linear infinite;
|
||||||
|
}
|
||||||
|
`}</style>
|
||||||
|
)}
|
||||||
|
|
||||||
|
<div className="flex items-center justify-center p-4">
|
||||||
|
<div className="email-form-wrapper relative isolate max-w-lg w-full mx-auto p-[2px] rounded-xl">
|
||||||
|
{children}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
'use client';
|
'use client';
|
||||||
|
|
||||||
import { useState } from 'react';
|
import { useState } from 'react';
|
||||||
import { AnimatedGradientBorder } from './components/AnimatedGradientBorder';
|
import { AnimatedGradientBorder } from './_components/AnimatedGradientBorder';
|
||||||
import {
|
import {
|
||||||
Zap,
|
Zap,
|
||||||
Globe,
|
Globe,
|
||||||
|
|
@ -35,6 +35,7 @@ import {
|
||||||
Award,
|
Award,
|
||||||
ArrowRight,
|
ArrowRight,
|
||||||
} from 'lucide-react';
|
} from 'lucide-react';
|
||||||
|
import GlowEffect from './_components/GlowEffect';
|
||||||
|
|
||||||
// ============================================================================
|
// ============================================================================
|
||||||
// STYLES (CSS-in-JS for custom styles not available in Tailwind)
|
// STYLES (CSS-in-JS for custom styles not available in Tailwind)
|
||||||
|
|
@ -49,7 +50,7 @@ const customStyles = `
|
||||||
-webkit-background-clip: text;
|
-webkit-background-clip: text;
|
||||||
-webkit-text-fill-color: transparent;
|
-webkit-text-fill-color: transparent;
|
||||||
background-clip: text;
|
background-clip: text;
|
||||||
animation: gradient-shift 4s ease-in-out infinite;
|
animation: gradient-shift 6s ease-in-out infinite;
|
||||||
}
|
}
|
||||||
|
|
||||||
@keyframes gradient-shift {
|
@keyframes gradient-shift {
|
||||||
|
|
@ -188,8 +189,12 @@ function HeroSection() {
|
||||||
</p>
|
</p>
|
||||||
|
|
||||||
{/* Email Form */}
|
{/* Email Form */}
|
||||||
<div className="email-form-wrapper mb-4">
|
<GlowEffect>
|
||||||
<form onSubmit={handleSubmit} className="flex flex-col sm:flex-row gap-2 bg-[rgba(10,6,18,0.95)] rounded-[10px] p-1.5 sm:p-1.5 sm:pl-3">
|
<form
|
||||||
|
onSubmit={handleSubmit}
|
||||||
|
className="flex flex-col sm:flex-row gap-2 rounded-[10px] p-1.5 sm:pl-3"
|
||||||
|
style={{ background: 'rgba(10, 6, 18, 0.95)' }}
|
||||||
|
>
|
||||||
<input
|
<input
|
||||||
type="email"
|
type="email"
|
||||||
value={email}
|
value={email}
|
||||||
|
|
@ -199,15 +204,17 @@ function HeroSection() {
|
||||||
/>
|
/>
|
||||||
<button
|
<button
|
||||||
type="submit"
|
type="submit"
|
||||||
className="px-6 py-3 bg-gradient-to-br from-indigo-500 to-purple-500 hover:from-indigo-600 hover:to-purple-600 border-none rounded-md text-white font-semibold cursor-pointer transition-all whitespace-nowrap"
|
className="px-6 py-3 bg-gradient-to-br from-indigo-500 to-purple-500 hover:from-indigo-600 hover:to-purple-600 rounded-md text-white font-semibold cursor-pointer transition-all whitespace-nowrap"
|
||||||
>
|
>
|
||||||
Get Early Access
|
Get Early Access
|
||||||
</button>
|
</button>
|
||||||
</form>
|
</form>
|
||||||
</div>
|
</GlowEffect>
|
||||||
|
|
||||||
<p className="text-sm text-gray-500 mb-10">Free early access. No credit card required.</p>
|
<p className="text-sm text-gray-500 mb-10">Free early access. No credit card required.</p>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
{/* Badges */}
|
{/* Badges */}
|
||||||
<div className="flex flex-nowrap gap-5 justify-center">
|
<div className="flex flex-nowrap gap-5 justify-center">
|
||||||
{badges.map((badge, i) => (
|
{badges.map((badge, i) => (
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue