//  AppearancePrefsView.swift
//  Tusker
//
//  Created by Shadowfacts on 6/13/19.
//  Copyright © 2019 Shadowfacts. All rights reserved.
//

import SwiftUI
import Combine

struct AppearancePrefsView : View {
    @ObservedObject var preferences = Preferences.shared

    private var appearanceChangePublisher: some Publisher<Void, Never> {
        preferences.$theme
            .map { _ in () }
            .merge(with: preferences.$pureBlackDarkMode.map { _ in () },
                   preferences.$accentColor.map { _ in () }
            )
            // the prefrence publishers are all willSet, but want to notify after the change, so wait one runloop iteration
            .receive(on: DispatchQueue.main)
    }
    
    private var useCircularAvatars: Binding<Bool> = Binding(get: {
        Preferences.shared.avatarStyle == .circle
    }) {
        Preferences.shared.avatarStyle = $0 ? .circle : .roundRect
    }
    
    private let accentColorsAndImages: [(Preferences.AccentColor, UIImage?)] = Preferences.AccentColor.allCases.map { color in
        var image: UIImage?
        if let color = color.color {
            if #available(iOS 16.0, *) {
                image = UIImage(systemName: "circle.fill")!.withTintColor(color, renderingMode: .alwaysTemplate).withRenderingMode(.alwaysOriginal)
            } else {
                image = UIGraphicsImageRenderer(size: CGSize(width: 20, height: 20)).image { context in
                    color.setFill()
                    context.cgContext.fillEllipse(in: CGRect(x: 0, y: 0, width: 20, height: 20))
                }
            }
        }
        return (color, image)
    }

    var body: some View {
        List {
            themeSection
            interfaceSection
            accountsSection
            postsSection
        }
        .listStyle(.insetGrouped)
        .appGroupedListBackground(container: PreferencesNavigationController.self)
        .navigationBarTitle(Text("Appearance"))
    }
    
    private var themeSection: some View {
        Section {
            Picker(selection: $preferences.theme, label: Text("Theme")) {
                Text("Use System Theme").tag(UIUserInterfaceStyle.unspecified)
                Text("Light").tag(UIUserInterfaceStyle.light)
                Text("Dark").tag(UIUserInterfaceStyle.dark)
            }
            
            // macOS system dark mode isn't pure black, so this isn't necessary
            if !ProcessInfo.processInfo.isMacCatalystApp && !ProcessInfo.processInfo.isiOSAppOnMac {
                Toggle(isOn: $preferences.pureBlackDarkMode) {
                    Text("Pure Black Dark Mode")
                }
            }
            
            Picker(selection: $preferences.accentColor, label: Text("Accent Color")) {
                ForEach(accentColorsAndImages, id: \.0.rawValue) { (color, image) in
                    HStack {
                        Text(color.name)
                        if let image {
                            Spacer()
                            Image(uiImage: image)
                        }
                    }
                    .tag(color)
                }
            }
        }
        .onReceive(appearanceChangePublisher) { _ in
            NotificationCenter.default.post(name: .themePreferenceChanged, object: nil)
        }
        .appGroupedListRowBackground()
    }
    
    @ViewBuilder
    private var interfaceSection: some View {
        if UIDevice.current.userInterfaceIdiom == .pad || UIDevice.current.userInterfaceIdiom == .mac {
            Section(header: Text("Interface")) {
                WidescreenNavigationPrefsView()
            }
            .appGroupedListRowBackground()
        }
    }
    
    private var accountsSection: some View {
        Section(header: Text("Accounts")) {
            Toggle(isOn: useCircularAvatars) {
                Text("Use Circular Avatars")
            }
            Toggle(isOn: $preferences.hideCustomEmojiInUsernames) {
                Text("Hide Custom Emoji in Usernames")
            }
        }
        .appGroupedListRowBackground()
    }
    
    private var postsSection: some View {
        Section(header: Text("Posts")) {
            Toggle(isOn: $preferences.showIsStatusReplyIcon) {
                Text("Show Status Reply Icons")
            }
            Toggle(isOn: $preferences.alwaysShowStatusVisibilityIcon) {
                Text("Always Show Status Visibility Icons")
            }
            Toggle(isOn: $preferences.hideActionsInTimeline) {
                Text("Hide Actions on Timeline")
            }
            Toggle(isOn: $preferences.showLinkPreviews) {
                Text("Show Link Previews")
            }
            Toggle(isOn: $preferences.underlineTextLinks) {
                Text("Underline Links")
            }
            NavigationLink("Leading Swipe Actions") {
                SwipeActionsPrefsView(selection: $preferences.leadingStatusSwipeActions)
                    .edgesIgnoringSafeArea(.all)
                    .navigationTitle("Leading Swipe Actions")
            }
            NavigationLink("Trailing Swipe Actions") {
                SwipeActionsPrefsView(selection: $preferences.trailingStatusSwipeActions)
                    .edgesIgnoringSafeArea(.all)
                    .navigationTitle("Trailing Swipe Actions")
            }
        }
        .appGroupedListRowBackground()
    }
}

#if DEBUG
struct AppearancePrefsView_Previews : PreviewProvider {
    static var previews: some View {
        AppearancePrefsView()
    }
}
#endif
