//
//  ListOneColumnFullWidthTextAllTextAndLinks.swift
//  MVMCoreUI
//
//  Created by Kruthika KP on 14/02/20.
//  Copyright © 2020 Verizon Wireless. All rights reserved.
//

import Foundation


@objcMembers public class ListOneColumnFullWidthTextAllTextAndLinks: TableViewCell {
    //-----------------------------------------------------
    // MARK: - Outlets
    //-----------------------------------------------------
    
    var stack: Stack<StackModel>
    let eyebrow = Label(fontStyle: .RegularMicro)
    let headline = Label(fontStyle: .BoldTitleMedium)
    let subHeadline = Label(fontStyle: .BoldBodySmall)
    let body = Label(fontStyle: .RegularBodySmall)
    let link = Link()
    
    //-----------------------------------------------------
    // MARK: - Initializers
    //-----------------------------------------------------
    public override init(style: UITableViewCell.CellStyle, reuseIdentifier: String?) {
        stack = Stack<StackModel>.createStack(with: [eyebrow, headline, subHeadline, body, link])
        stack.stackModel?.spacing = 0
        stack.stackModel?.molecules[4].spacing = 8
        super.init(style: style, reuseIdentifier: reuseIdentifier)
    }
    
    public required init?(coder aDecoder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }
    
    //-----------------------------------------------------
    // MARK: - View Lifecycle
    //-----------------------------------------------------
    
    override open func setupView() {
        super.setupView()
        addMolecule(stack)
        stack.restack()
    }
    
    open override func set(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?, _ additionalData: [AnyHashable: Any]?) {
        super.set(with: model, delegateObject, additionalData)
        
        guard let model = model as? ListOneColumnFullWidthTextAllTextAndLinksModel else { return }
        
        stack.updateContainedMolecules(with: [model.eyebrow, model.headline, model.subHeadline, model.body, model.link],
                                       delegateObject, additionalData)
        updateAccessibilityLabel()
    }
    
    open override class func estimatedHeight(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?) -> CGFloat? {
        return 90
    }
    
    open override func reset() {
        super.reset()
        eyebrow.setFontStyle(.RegularMicro)
        headline.setFontStyle(.BoldTitleMedium)
        subHeadline.setFontStyle(.BoldBodySmall)
        body.setFontStyle(.RegularBodySmall)
    }
    
    //--------------------------------------------------
    // MARK: - Accessibility
    //--------------------------------------------------
    
    func getAccessibilityMessage() -> String? {
        var message = ""
        
        if let eyebrowLabel = eyebrow.text, !eyebrowLabel.isEmpty {
            message += eyebrowLabel + ", "
        }
        
        if let headlineLabel = headline.text, !headlineLabel.isEmpty {
            message += headlineLabel + ", "
        }
        
        if let subHeadlineLabel = subHeadline.text, !subHeadlineLabel.isEmpty {
            message += subHeadlineLabel + ", "
        }
        
        if let bodyLabel = body.text, !bodyLabel.isEmpty {
            message += bodyLabel
        }
        return message.count > 0 ? message : nil
    }
    
    // Ensures voice over does not read "selected" after user triggers action on cell.
    override public var accessibilityTraits: UIAccessibilityTraits {
        get {
            return (accessoryView != nil) ? .button : .none
        }
        set {}
    }
    
    func updateAccessibilityLabel() {

        let linkShowing = link.titleLabel?.text?.count ?? 0 > 0
        isAccessibilityElement = !linkShowing
        if !linkShowing {
            // Make whole cell focusable if no link.
            accessibilityLabel = getAccessibilityMessage()
        } else if let accessoryView = accessoryView {
            // Both caret and link. Read all content on caret.
            accessoryView.accessibilityLabel = getAccessibilityMessage()
            accessibilityElements = [accessoryView, link]
        } else {
            // Only link. Manually add accessibility elements to ensure they are read in the right order.
            var elements: [Any] = []
            if let eyeBrowText = eyebrow.text, !eyeBrowText.isEmpty {
                elements.append(eyebrow)
            }
            
            if let headlineText = headline.text, !headlineText.isEmpty {
                elements.append(headline)
            }
            
            if let subHeadlineText = subHeadline.text, !subHeadlineText.isEmpty {
                elements.append(subHeadline)
            }
            
            if let bodyText = body.text, !bodyText.isEmpty {
                elements.append(body)
            }
            elements.append(link)
            accessibilityElements = elements
        }
    }
}
