Update padding in Parallax component for improved layout consistency
Some checks failed
Deploy / deploy (push) Has been cancelled

This commit is contained in:
bilalgursen
2026-07-30 03:54:31 +03:00
parent dc6d894a37
commit 2c542e7756
22 changed files with 274 additions and 133 deletions

View File

@@ -2,6 +2,7 @@ import type { Metadata } from "next";
import Link from "next/link";
import { redirect } from "next/navigation";
import { getSession } from "@/lib/session";
import { PixelCorner } from "@/components/pixel-decor";
import { GirisForm } from "./giris-form";
import { GirisBaslik } from "./giris-baslik";
@@ -27,24 +28,35 @@ export default async function GirisPage({
return (
<div className="flex min-h-screen flex-col bg-slate-50 text-slate-900">
<main className="mx-auto flex w-full max-w-md flex-1 flex-col items-stretch justify-center px-4 py-16">
<div className="rounded-2xl border border-slate-200 bg-white p-8 shadow-sm">
<GirisBaslik funnel={funnel} />
<p className="mt-2 text-sm text-slate-600">
{funnel ? (
<>
Seçimlerin hazır giriş yap,{" "}
<span className="font-semibold">5 deneme kredinle</span> listen
hemen üretilsin.
</>
) : (
<>
Kayıt olduğunda{" "}
<span className="font-semibold">5 deneme kredisi</span> hesabına
tanımlanır AI danışmana ücretsiz soru sorabilirsin.
</>
)}
</p>
<GirisForm callbackURL={callbackURL} />
<div className="relative">
<div className="relative rounded-2xl border border-slate-200 bg-white p-8 shadow-sm">
<GirisBaslik funnel={funnel} />
<p className="mt-2 text-sm text-slate-600">
{funnel ? (
<>
Seçimlerin hazır giriş yap,{" "}
<span className="font-semibold">5 deneme kredinle</span> listen
hemen üretilsin.
</>
) : (
<>
Kayıt olduğunda{" "}
<span className="font-semibold">5 deneme kredisi</span>{" "}
hesabına tanımlanır AI danışmana ücretsiz soru sorabilirsin.
</>
)}
</p>
<GirisForm callbackURL={callbackURL} />
</div>
<div
aria-hidden
className="pointer-events-none absolute inset-0 z-10 text-primary"
>
<PixelCorner className="absolute -right-4 -top-4 size-9 [&_rect]:[fill-opacity:0.65]" />
<PixelCorner className="absolute -bottom-4 -right-4 size-9 rotate-90 [&_rect]:[fill-opacity:0.65]" />
<PixelCorner className="absolute -bottom-4 -left-4 size-9 rotate-180 [&_rect]:[fill-opacity:0.65]" />
<PixelCorner className="absolute -left-4 -top-4 size-9 -rotate-90 [&_rect]:[fill-opacity:0.65]" />
</div>
</div>
<p className="mt-6 text-center text-xs leading-relaxed text-slate-500">
Giriş yaparak verilerinin tercih önerileri üretmek amacıyla{" "}

View File

@@ -1,7 +1,6 @@
import type { Metadata } from "next";
import Link from "next/link";
import { Parallax } from "@/components/parallax";
import { ScrollFlow } from "@/components/scroll-flow";
export const metadata: Metadata = {
title: "Gizlilik ve KVKK — KolayTercih",
@@ -10,8 +9,7 @@ export const metadata: Metadata = {
// NOT: MVP taslağıdır; yayına almadan önce hukuki gözden geçirme gerekir.
export default function GizlilikPage() {
return (
<ScrollFlow>
<main className="mx-auto w-full max-w-2xl px-4 py-16">
<main className="mx-auto w-full max-w-2xl px-4 py-16">
<Parallax fromStart strength={10}>
<h1 className="font-heading text-3xl font-bold">
Gizlilik ve Kişisel Verilerin Korunması
@@ -73,7 +71,6 @@ export default function GizlilikPage() {
</p>
</section>
</Parallax>
</main>
</ScrollFlow>
</main>
);
}

View File

@@ -1,7 +1,6 @@
import type { Metadata } from "next";
import { Mail } from "lucide-react";
import { Parallax } from "@/components/parallax";
import { ScrollFlow } from "@/components/scroll-flow";
export const metadata: Metadata = {
title: "İletişim — KolayTercih",
@@ -9,8 +8,7 @@ export const metadata: Metadata = {
export default function IletisimPage() {
return (
<ScrollFlow>
<main className="mx-auto w-full max-w-2xl px-4 py-16">
<main className="mx-auto w-full max-w-2xl px-4 py-16">
<Parallax fromStart strength={10}>
<h1 className="font-heading text-3xl font-bold">İletişim</h1>
</Parallax>
@@ -30,7 +28,6 @@ export default function IletisimPage() {
hesap adresini eklersen daha hızlı yardımcı olabiliriz. Kart bilgini
asla e-postayla paylaşma.
</p>
</main>
</ScrollFlow>
</main>
);
}

View File

@@ -1,7 +1,6 @@
import type { Metadata } from "next";
import Link from "next/link";
import { Parallax } from "@/components/parallax";
import { ScrollFlow } from "@/components/scroll-flow";
export const metadata: Metadata = {
title: "Kullanım ve Satış Koşulları — KolayTercih",
@@ -10,8 +9,7 @@ export const metadata: Metadata = {
// NOT: MVP taslağıdır; yayına almadan önce hukuki gözden geçirme gerekir.
export default function KosullarPage() {
return (
<ScrollFlow>
<main className="mx-auto w-full max-w-2xl px-4 py-16">
<main className="mx-auto w-full max-w-2xl px-4 py-16">
<Parallax fromStart strength={10}>
<h1 className="font-heading text-3xl font-bold">
Kullanım ve Satış Koşulları
@@ -80,7 +78,6 @@ export default function KosullarPage() {
</p>
</section>
</Parallax>
</main>
</ScrollFlow>
</main>
);
}

View File

@@ -7,6 +7,9 @@ import { ListeCekmecesi } from "@/components/manuel-liste/liste-cekmecesi";
import { HeaderGate } from "@/components/header-gate";
import { ProgressiveBlur } from "@/components/ui/skiper-ui/skiper41";
import { DevPanel } from "@/components/dev/dev-panel";
import { ScrollFlow } from "@/components/scroll-flow";
import { PagePixelLayer } from "@/components/page-pixel-layer";
import { ConsoleAsr } from "@/components/console-asr";
import "./globals.css";
const calSans = Cal_Sans({
@@ -54,6 +57,8 @@ export default function RootLayout({
className={`${calSans.variable} ${clarityCity.variable} ${geistMono.variable} ${bricolage.variable} h-full antialiased`}
>
<body className="min-h-full flex flex-col bg-slate-50">
<ConsoleAsr />
<PagePixelLayer />
{/* Site geneli progressive blur — üst ve alt */}
<div className="pointer-events-none fixed inset-x-0 top-0 z-40 h-28">
<ProgressiveBlur
@@ -74,7 +79,9 @@ export default function RootLayout({
<HeaderGate>
<SiteHeader />
</HeaderGate>
{children}
<ScrollFlow className="flex min-h-0 flex-1 flex-col">
{children}
</ScrollFlow>
{/* Manuel 24'lük liste çekmecesi + "+" uçuş katmanı (navbar'dan açılır) */}
<ListeCekmecesi />
<Toaster position="top-center" />

View File

@@ -24,6 +24,7 @@ import type { RaporParams } from "@/lib/rapor-havuzu";
import { Button } from "@/components/ui/button";
import { Badge } from "@/components/ui/badge";
import { RaporListesi } from "@/components/rapor-listesi";
import { ViewportPortal } from "@/components/viewport-portal";
import { raporMaskele, ACIK_SATIR } from "@/lib/rapor-maske";
import { SohbetClient } from "./sohbet-client";
import { RevizyonKutusu } from "./revizyon-kutusu";
@@ -322,13 +323,15 @@ export default async function ListemPage({
{/* Mobilde sohbet sağ rayla birlikte en alta düşer; yüzen kısayol
kullanıcıyı 24 satırı kaydırmadan danışmana ulaştırır. */}
<a
href="#sohbet"
className="fixed bottom-5 right-4 z-40 inline-flex h-11 items-center gap-2 rounded-full bg-primary px-4 text-sm font-semibold text-white shadow-lg transition-transform duration-200 active:scale-[0.97] lg:hidden print:hidden"
>
<MessageCircleQuestion className="size-4" aria-hidden />
Danışmana sor
</a>
<ViewportPortal>
<a
href="#sohbet"
className="fixed bottom-5 right-4 z-40 inline-flex h-11 items-center gap-2 rounded-full bg-primary px-4 text-sm font-semibold text-white shadow-lg transition-transform duration-200 active:scale-[0.97] lg:hidden print:hidden"
>
<MessageCircleQuestion className="size-4" aria-hidden />
Danışmana sor
</a>
</ViewportPortal>
</main>
);
}

View File

@@ -11,9 +11,9 @@ import {
} from "lucide-react";
import Image from "next/image";
import Link from "next/link";
import { HeroFocusButton } from "@/components/hero-focus-button";
import { HeroForm } from "@/components/hero-form";
import { Parallax } from "@/components/parallax";
import { ScrollFlow } from "@/components/scroll-flow";
import { Reveal } from "@/components/landing/reveal";
import { TurkeyPixelMap } from "@/components/turkey-pixel-map";
import {
@@ -24,7 +24,6 @@ import {
} from "@/components/pixel-decor";
import { URUNLER } from "@/lib/credits";
import { Badge } from "@/components/ui/badge";
import { Button } from "@/components/ui/button";
import {
Accordion,
AccordionContent,
@@ -166,8 +165,10 @@ function ComparisonCell({ value }: { value: boolean | string }) {
export default function Home() {
return (
<div className="bg-slate-50 text-slate-900">
<ScrollFlow className="flex min-h-screen flex-col">
<div
id="top"
className="flex min-h-screen flex-col bg-slate-50 text-slate-900"
>
<main className="flex-1">
{/* Hero */}
<section className="relative isolate overflow-hidden">
@@ -193,7 +194,7 @@ export default function Home() {
<Parallax
fromStart
strength={14}
className="mx-auto flex min-h-[calc(100svh-5.5rem)] max-w-6xl flex-col items-center justify-center px-4 pb-44 pt-4 text-center"
className="mx-auto flex min-h-[calc(100svh-5.5rem)] max-w-6xl flex-col items-center justify-center px-4 py-4 text-center sm:pb-44 sm:pt-4"
>
<Badge
variant="secondary"
@@ -201,7 +202,7 @@ export default function Home() {
>
2026 YKS tercih dönemi ık
</Badge>
<h1 className="max-w-3xl font-heading text-4xl font-bold tracking-[0.015em] sm:text-6xl">
<h1 className="max-w-3xl font-heading text-7xl font-bold tracking-[0.015em] sm:text-6xl">
Dört yıllık geleceğini <br className="hidden sm:block" />
<span className="font-bricolage italic tracking-tighter font-bold text-primary">
48 saatlik panikle
@@ -481,7 +482,7 @@ export default function Home() {
value={faq.question}
className="last:border-b-0"
>
<AccordionTrigger className="cursor-pointer text-left font-heading text-base font-semibold">
<AccordionTrigger className="cursor-pointer text-left font-sans text-base font-semibold">
{faq.question}
</AccordionTrigger>
<AccordionContent className="text-base leading-relaxed text-slate-600">
@@ -522,13 +523,7 @@ export default function Home() {
Sıralamanı gir, yapay zekâ danışmanın veriyle konuşsun.
Tercih dönemi bitmeden yerini al.
</p>
<Button
asChild
size="lg"
className="mt-8 h-12 cursor-pointer bg-orange-500 px-8 text-white transition-colors duration-200 hover:bg-orange-600"
>
<a href="#hero-form">Ücretsiz dene</a>
</Button>
<HeroFocusButton />
</div>
</div>
</Reveal>
@@ -571,7 +566,6 @@ export default function Home() {
</nav>
</div>
</footer>
</ScrollFlow>
</div>
);
}

View File

@@ -14,7 +14,6 @@ import { URUNLER, DENEME_KREDISI } from "@/lib/credits";
import { Button } from "@/components/ui/button";
import { Badge } from "@/components/ui/badge";
import { Parallax } from "@/components/parallax";
import { ScrollFlow } from "@/components/scroll-flow";
import { SatinAlForm } from "./satin-al-form";
export const metadata: Metadata = {
@@ -53,8 +52,7 @@ export default async function PaketPage({
const odemeHatasi = hata === "token" || hata === "siparis";
return (
<div className="bg-slate-50 text-slate-900">
<ScrollFlow className="flex min-h-screen flex-col">
<div className="flex min-h-screen flex-col bg-slate-50 text-slate-900">
<main className="mx-auto w-full max-w-3xl flex-1 px-4 py-16">
{odemeHatasi ? (
<div
@@ -189,7 +187,6 @@ export default async function PaketPage({
.
</p>
</main>
</ScrollFlow>
</div>
);
}

View File

@@ -8,6 +8,7 @@ import { animate } from "motion";
import { AnimatePresence, motion, useReducedMotion } from "motion/react";
import { toast } from "sonner";
import { Button } from "@/components/ui/button";
import { ViewportPortal } from "@/components/viewport-portal";
import type { SihirbazFacetleri } from "@/lib/db";
import {
SIHIRBAZ_STORAGE_KEY,
@@ -446,54 +447,56 @@ export function SihirbazBolumu({
</div>
{/* Sabit alt çağrı kartı — liste/panel yokken ve kart kapatılmadıysa */}
{monteEdildi && !panelde && !kartGizle && !acik ? (
<div className="pointer-events-none fixed inset-x-0 bottom-4 z-40 px-4">
<div className="pointer-events-auto mx-auto flex max-w-xl items-center gap-4 rounded-2xl border border-slate-200 bg-white p-4 shadow-xl">
<div className="flex-1">
<p className="font-heading text-sm font-bold text-slate-900">
{girisBekliyor
? "Seçimlerin kayıtlı — AI listen hazır bekliyor"
: "3 adımda 24 tercihlik listen"}
</p>
<p className="text-xs text-slate-500">
{girisBekliyor
? "Ücretsiz giriş yap, 5 deneme kredinle listen otomatik kurulsun."
: "Sıralamana uygun bölümleri seç, yapay zekâ listeni kursun."}
</p>
<ViewportPortal>
{monteEdildi && !panelde && !kartGizle && !acik ? (
<div className="pointer-events-none fixed inset-x-0 bottom-4 z-40 px-4">
<div className="pointer-events-auto mx-auto flex max-w-xl items-center gap-4 rounded-2xl border border-slate-200 bg-white p-4 shadow-xl">
<div className="flex-1">
<p className="font-heading text-sm font-bold text-slate-900">
{girisBekliyor
? "Seçimlerin kayıtlı — AI listen hazır bekliyor"
: "3 adımda 24 tercihlik listen"}
</p>
<p className="text-xs text-slate-500">
{girisBekliyor
? "Ücretsiz giriş yap, 5 deneme kredinle listen otomatik kurulsun."
: "Sıralamana uygun bölümleri seç, yapay zekâ listeni kursun."}
</p>
</div>
{girisBekliyor ? (
<Button
asChild
size="sm"
className="cursor-pointer bg-orange-500 text-white transition-colors duration-200 hover:bg-orange-600"
>
<Link href={girisUrl}>Giriş yap</Link>
</Button>
) : (
<Button
size="sm"
onClick={() => acikDegisti(true)}
className="cursor-pointer bg-orange-500 text-white transition-colors duration-200 hover:bg-orange-600"
>
Başla
</Button>
)}
<button
type="button"
aria-label="Kapat"
onClick={() => {
setKartGizle(true);
try {
sessionStorage.setItem(KAPATMA_KEY, "1");
} catch {}
}}
className="cursor-pointer rounded-full p-1 text-slate-400 transition-colors duration-200 hover:bg-slate-100 hover:text-slate-600"
>
<X className="size-4" aria-hidden />
</button>
</div>
{girisBekliyor ? (
<Button
asChild
size="sm"
className="cursor-pointer bg-orange-500 text-white transition-colors duration-200 hover:bg-orange-600"
>
<Link href={girisUrl}>Giriş yap</Link>
</Button>
) : (
<Button
size="sm"
onClick={() => acikDegisti(true)}
className="cursor-pointer bg-orange-500 text-white transition-colors duration-200 hover:bg-orange-600"
>
Başla
</Button>
)}
<button
type="button"
aria-label="Kapat"
onClick={() => {
setKartGizle(true);
try {
sessionStorage.setItem(KAPATMA_KEY, "1");
} catch {}
}}
className="cursor-pointer rounded-full p-1 text-slate-400 transition-colors duration-200 hover:bg-slate-100 hover:text-slate-600"
>
<X className="size-4" aria-hidden />
</button>
</div>
</div>
) : null}
) : null}
</ViewportPortal>
{/* Üretim başladığında modalı kaldır; yeni panelin geçişini Motion
üstlenir ve odağı panel içeriğine taşır. */}

View File

@@ -8,6 +8,7 @@ import { useEffect, useState } from "react";
import { MessageCircleMore, X } from "lucide-react";
import { AnimatePresence, motion, useReducedMotion } from "motion/react";
import { SohbetClient } from "@/app/listem/sohbet-client";
import { ViewportPortal } from "@/components/viewport-portal";
export function SohbetPopup({ kredi }: { kredi: number }) {
const [acik, setAcik] = useState(false);
@@ -23,7 +24,7 @@ export function SohbetPopup({ kredi }: { kredi: number }) {
}, [acik]);
return (
<>
<ViewportPortal>
<AnimatePresence>
{acik ? (
<motion.div
@@ -68,6 +69,6 @@ export function SohbetPopup({ kredi }: { kredi: number }) {
)}
{acik ? "Kapat" : "Danışmana sor"}
</button>
</>
</ViewportPortal>
);
}