//
//  theme.currentTheme.swift
//  Reflect (iOS)
//
//  Created by Trey Tartt on 2/4/22.
//

import SwiftUI

struct ThemeConstants {
    static let iconSize: CGFloat = 50
}

enum Theme: String, CaseIterable {
    case system = "system"
    case iFeel = "iFeel"
    case dark = "dark"
    case light = "light"

    // Legacy Int-based init for backwards compatibility with existing UserDefaults data
    init?(legacyIntValue: Int) {
        switch legacyIntValue {
        case 0: self = .system
        case 1: self = .iFeel
        case 2: self = .dark
        case 3: self = .light
        default: return nil
        }
    }

    var title: String {
        switch self {
        case .system:
            return SystemTheme.title
        case .iFeel:
            return IFeelTheme.title
        case .dark:
            return AlwaysDark.title
        case .light:
            return AlwaysLight.title
        }
    }
    
    var currentTheme: Themeable {
        switch self {

        case .system:
            return SystemTheme()
        case .iFeel:
            return IFeelTheme()
        case .dark:
            return AlwaysDark()
        case .light:
            return AlwaysLight()
        }
    }

    var preferredColorScheme: ColorScheme? {
        switch self {
        case .system, .iFeel:
            return nil // Follow system
        case .dark:
            return .dark
        case .light:
            return .light
        }
    }
}

protocol Themeable {
    static var title: String { get }
    var secondaryBGColor: Color { get }
    var bgColor: Color { get }
    var bg: AnyView { get }
    var preview: AnyView { get }
    var labelColor: Color { get }
}

struct IFeelTheme: Themeable {
    var bgColor: Color {
        return Color(uiColor: UIColor.systemBackground)
    }
    
    var labelColor: Color {
        return Color(uiColor: UIColor.label)
    }
    
    static var title: String {
        return "iFeel"
    }
    
    var secondaryBGColor: Color {
        return Color(uiColor: UIColor.secondarySystemBackground)
    }
    
    var bg: AnyView {
        return AnyView(
            BGView().equatable()
        )
    }
    
    var preview: AnyView {
        return AnyView(
            ZStack {
                BGView().equatable()
                    .frame(width: ThemeConstants.iconSize, height: ThemeConstants.iconSize)
                    .clipShape(RoundedRectangle(cornerRadius: 25, style: .continuous))
            }
        )
    }
}

struct SystemTheme: Themeable {
    var bgColor: Color {
        return Color(uiColor: UIColor.systemBackground)
    }
    
    var labelColor: Color {
        return Color(uiColor: UIColor.label)
    }
    
    static var title: String {
        return "System"
    }
    
    var secondaryBGColor: Color {
        return Color(uiColor: UIColor.secondarySystemBackground)
    }
    
    var bg: AnyView {
        return AnyView(
            ZStack {
                Rectangle()
                    .fill(Color(UIColor.systemBackground))
            }
        )
    }
    
    var preview: AnyView {
        return AnyView(
            ZStack {
                Rectangle()
                    .fill(Color(UIColor.secondarySystemBackground))
                    .frame(width: ThemeConstants.iconSize, height: ThemeConstants.iconSize)
                    .clipShape(RoundedRectangle(cornerRadius: 25, style: .continuous))
            }
        )
    }
}

struct AlwaysDark: Themeable {
    var bgColor: Color {
        return Color(uiColor: UIColor.systemBackground.resolvedColor(with: .init(userInterfaceStyle: .dark)))
    }
    
    var labelColor: Color {
        return .white
    }
    
    static var title: String {
        return "Dark"
    }
    
    var secondaryBGColor: Color {
        return Color(uiColor: UIColor.secondarySystemBackground.resolvedColor(with: .init(userInterfaceStyle: .dark)))
    }
    
    var bg: AnyView {
        return AnyView(
            ZStack {
                Rectangle()
                    .fill(Color(UIColor.systemBackground.resolvedColor(with: .init(userInterfaceStyle: .dark))))
            }
        )
    }
    
    var preview: AnyView {
        return AnyView(
            ZStack {
                Rectangle()
                    .fill(Color(UIColor.secondarySystemBackground.resolvedColor(with: .init(userInterfaceStyle: .dark))))
                    .frame(width: ThemeConstants.iconSize, height: ThemeConstants.iconSize)
                    .clipShape(RoundedRectangle(cornerRadius: 25, style: .continuous))
            }
        )
    }
}

struct AlwaysLight: Themeable {
    var bgColor: Color {
        return Color(uiColor: UIColor.systemBackground)
    }
    
    var labelColor: Color {
        return .black
    }
    
    static var title: String {
        return "Light"
    }
    
    var secondaryBGColor: Color {
        return Color(uiColor: UIColor.secondarySystemBackground.resolvedColor(with: .init(userInterfaceStyle: .light)))
    }
    
    var bg: AnyView {
        return AnyView(
            ZStack {
                Rectangle()
                    .fill(Color(UIColor.systemBackground.resolvedColor(with: .init(userInterfaceStyle: .light))))
            }
        )
    }
    
    var preview: AnyView {
        return AnyView(
            ZStack {
                Rectangle()
                    .fill(Color(UIColor.secondarySystemBackground.resolvedColor(with: .init(userInterfaceStyle: .light))))
                    .frame(width: ThemeConstants.iconSize, height: ThemeConstants.iconSize)
                    .clipShape(RoundedRectangle(cornerRadius: 25, style: .continuous))
            }
        )
    }
}
