264 lines
17 KiB
TypeScript
264 lines
17 KiB
TypeScript
'use client';
|
||
|
||
import React from 'react';
|
||
import Link from 'next/link';
|
||
import Image from 'next/image';
|
||
import { useReveal } from '@/hooks/useReveal';
|
||
import GSAPAnimator from '@/components/GSAPAnimator';
|
||
import ScrollStack, { ScrollStackItem } from '@/components/ScrollStack';
|
||
|
||
function Reveal({ children, delay = 0 }: { children: React.ReactNode; delay?: number }) {
|
||
const { ref, visible } = useReveal();
|
||
return (
|
||
<div ref={ref} style={{
|
||
opacity: visible ? 1 : 0,
|
||
transform: visible ? 'translateY(0)' : 'translateY(48px)',
|
||
transition: `opacity 0.9s cubic-bezier(0.22,1,0.36,1) ${delay}s, transform 0.9s cubic-bezier(0.22,1,0.36,1) ${delay}s`,
|
||
}}>{children}</div>
|
||
);
|
||
}
|
||
|
||
const VALUES = [
|
||
{ n: '01', title: 'Intelligence first', desc: 'Every product decision starts with data, not instinct.' },
|
||
{ n: '02', title: 'Merchant obsessed', desc: 'We build for the store owner who works 14-hour days.' },
|
||
{ n: '03', title: 'Radical transparency', desc: 'No black boxes. Our AI explains every recommendation.' },
|
||
{ n: '04', title: 'Build to last', desc: 'We optimise for long-term impact, not vanity metrics.' },
|
||
];
|
||
|
||
const PRODUCTS = [
|
||
{
|
||
n: '01', title: 'Behavision', subtitle: 'AI Powered Footfall Analytics', color: '#f4be28',
|
||
desc: 'AI powered footfall analytics and behavioral intelligence for physical retail. Behavision turns every camera and sensor you already have into a live map of how customers move, where they linger, and what makes them walk away, so store layout and staffing decisions are based on evidence, not guesswork.',
|
||
capabilities: [
|
||
'Real-time footfall counting, accurate to 98% across every entry point',
|
||
'Dwell-time and zone heatmaps that show exactly where attention concentrates',
|
||
'Entry-to-purchase funnel tracking that flags where shoppers drop off',
|
||
],
|
||
metric: { val: '3.2×', lbl: 'conversion uplift' },
|
||
tags: ['Footfall Tracking', 'Behavior Analysis'],
|
||
},
|
||
{
|
||
n: '02', title: 'SpendSense', subtitle: 'Customer Spending Intelligence', color: '#10B981',
|
||
desc: 'Deep, continuously updating intelligence on how your customers spend. SpendSense studies basket size, purchase frequency, and category preferences across every visit, surfacing the high-value segments and the early warning signs of churn well before a customer stops coming back.',
|
||
capabilities: [
|
||
'Automatic customer segmentation by spend, frequency, and loyalty tier',
|
||
'Predictive churn scoring that flags at-risk high-value shoppers early',
|
||
'Revenue opportunity alerts triggered by shifting basket-size trends',
|
||
],
|
||
metric: { val: '68%', lbl: 'retention improvement' },
|
||
tags: ['Spending Trends', 'Revenue Analytics', 'Customer Value'],
|
||
},
|
||
{
|
||
n: '03', title: 'Dyscount', subtitle: 'Smart Discount Engine', color: '#EF4444',
|
||
desc: 'A discount engine that treats margin as a budget, not an afterthought. Dyscount decides who gets an offer, how deep it goes, and when it fires, targeting the customers most likely to convert while capping every discount so promotions never quietly eat into profit.',
|
||
capabilities: [
|
||
'Dynamic offer targeting based on real-time purchase intent signals',
|
||
'Margin-safe discount caps enforced per product, category, or campaign',
|
||
'A/B tested offer formats that keep conversion up without overspending',
|
||
],
|
||
metric: { val: '41%', lbl: 'discount waste reduced' },
|
||
tags: ['Smart Discounts', 'Offer Automation', 'Margin Protection'],
|
||
},
|
||
{
|
||
n: '04', title: 'Identiq', subtitle: 'Consumer Loyalty Platform', color: '#f4be28',
|
||
desc: 'The consumer-facing app that closes the loop. Identiq turns daily logins, walking challenges, and quick mini-games into LYTs, Loyaly’s reward tokens, redeemable instantly at any partner store, so every idle moment on a phone becomes a reason to walk into a real one.',
|
||
capabilities: [
|
||
'Daily login and step-challenge Lyts that build a lasting habit loop',
|
||
'Game based offers like Spin Wheel, Scratch Card, and Maze Challenge',
|
||
'Instant offline redemption at any partner store, no card required',
|
||
],
|
||
metric: { val: '50K+', lbl: 'active shoppers' },
|
||
tags: ['Daily Lyts', 'Game Based Offers', 'Offline Redemption'],
|
||
},
|
||
];
|
||
|
||
export default function MeetTheCrewPage() {
|
||
return (
|
||
<main style={{ background: '#ffffff', minHeight: '100vh', overflowX: 'hidden' }}>
|
||
<GSAPAnimator />
|
||
|
||
{/* ── HERO ── */}
|
||
<section style={{
|
||
minHeight: '100vh', background: 'radial-gradient(ellipse 120% 90% at 22% 0%, #3a2b5e 0%, #251c40 38%, #1a1530 100%)',
|
||
display: 'flex', alignItems: 'center',
|
||
padding: '120px 8% 80px',
|
||
margin: '20px', borderRadius: '32px',
|
||
position: 'relative', overflow: 'hidden',
|
||
}}>
|
||
{/* Background photo */}
|
||
<Image src="/images/stock/about-team.jpg" alt="" fill priority style={{ objectFit: 'cover', opacity: 0.9 }} />
|
||
<div style={{ position: 'absolute', inset: 0, background: 'linear-gradient(180deg, rgba(26,21,48,0.1) 0%, rgba(26,21,48,0.55) 85%)' }} />
|
||
<div style={{ position: 'absolute', inset: 0, background: 'radial-gradient(ellipse 60% 65% at 50% 48%, rgba(18,14,30,0.78) 0%, rgba(18,14,30,0.35) 60%, transparent 100%)' }} />
|
||
{/* Accent blobs */}
|
||
<div style={{ position: 'absolute', top: '-12%', right: '-8%', width: 520, height: 520, borderRadius: '50%', background: 'radial-gradient(circle, rgba(244,190,40,0.22) 0%, transparent 70%)', filter: 'blur(10px)', pointerEvents: 'none' }} />
|
||
<div style={{ position: 'absolute', bottom: '-15%', left: '-10%', width: 460, height: 460, borderRadius: '50%', background: 'radial-gradient(circle, rgba(167,139,250,0.18) 0%, transparent 70%)', pointerEvents: 'none' }} />
|
||
{/* Big ghost text */}
|
||
<div style={{
|
||
position: 'absolute', top: '50%', left: '50%',
|
||
transform: 'translate(-50%,-50%)',
|
||
fontSize: 'clamp(120px, 22vw, 320px)', fontWeight: 900,
|
||
fontFamily: 'Sora, sans-serif', color: 'transparent',
|
||
WebkitTextStroke: '1px rgba(244,190,40,0.08)',
|
||
letterSpacing: '-0.06em', lineHeight: 1,
|
||
whiteSpace: 'nowrap', userSelect: 'none',
|
||
pointerEvents: 'none', zIndex: 0,
|
||
}}>LOYALY</div>
|
||
|
||
<div style={{ position: 'relative', zIndex: 2, width: '100%', display: 'flex', flexDirection: 'column', alignItems: 'center', textAlign: 'center' }}>
|
||
<div style={{ maxWidth: 760 }}>
|
||
<h1 data-gsap="heading" style={{
|
||
fontSize: 'clamp(52px, 9vw, 140px)', fontWeight: 800,
|
||
letterSpacing: '-0.06em', lineHeight: 0.88,
|
||
color: '#ffffff', margin: '0 0 36px', fontFamily: 'Sora, sans-serif',
|
||
}}>
|
||
Meet the<br />
|
||
<span style={{ color: '#f4be28' }}>Agents.</span>
|
||
</h1>
|
||
<p data-gsap="text" style={{ fontSize: 'clamp(16px, 1.5vw, 20px)', lineHeight: 1.75, color: 'rgba(255,255,255,0.55)', fontFamily: 'Sora, sans-serif', maxWidth: 560, margin: '0 auto' }}>
|
||
The builders, thinkers, and retail obsessives behind Loyaly, working every day to make offline shopping as smart as online.
|
||
</p>
|
||
</div>
|
||
</div>
|
||
</section>
|
||
|
||
{/* ── VALUES ── */}
|
||
<section style={{ padding: '140px 8%', background: '#fff', margin: '0 20px 20px', borderRadius: 24 }}>
|
||
<Reveal>
|
||
<div style={{ fontSize: 11, fontWeight: 700, letterSpacing: '0.2em', textTransform: 'uppercase', color: '#f4be28', fontFamily: 'Sora, sans-serif', marginBottom: 20 }}>How We Work</div>
|
||
<h2 style={{ fontSize: 'clamp(36px, 5vw, 72px)', fontWeight: 800, letterSpacing: '-0.04em', lineHeight: 0.95, color: '#0a0a0f', margin: '0 0 80px', fontFamily: 'Sora, sans-serif' }}>
|
||
What we believe.
|
||
</h2>
|
||
</Reveal>
|
||
<div style={{ display: 'flex', flexDirection: 'column' }}>
|
||
{VALUES.map((v, i) => (
|
||
<Reveal key={i} delay={i * 0.08}>
|
||
<div className="mtc-value-row" style={{
|
||
display: 'grid', gridTemplateColumns: '80px 1fr 1fr',
|
||
gap: '4vw', alignItems: 'center',
|
||
padding: '40px 0', borderBottom: '1px solid rgba(0,0,0,0.07)',
|
||
}}>
|
||
<span style={{ fontSize: 13, fontWeight: 700, color: '#f4be28', fontFamily: 'Sora, sans-serif', letterSpacing: '0.06em' }}>{v.n}</span>
|
||
<h3 style={{ fontSize: 'clamp(20px, 2.5vw, 36px)', fontWeight: 800, color: '#0a0a0f', fontFamily: 'Sora, sans-serif', margin: 0, letterSpacing: '-0.03em' }}>{v.title}</h3>
|
||
<p style={{ fontSize: 16, color: 'rgba(0,0,0,0.45)', fontFamily: 'Sora, sans-serif', margin: 0, lineHeight: 1.65 }}>{v.desc}</p>
|
||
</div>
|
||
</Reveal>
|
||
))}
|
||
</div>
|
||
</section>
|
||
|
||
{/* ── OUR PRODUCTS ── */}
|
||
<section style={{ padding: '140px 8%', background: '#07070d', margin: '0 20px 20px', borderRadius: 24, overflow: 'hidden', position: 'relative' }}>
|
||
<div style={{ position: 'absolute', inset: 0, backgroundImage: 'linear-gradient(rgba(244,190,40,0.025) 1px,transparent 1px),linear-gradient(90deg,rgba(244,190,40,0.025) 1px,transparent 1px)', backgroundSize: '64px 64px', pointerEvents: 'none' }} />
|
||
<Reveal>
|
||
<div style={{ fontSize: 11, fontWeight: 700, letterSpacing: '0.2em', textTransform: 'uppercase', color: '#f4be28', fontFamily: 'Sora, sans-serif', marginBottom: 20, position: 'relative' }}>Meet the Agents</div>
|
||
<h2 style={{ fontSize: 'clamp(36px, 5vw, 72px)', fontWeight: 800, letterSpacing: '-0.04em', lineHeight: 0.95, color: '#fff', margin: '0 0 20px', fontFamily: 'Sora, sans-serif', position: 'relative', maxWidth: 700 }}>
|
||
Four agents.<br />One AI.
|
||
</h2>
|
||
<p style={{ fontSize: 16, color: 'rgba(255,255,255,0.45)', fontFamily: 'Sora, sans-serif', maxWidth: 460, lineHeight: 1.7, marginBottom: 80, position: 'relative' }}>
|
||
Behavision, SpendSense, Dyscount, and Identiq, each solves a distinct part of the retail journey, and together they form one connected platform, from footfall to spend to loyalty.
|
||
</p>
|
||
</Reveal>
|
||
|
||
<div style={{ position: 'relative' }}>
|
||
<ScrollStack useWindowScroll itemDistance={160} itemScale={0.035} itemStackDistance={40} baseScale={0.86} hideBehind>
|
||
{PRODUCTS.map((p, i) => (
|
||
<ScrollStackItem key={i}>
|
||
<div style={{
|
||
position: 'relative', overflow: 'hidden',
|
||
background: `radial-gradient(130% 80% at 100% 0%, ${p.color}22 0%, transparent 46%), linear-gradient(155deg, #16161f 0%, #0a0a10 100%)`,
|
||
border: `1px solid ${p.color}4d`,
|
||
boxShadow: `inset 0 1px 0 rgba(255,255,255,0.06)`,
|
||
borderRadius: 28, padding: 'clamp(36px, 4vw, 64px)',
|
||
minHeight: 'clamp(380px, 48vh, 500px)', height: '100%', boxSizing: 'border-box',
|
||
}}>
|
||
{/* Accent glow blob */}
|
||
<div aria-hidden style={{ position: 'absolute', top: '-22%', right: '-8%', width: 360, height: 360, borderRadius: '50%', background: `radial-gradient(circle, ${p.color}26 0%, transparent 70%)`, pointerEvents: 'none' }} />
|
||
|
||
<div className="mtc-product-grid" style={{ position: 'relative', display: 'grid', gridTemplateColumns: '1.3fr 1fr', gap: 'clamp(32px, 4.5vw, 68px)', alignItems: 'center', height: '100%' }}>
|
||
|
||
{/* Left — identity + description */}
|
||
<div>
|
||
<div style={{ display: 'flex', alignItems: 'center', gap: 14, marginBottom: 24 }}>
|
||
<span style={{ fontSize: 15, fontWeight: 800, color: p.color, fontFamily: 'Sora, sans-serif', letterSpacing: '0.05em' }}>{p.n}</span>
|
||
<span style={{ fontSize: '0.74rem', fontWeight: 700, letterSpacing: '0.12em', textTransform: 'uppercase', color: p.color, fontFamily: 'Sora, sans-serif' }}>{p.subtitle}</span>
|
||
</div>
|
||
<h3 style={{ fontSize: 'clamp(2.1rem, 3.4vw, 3.4rem)', fontWeight: 800, letterSpacing: '-0.035em', color: '#fff', margin: '0 0 20px', fontFamily: 'Sora, sans-serif', lineHeight: 1 }}>{p.title}</h3>
|
||
<p style={{ fontSize: 'clamp(15px, 1.1vw, 17px)', lineHeight: 1.8, color: 'rgba(255,255,255,0.55)', fontFamily: 'Sora, sans-serif', margin: '0 0 30px', maxWidth: 520 }}>{p.desc}</p>
|
||
<div style={{ display: 'flex', flexWrap: 'wrap', gap: 10 }}>
|
||
{p.tags.map((tag) => (
|
||
<span key={tag} style={{
|
||
padding: '8px 16px', borderRadius: 100, fontSize: '0.76rem', fontWeight: 700,
|
||
color: '#fff', background: `${p.color}1a`,
|
||
border: `1px solid ${p.color}3d`, fontFamily: 'Sora, sans-serif',
|
||
}}>{tag}</span>
|
||
))}
|
||
</div>
|
||
</div>
|
||
|
||
{/* Right — metric hero + capabilities */}
|
||
<div>
|
||
<div style={{
|
||
padding: 'clamp(24px, 2.6vw, 34px)', borderRadius: 22, marginBottom: 24,
|
||
background: `linear-gradient(150deg, ${p.color}2b 0%, ${p.color}0d 100%)`,
|
||
border: `1px solid ${p.color}55`,
|
||
boxShadow: `0 22px 54px -26px ${p.color}66, inset 0 1px 0 rgba(255,255,255,0.08)`,
|
||
}}>
|
||
<div style={{ fontSize: 'clamp(2.4rem, 3.4vw, 3.4rem)', fontWeight: 900, color: p.color, fontFamily: 'Sora, sans-serif', letterSpacing: '-0.04em', lineHeight: 1, textShadow: `0 0 30px ${p.color}55` }}>{p.metric.val}</div>
|
||
<div style={{ fontSize: 12, fontWeight: 700, color: 'rgba(255,255,255,0.5)', fontFamily: 'Sora, sans-serif', marginTop: 10, textTransform: 'uppercase', letterSpacing: '0.08em' }}>{p.metric.lbl}</div>
|
||
</div>
|
||
|
||
<div style={{ display: 'flex', flexDirection: 'column', gap: 16 }}>
|
||
{p.capabilities.map((cap) => (
|
||
<div key={cap} style={{ display: 'flex', alignItems: 'flex-start', gap: 12 }}>
|
||
<span style={{
|
||
width: 22, height: 22, borderRadius: '50%', flexShrink: 0, marginTop: 1,
|
||
display: 'flex', alignItems: 'center', justifyContent: 'center',
|
||
background: `${p.color}22`, border: `1px solid ${p.color}66`,
|
||
boxShadow: `0 0 14px -2px ${p.color}77`,
|
||
}}>
|
||
<svg width="11" height="11" viewBox="0 0 24 24" fill="none" stroke={p.color} strokeWidth="3.2" strokeLinecap="round" strokeLinejoin="round"><path d="M20 6L9 17l-5-5" /></svg>
|
||
</span>
|
||
<span style={{ fontSize: 14.5, lineHeight: 1.55, color: 'rgba(255,255,255,0.72)', fontFamily: 'Sora, sans-serif' }}>{cap}</span>
|
||
</div>
|
||
))}
|
||
</div>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
</ScrollStackItem>
|
||
))}
|
||
</ScrollStack>
|
||
</div>
|
||
</section>
|
||
|
||
{/* ── CULTURE CLOSE ── */}
|
||
<section style={{
|
||
padding: '160px 8%', background: '#f4be28',
|
||
margin: '0 20px 20px', borderRadius: 24,
|
||
display: 'flex', flexDirection: 'column', alignItems: 'center', textAlign: 'center',
|
||
position: 'relative', overflow: 'hidden',
|
||
}}>
|
||
<div style={{ position: 'absolute', inset: 0, background: 'radial-gradient(ellipse at 50% 0%,rgba(255,255,255,0.2) 0%,transparent 60%)', pointerEvents: 'none' }} />
|
||
<Reveal>
|
||
<p style={{ fontSize: 'clamp(32px, 6vw, 90px)', fontWeight: 900, letterSpacing: '-0.05em', lineHeight: 0.95, color: '#111', margin: '0 0 48px', fontFamily: 'Sora, sans-serif', position: 'relative', zIndex: 2 }}>
|
||
"We're not just building a product. We're redefining retail."
|
||
</p>
|
||
<Link href="/contacts" style={{
|
||
display: 'inline-flex', alignItems: 'center', gap: 10,
|
||
padding: '18px 44px', background: '#111', color: '#f4be28',
|
||
fontSize: 16, fontWeight: 800, borderRadius: 100, textDecoration: 'none',
|
||
fontFamily: 'Sora, sans-serif', position: 'relative', zIndex: 2,
|
||
}}>Join Us →</Link>
|
||
</Reveal>
|
||
</section>
|
||
|
||
<style>{`
|
||
@media (max-width: 860px) {
|
||
.mtc-value-row { grid-template-columns: 1fr !important; gap: 10px !important; padding: 28px 0 !important; }
|
||
.mtc-product-grid { grid-template-columns: 1fr !important; }
|
||
}
|
||
`}</style>
|
||
</main>
|
||
);
|
||
}
|