Files
FamilyMealPlanner/MealMood/Services/PremiumAccess.swift
T
alexandrev-tibco ce88d7b265 2.0: weekly shopping list from planned dishes
- ShoppingItem model (per-week lines; dish-derived or free-text) + schema.
- ShoppingListService.reconcile mirrors planned dishes' ingredients into the
  list, preserving check-off state and user items; plain-text export helper.
- ShoppingListView: grouped by dish, check-off, swipe-delete, free-text adds,
  clear-checked, ShareLink export, and inline on-device "Generate" for planned
  dishes without ingredients (paywall after 3 free generations,
  source=ingredient_generation).
- Home toolbar: cart entry point (all users) + sheet.
- Analytics: shopping_list_opened, shopping_item_added, ingredients_generated.
- Localized in all 6 languages.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01BkanrydYtrme8wipTzWssG
2026-07-12 17:47:41 +02:00

25 lines
890 B
Swift

import Foundation
enum PremiumAccess {
static let freeDishLimit = 15
static let freeFutureWeeks = 1
/// Free users get a taste of on-device ingredient generation; premium is
/// unlimited. Counted per install via UserDefaults.
static let freeIngredientGenerations = 3
private static let generationCountKey = "ingredient_generation_count"
static func hasReachedFreeDishLimit(dishCount: Int, isPremium: Bool) -> Bool {
!isPremium && dishCount >= freeDishLimit
}
static func canGenerateIngredients(isPremium: Bool) -> Bool {
isPremium || UserDefaults.standard.integer(forKey: generationCountKey) < freeIngredientGenerations
}
static func recordIngredientGeneration() {
let count = UserDefaults.standard.integer(forKey: generationCountKey)
UserDefaults.standard.set(count + 1, forKey: generationCountKey)
}
}