fix merge conflict
This commit is contained in:
commit
9746927126
6 changed files with 298 additions and 129 deletions
63
src/components/CTA.tsx
Normal file
63
src/components/CTA.tsx
Normal file
|
|
@ -0,0 +1,63 @@
|
|||
import { useAtom } from "jotai/index";
|
||||
import recordVideoModalOpen from "~/atoms/recordVideoModalOpen";
|
||||
import { usePostHog } from "posthog-js/react";
|
||||
|
||||
export default function CTA() {
|
||||
const [, setRecordOpen] = useAtom(recordVideoModalOpen);
|
||||
const posthog = usePostHog();
|
||||
|
||||
const openRecordModal = () => {
|
||||
setRecordOpen(true);
|
||||
|
||||
posthog?.capture("open record video modal", {
|
||||
cta: "cta section",
|
||||
});
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="bg-white">
|
||||
<div className="mx-auto max-w-7xl py-12 sm:px-6 sm:py-16 lg:px-8">
|
||||
<div className="relative isolate overflow-hidden bg-gray-900 px-6 py-24 text-center shadow-2xl sm:rounded-3xl sm:px-16">
|
||||
<h2 className="mx-auto max-w-2xl text-4xl font-bold tracking-tight text-white">
|
||||
Ready to improve how your team communicates?
|
||||
</h2>
|
||||
<div className="mt-10 flex items-center justify-center gap-x-6">
|
||||
<button
|
||||
onClick={openRecordModal}
|
||||
className="inline-flex max-h-[40px] items-center rounded-md border border-transparent bg-red-600 px-4 py-2 text-sm font-medium text-white shadow-sm hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-red-500 focus:ring-offset-2"
|
||||
>
|
||||
Record a video
|
||||
</button>
|
||||
</div>
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
viewBox="0 0 1024 1024"
|
||||
className="absolute left-1/2 top-1/2 -z-10 h-[64rem] w-[64rem] -translate-x-1/2"
|
||||
aria-hidden="true"
|
||||
>
|
||||
<circle
|
||||
cx={512}
|
||||
cy={512}
|
||||
r={512}
|
||||
fill="url(#827591b1-ce8c-4110-b064-7cb85a0b1217)"
|
||||
fillOpacity="0.7"
|
||||
/>
|
||||
<defs>
|
||||
<radialGradient
|
||||
id="827591b1-ce8c-4110-b064-7cb85a0b1217"
|
||||
cx={0}
|
||||
cy={0}
|
||||
r={1}
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="translate(512 512) rotate(90) scale(512)"
|
||||
>
|
||||
<stop stopColor="#7775D6" />
|
||||
<stop offset={1} stopColor="#E935C1" stopOpacity={0} />
|
||||
</radialGradient>
|
||||
</defs>
|
||||
</svg>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
|
@ -1,35 +1,27 @@
|
|||
import Link from "next/link";
|
||||
|
||||
export default function Footer() {
|
||||
return (
|
||||
<div className="mx-16 flex items-center justify-center">
|
||||
<footer className="mb-4 mt-4 flex h-full w-[1048px] flex-col-reverse items-center justify-between text-sm md:flex-row">
|
||||
<div className="mx-8 my-[50px] text-sm text-[#666] md:my-0">
|
||||
<div className="my-[50px] ml-8 text-sm text-[#666] md:my-0">
|
||||
© 2023 Snapify
|
||||
</div>
|
||||
<div className="mx-8 flex w-full flex-col px-[50px] md:w-auto md:flex-row md:px-0">
|
||||
<a
|
||||
className="flex h-[42px] cursor-pointer items-center border-b border-[#eee] text-sm text-[#666] hover:text-black md:ml-8 md:border-none"
|
||||
href="/legal/privacy-policy"
|
||||
<div className="mr-8 flex w-full flex-col sm:px-[50px] md:w-auto md:flex-row md:gap-8 md:px-0">
|
||||
{[
|
||||
{ name: "Privacy Policy", link: "/legal/privacy-policy" },
|
||||
{ name: "Terms and Conditions", link: "/legal/terms" },
|
||||
{ name: "Status", link: "https://status.snapify.it" },
|
||||
{ name: "Impressum", link: "/legal/impressum" },
|
||||
].map(({ name, link }) => (
|
||||
<Link
|
||||
key={name}
|
||||
className="flex h-[42px] cursor-pointer items-center border-b border-[#eee] text-sm text-[#666] hover:text-black md:border-none"
|
||||
href={link}
|
||||
>
|
||||
Privacy Policy
|
||||
</a>
|
||||
<a
|
||||
className="flex h-[42px] cursor-pointer items-center border-b border-[#eee] text-sm text-[#666] hover:text-black md:ml-8 md:border-none"
|
||||
href="/legal/terms"
|
||||
>
|
||||
Terms and Conditions
|
||||
</a>
|
||||
<a
|
||||
className="flex h-[42px] cursor-pointer items-center border-b border-[#eee] text-sm text-[#666] hover:text-black md:ml-8 md:border-none"
|
||||
href="/legal/impressum"
|
||||
>
|
||||
Impressum
|
||||
</a>
|
||||
<a
|
||||
className="flex h-[42px] cursor-pointer items-center border-b border-[#eee] text-sm text-[#666] hover:text-black md:ml-8 md:border-none"
|
||||
href="https://status.snapify.it"
|
||||
>
|
||||
Status
|
||||
</a>
|
||||
{name}
|
||||
</Link>
|
||||
))}
|
||||
</div>
|
||||
</footer>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -49,20 +49,14 @@ export default function Header() {
|
|||
</Link>
|
||||
))}
|
||||
</div>
|
||||
|
||||
<div className="flex flex-row items-center md:hidden">
|
||||
<Link
|
||||
href="/sign-in"
|
||||
className="text-sm font-semibold leading-6 text-gray-900"
|
||||
>
|
||||
Log in <span aria-hidden="true">→</span>
|
||||
</Link>
|
||||
|
||||
<>
|
||||
<div className="flex flex-row items-center md:hidden">
|
||||
<Link href={"#"} className="mr-6">
|
||||
<div className="block h-[32px] rounded-[5px] border border-solid border-black bg-black p-2 text-sm leading-3 text-white transition hover:bg-white hover:text-black">
|
||||
Open App
|
||||
</div>
|
||||
</Link>
|
||||
<div
|
||||
className="flex h-[42px] w-[42px] cursor-pointer items-center justify-center"
|
||||
onClick={() => setNavbarOpen(!navbarOpen)}
|
||||
|
|
@ -83,28 +77,14 @@ export default function Header() {
|
|||
: "invisible top-[80px]"
|
||||
}`}
|
||||
>
|
||||
<Link href="/" onClick={closeNav}>
|
||||
{navigation.map(({ href, name }) => (
|
||||
<Link key={name} href={href} onClick={closeNav}>
|
||||
<div className="flex h-[48px] cursor-pointer items-center border-b border-[#EAEAEA] text-[16px] hover:bg-[#FAFAFA]">
|
||||
Overview
|
||||
{name}
|
||||
</div>
|
||||
</Link>
|
||||
<Link href="/contact" onClick={closeNav}>
|
||||
<div className="flex h-[48px] cursor-pointer items-center border-b border-[#EAEAEA] text-[16px] hover:bg-[#FAFAFA]">
|
||||
Contact
|
||||
))}
|
||||
</div>
|
||||
</Link>
|
||||
<Link href="/changelog" onClick={closeNav}>
|
||||
<div className="flex h-[48px] cursor-pointer items-center border-b border-[#EAEAEA] text-[16px] hover:bg-[#FAFAFA]">
|
||||
Changelog
|
||||
</div>
|
||||
</Link>
|
||||
<Link href="https://app.tablane.net/shared/board/63906741c22c232ed88df799">
|
||||
<div className="flex h-[48px] cursor-pointer items-center border-b border-[#EAEAEA] text-[16px] hover:bg-[#FAFAFA]">
|
||||
Roadmap
|
||||
</div>
|
||||
</Link>
|
||||
</div>
|
||||
</>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
|
|
|
|||
|
|
@ -92,7 +92,7 @@ export default function Paywall() {
|
|||
<div className="w-full md:max-w-sm">
|
||||
<div className="sm:align-center mb-4 flex flex-none flex-wrap items-center gap-4 px-2 py-1 md:justify-center">
|
||||
<div className="relative flex items-center gap-2 text-sm font-medium">
|
||||
<span className=" svelte-10wstod">Monthly</span>
|
||||
<span className="">Monthly</span>
|
||||
<label className="group relative flex cursor-pointer items-center gap-2 text-sm font-medium text-gray-600">
|
||||
<input
|
||||
onChange={toggleBillingCycle}
|
||||
|
|
@ -105,9 +105,7 @@ export default function Paywall() {
|
|||
</span>
|
||||
<span />
|
||||
</label>
|
||||
<span className="svelte-10wstod opacity-50">
|
||||
Annually
|
||||
</span>
|
||||
<span className="opacity-50">Annually</span>
|
||||
<span className="rounded-md bg-[#cbf4c9] px-2 py-1 text-xs text-[#0e6245]">
|
||||
20% Off
|
||||
</span>
|
||||
|
|
@ -118,7 +116,7 @@ export default function Paywall() {
|
|||
className="w-full flex-none rounded-3xl border bg-white shadow-sm"
|
||||
>
|
||||
<div className="hero relative flex flex-col items-start rounded-3xl px-6 py-6 shadow-sm">
|
||||
<div className="svelte-10wstod rounded-lg bg-white/20 px-2 font-medium">
|
||||
<div className="rounded-lg bg-white/20 px-2 font-medium">
|
||||
Pro
|
||||
</div>
|
||||
<div className="mb-2 mt-4 flex items-end text-5xl font-extrabold tracking-tight">
|
||||
|
|
@ -167,7 +165,7 @@ export default function Paywall() {
|
|||
</div>
|
||||
|
||||
<Tooltip title={description}>
|
||||
<div className="svelte-10wstod text-base text-gray-500 underline decoration-gray-400 decoration-dashed underline-offset-4">
|
||||
<div className="text-base text-gray-500 underline decoration-gray-400 decoration-dashed underline-offset-4">
|
||||
{feature}
|
||||
</div>
|
||||
</Tooltip>
|
||||
|
|
|
|||
|
|
@ -11,6 +11,7 @@ import { CheckCircleIcon } from "@heroicons/react/24/outline";
|
|||
import Footer from "~/components/Footer";
|
||||
import Header from "~/components/Header";
|
||||
import Image from "next/image";
|
||||
import CTA from "~/components/CTA";
|
||||
|
||||
const Home: NextPage = () => {
|
||||
const [, setRecordOpen] = useAtom(recordVideoModalOpen);
|
||||
|
|
@ -299,50 +300,7 @@ const Home: NextPage = () => {
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="bg-white">
|
||||
<div className="mx-auto max-w-7xl py-12 sm:px-6 sm:py-16 lg:px-8">
|
||||
<div className="relative isolate overflow-hidden bg-gray-900 px-6 py-24 text-center shadow-2xl sm:rounded-3xl sm:px-16">
|
||||
<h2 className="mx-auto max-w-2xl text-4xl font-bold tracking-tight text-white">
|
||||
Ready to improve how your team communicates?
|
||||
</h2>
|
||||
<div className="mt-10 flex items-center justify-center gap-x-6">
|
||||
<button
|
||||
onClick={openRecordModal}
|
||||
className="inline-flex max-h-[40px] items-center rounded-md border border-transparent bg-red-600 px-4 py-2 text-sm font-medium text-white shadow-sm hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-red-500 focus:ring-offset-2"
|
||||
>
|
||||
Record a video
|
||||
</button>
|
||||
</div>
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
viewBox="0 0 1024 1024"
|
||||
className="absolute left-1/2 top-1/2 -z-10 h-[64rem] w-[64rem] -translate-x-1/2"
|
||||
aria-hidden="true"
|
||||
>
|
||||
<circle
|
||||
cx={512}
|
||||
cy={512}
|
||||
r={512}
|
||||
fill="url(#827591b1-ce8c-4110-b064-7cb85a0b1217)"
|
||||
fillOpacity="0.7"
|
||||
/>
|
||||
<defs>
|
||||
<radialGradient
|
||||
id="827591b1-ce8c-4110-b064-7cb85a0b1217"
|
||||
cx={0}
|
||||
cy={0}
|
||||
r={1}
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="translate(512 512) rotate(90) scale(512)"
|
||||
>
|
||||
<stop stopColor="#7775D6" />
|
||||
<stop offset={1} stopColor="#E935C1" stopOpacity={0} />
|
||||
</radialGradient>
|
||||
</defs>
|
||||
</svg>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<CTA />
|
||||
|
||||
<Footer />
|
||||
</div>
|
||||
|
|
|
|||
178
src/pages/pricing.tsx
Normal file
178
src/pages/pricing.tsx
Normal file
|
|
@ -0,0 +1,178 @@
|
|||
import Footer from "~/components/Footer";
|
||||
import Header from "~/components/Header";
|
||||
import Head from "next/head";
|
||||
import { useState } from "react";
|
||||
import { CheckIcon } from "@heroicons/react/20/solid";
|
||||
import Tooltip from "~/components/Tooltip";
|
||||
import { Disclosure, Transition } from "@headlessui/react";
|
||||
import { ChevronUpIcon } from "@heroicons/react/20/solid";
|
||||
import CTA from "~/components/CTA";
|
||||
import VideoRecordModal from "~/components/VideoRecordModal";
|
||||
|
||||
export default function Pricing() {
|
||||
const [billedAnnually, setBilledAnnually] = useState<boolean>(false);
|
||||
|
||||
return (
|
||||
<>
|
||||
<Head>
|
||||
<title>{"Snapify | Pricing"}</title>
|
||||
<meta name="description" content="Generated by create-t3-app" />
|
||||
<link rel="icon" href="/favicon.ico" />
|
||||
</Head>
|
||||
<Header />
|
||||
<div className="my-20 flex h-40 items-center justify-center sm:mx-10 lg:mx-20">
|
||||
<span className="text-center text-4xl font-bold lg:text-7xl">
|
||||
Choose the plan that fits your needs.
|
||||
</span>
|
||||
</div>
|
||||
|
||||
<div className="relative mx-4 mb-20 flex flex-col items-center justify-center gap-12 md:flex-row md:gap-4 lg:mx-16 lg:gap-16">
|
||||
<div className="absolute left-[calc(50%_-_calc(min(75vw,500px)_/_2))] h-[min(75vw,500px)] w-[min(75vw,500px)] bg-[radial-gradient(circle_at_center,#666_0,#fff_100%)] opacity-80 blur-[calc(0.5_*_min(75vw,500px))]"></div>
|
||||
{[
|
||||
{
|
||||
name: "Free",
|
||||
price: { monthly: 0, annual: 0 },
|
||||
features: [
|
||||
{
|
||||
feature: "Unlimited video recording",
|
||||
description: "Record and share unlimited videos",
|
||||
},
|
||||
{
|
||||
feature: "10 video uploads",
|
||||
description: "Upload external videos to your Library",
|
||||
},
|
||||
{
|
||||
feature: "Remove branding",
|
||||
description: "Remove Snapify branding from your videos",
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
name: "Pro",
|
||||
price: { monthly: 5, annual: 4 },
|
||||
features: [
|
||||
{
|
||||
feature: "Unlimited videos",
|
||||
description: "Record and share unlimited videos",
|
||||
},
|
||||
{
|
||||
feature: "Video uploads",
|
||||
description: "Upload external videos to your Library",
|
||||
},
|
||||
{
|
||||
feature: "Remove branding",
|
||||
description: "Remove Snapify branding from your videos",
|
||||
},
|
||||
],
|
||||
},
|
||||
].map(({ name, price, features }) => (
|
||||
<div
|
||||
key={name}
|
||||
className="relative w-full max-w-[400px] flex-1 rounded-3xl border bg-white shadow-sm"
|
||||
>
|
||||
{name === "Pro" ? (
|
||||
<div className="absolute -top-6 left-2/4 z-[1] mt-0 -translate-x-2/4 cursor-default select-none rounded-3xl border-0 border-solid border-[#eaeaea] bg-[linear-gradient(180deg,rgba(0,0,0,.8),#000)] px-[22px] py-3.5 text-white shadow-[0_8px_30px_rgb(0_0_0/6%)] backdrop-blur-[2px]">
|
||||
<span className="text-xs font-bold">Most Popular</span>
|
||||
</div>
|
||||
) : null}
|
||||
<div className="hero relative flex flex-col items-start rounded-3xl px-6 py-6 shadow-sm">
|
||||
<div className="rounded-lg bg-white/20 px-2 font-medium">
|
||||
{name}
|
||||
</div>
|
||||
<div className="mb-2 mt-4 flex items-end text-5xl font-extrabold tracking-tight">
|
||||
{billedAnnually ? price.annual : price.monthly}
|
||||
<span className="mb-1 text-sm opacity-80">/ mo.</span>
|
||||
</div>
|
||||
<div className="mt-2 text-sm">
|
||||
{billedAnnually ? "billed annually" : "billed monthly"}
|
||||
</div>
|
||||
<div className="mt-2 flex-grow" />
|
||||
<button
|
||||
type="submit"
|
||||
className="btn mt-4 block w-full appearance-none rounded-lg bg-black px-4 py-2.5 text-center text-sm font-medium text-white shadow-lg shadow-black/50 duration-100 focus:outline-transparent disabled:opacity-80"
|
||||
>
|
||||
Get started
|
||||
</button>
|
||||
</div>
|
||||
<div className="mt-4 flex flex-col gap-2 pb-8">
|
||||
{features.map(({ feature, description }) => (
|
||||
<div
|
||||
key={feature}
|
||||
className="flex items-center gap-2 text-gray-500"
|
||||
>
|
||||
<div className="ml-6 h-5 w-5 flex-none">
|
||||
<CheckIcon />
|
||||
</div>
|
||||
|
||||
<Tooltip title={description}>
|
||||
<div className="text-base text-gray-500 underline decoration-gray-400 decoration-dashed underline-offset-4">
|
||||
{feature}
|
||||
</div>
|
||||
</Tooltip>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
|
||||
<div className="flex flex-col items-center justify-center border-y border-[#eaeaea] bg-[#fafafa] pb-8">
|
||||
<div className="mb-12 mt-8">
|
||||
<span className="text-5xl font-bold">FAQs</span>
|
||||
</div>
|
||||
<div className="flex flex-1 border-collapse flex-col justify-center px-6">
|
||||
{[
|
||||
{
|
||||
question: "What are my payment options?",
|
||||
answer:
|
||||
"You can be billed monthly, but save 20% if you pay annually. We currently accept credit card payment. Contact us at hello@snapify.it if you need an alternative payment method.",
|
||||
},
|
||||
{
|
||||
question:
|
||||
"What happens when I hit my 10 video limit on the Free plan?",
|
||||
answer:
|
||||
"Our Free plan has a limit of 10 videos. To record more than 10 videos, you will need to delete videos or upgrade to the Pro plan.",
|
||||
},
|
||||
].map(({ answer, question }) => (
|
||||
<Disclosure
|
||||
key={question}
|
||||
as="div"
|
||||
className="max-w-[600px] max-w-[80vw] sm:w-[600px]"
|
||||
>
|
||||
{({ open }) => (
|
||||
<>
|
||||
<Disclosure.Button className="flex h-12 w-full items-center justify-between border-t border-[#eaeaea] px-4 py-8 text-left text-sm font-medium">
|
||||
<span>{question}</span>
|
||||
<ChevronUpIcon
|
||||
className={`transition-transform ${
|
||||
open ? "rotate-180" : ""
|
||||
} h-5 w-5`}
|
||||
/>
|
||||
</Disclosure.Button>
|
||||
<Transition
|
||||
enter="transition duration-100 ease-out"
|
||||
enterFrom="transform scale-95 opacity-0"
|
||||
enterTo="transform scale-100 opacity-100"
|
||||
leave="transition duration-75 ease-out"
|
||||
leaveFrom="transform scale-100 opacity-100"
|
||||
leaveTo="transform scale-95 opacity-0"
|
||||
>
|
||||
<Disclosure.Panel className="px-4 pb-2 pt-0 text-sm text-gray-500">
|
||||
{answer}
|
||||
</Disclosure.Panel>
|
||||
</Transition>
|
||||
</>
|
||||
)}
|
||||
</Disclosure>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<CTA />
|
||||
|
||||
<Footer />
|
||||
|
||||
<VideoRecordModal />
|
||||
</>
|
||||
);
|
||||
}
|
||||
Loading…
Reference in a new issue