// // OnboardingSoftPaywallView.swift // SelfieCam // // Soft paywall shown to free users during onboarding. // Presents premium benefits with options to upgrade or continue with free version. // Supports landscape and iPad layouts with max width constraints. // import SwiftUI import Bedrock struct OnboardingSoftPaywallView: View { @Bindable var viewModel: OnboardingViewModel @Bindable var settingsViewModel: SettingsViewModel @Binding var showPaywall: Bool let onComplete: () -> Void /// Premium manager for restore purchases @State private var premiumManager = PremiumManager() /// Whether a restore is in progress @State private var isRestoring = false var body: some View { OnboardingContentContainer { VStack(spacing: Design.Spacing.large) { Spacer() // Header VStack(spacing: Design.Spacing.medium) { SymbolIcon("crown.fill", size: .hero, color: AppStatus.warning) OnboardingSectionTitle( title: String(localized: "Unlock Pro Features"), subtitle: String(localized: "Get the most out of SelfieCam") ) } Spacer() // Benefits list VStack(alignment: .leading, spacing: Design.Spacing.medium) { OnboardingBenefitRow( image: "paintpalette.fill", text: String(localized: "Premium Colors + Custom Color Picker") ) OnboardingBenefitRow( image: "sparkles", text: String(localized: "Skin Smoothing Beauty Filter") ) OnboardingBenefitRow( image: "arrow.left.and.right.righttriangle.left.righttriangle.right.fill", text: String(localized: "True Mirror Mode") ) OnboardingBenefitRow( image: "camera.filters", text: String(localized: "HDR Mode for Better Photos") ) OnboardingBenefitRow( image: "timer", text: String(localized: "Extended Self-Timers (5s, 10s)") ) OnboardingBenefitRow( image: "star.fill", text: String(localized: "High Quality Photo Export") ) } .padding(.horizontal, Design.Spacing.large) Spacer() // Action buttons VStack(spacing: Design.Spacing.medium) { // Upgrade button OnboardingPrimaryButton( title: String(localized: "Upgrade to Pro"), action: { showPaywall = true }, icon: "crown.fill", style: .premium ) // Maybe Later button OnboardingSecondaryButton( title: String(localized: "Maybe Later"), action: { viewModel.completeOnboarding(settingsViewModel: settingsViewModel) onComplete() } ) // Restore Purchases button Button { Task { isRestoring = true try? await premiumManager.restorePurchases() isRestoring = false // Check if premium was restored if premiumManager.isPremiumUnlocked { viewModel.completeOnboarding(settingsViewModel: settingsViewModel) onComplete() } } } label: { if isRestoring { ProgressView() .tint(.secondary) } else { Text(String(localized: "Restore Purchases")) } } .font(.footnote) .foregroundStyle(.secondary) .disabled(isRestoring) } .padding(.horizontal, Design.Spacing.xLarge) .padding(.bottom, Design.Spacing.xLarge) } .padding(.horizontal, Design.Spacing.medium) } .onChange(of: viewModel.isPremiumUser) { _, isPremium in // If user subscribed during paywall, complete onboarding if isPremium { viewModel.completeOnboarding(settingsViewModel: settingsViewModel) onComplete() } } } } // MARK: - Preview #Preview { OnboardingSoftPaywallView( viewModel: OnboardingViewModel(), settingsViewModel: SettingsViewModel(), showPaywall: .constant(false), onComplete: {} ) .background(AppSurface.primary) .preferredColorScheme(.dark) } #Preview("Landscape", traits: .landscapeLeft) { OnboardingSoftPaywallView( viewModel: OnboardingViewModel(), settingsViewModel: SettingsViewModel(), showPaywall: .constant(false), onComplete: {} ) .background(AppSurface.primary) .preferredColorScheme(.dark) }