import { Component, createSignal } from 'solid-js'; import { A } from '@solidjs/router'; import { useBetaSignup } from '../../lib/api/trpc-hooks'; import '../../styles/beta-signup.css'; export const BetaSignup: Component = () => { const [formData, setFormData] = createSignal({ name: '', email: '', primaryRole: '', scriptsWritten: '', currentSoftware: '', softwareLove: '', softwareFrustrate: '', hoursPerWeek: '', willingFeedback: '', joinDiscord: '', discordUsername: '', excitedFeatures: [] as string[], heardAbout: '', additionalInfo: '', utmSource: '', utmMedium: '', utmCampaign: '', utmContent: '', utmTerm: '', }); const [submitted, setSubmitted] = createSignal(false); const [error, setError] = createSignal(''); const [isSubmitting, setIsSubmitting] = createSignal(false); const betaSignup = useBetaSignup(); const captureUTMParams = () => { if (typeof window === 'undefined') return { utmSource: '', utmMedium: '', utmCampaign: '', utmContent: '', utmTerm: '', }; const params = new URLSearchParams(window.location.search); return { utmSource: params.get('utm_source') || '', utmMedium: params.get('utm_medium') || '', utmCampaign: params.get('utm_campaign') || '', utmContent: params.get('utm_content') || '', utmTerm: params.get('utm_term') || '', }; }; const utmParams = captureUTMParams(); const updateField = (field: string, value: any) => { setFormData((prev) => ({ ...prev, [field]: value })); }; const toggleFeature = (feature: string) => { setFormData((prev) => { const features = prev.excitedFeatures.includes(feature) ? prev.excitedFeatures.filter((f) => f !== feature) : [...prev.excitedFeatures, feature]; return { ...prev, excitedFeatures: features }; }); }; const handleSubmit = async (e: Event) => { e.preventDefault(); setError(''); const data = formData(); if (!data.name.trim() || !data.email.trim()) { setError('Name and email are required.'); return; } if (!data.primaryRole) { setError('Please select your primary role.'); return; } if (!data.willingFeedback || data.willingFeedback === 'No, just want early access') { setError('Beta access requires willingness to provide weekly feedback.'); return; } setIsSubmitting(true); try { await betaSignup.mutateAsync({ name: data.name.trim(), email: data.email.trim(), primaryRole: data.primaryRole, scriptsWritten: data.scriptsWritten, currentSoftware: data.currentSoftware, softwareLove: data.softwareLove, softwareFrustrate: data.softwareFrustrate, hoursPerWeek: data.hoursPerWeek, willingFeedback: data.willingFeedback, joinDiscord: data.joinDiscord, discordUsername: data.discordUsername, excitedFeatures: data.excitedFeatures, heardAbout: data.heardAbout, additionalInfo: data.additionalInfo, utmSource: utmParams.utmSource, utmMedium: utmParams.utmMedium, utmCampaign: utmParams.utmCampaign, utmContent: utmParams.utmContent, utmTerm: utmParams.utmTerm, }); setSubmitted(true); } catch (err: any) { setError(err?.message || 'Something went wrong. Please try again.'); } finally { setIsSubmitting(false); } }; return (

Join the Scripter Beta

Help us build the future of screenwriting. We're looking for 500 active writers to test Scripter before our public launch.

🎬 3-week beta program 📝 Weekly feedback (5 min) 💬 Discord community
{submitted() ? (
🎉

Application Submitted!

Thanks for applying to the Scripter beta. We're reviewing applications and will get back to you within 48 hours.

What happens next:

  1. We'll review your application
  2. If accepted, you'll get beta access + Discord invite
  3. Beta starts April 26 - get ready to write!
) : (
{error() &&
{error()}
}

Section 1: About You

updateField('name', e.currentTarget.value)} required />
updateField('email', e.currentTarget.value)} required />

Section 2: Current Tools