diff --git a/MVMCoreUI/Atomic/Atoms/FormFields/TextFields/EntryFieldModel.swift b/MVMCoreUI/Atomic/Atoms/FormFields/TextFields/EntryFieldModel.swift index dd2a3c62..d64f70ae 100644 --- a/MVMCoreUI/Atomic/Atoms/FormFields/TextFields/EntryFieldModel.swift +++ b/MVMCoreUI/Atomic/Atoms/FormFields/TextFields/EntryFieldModel.swift @@ -34,7 +34,7 @@ import Foundation public var baseValue: AnyHashable? public var wasInitiallySelected: Bool = false - public var isValid: Bool? { + public var isValid: Bool? = true { didSet { updateUI?() } } diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/BGImageHeadlineBodyButton.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/BGImageHeadlineBodyButton.swift index 946022ac..bac1b1c2 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/BGImageHeadlineBodyButton.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/BGImageHeadlineBodyButton.swift @@ -6,82 +6,136 @@ // Copyright © 2020 Verizon Wireless. All rights reserved. // -import Foundation @objcMembers public class BGImageHeadlineBodyButton: Container { - let headlineBody = HeadlineBody(frame: .zero) - let button = PillButton(frame: .zero) + //-------------------------------------------------- + // MARK: - Outlets + //-------------------------------------------------- + + let headlineBody = HeadlineBody() + let button = PillButton() let backgroundImageView = LoadImageView(pinnedEdges: .all) - let maxWidth: CGFloat = 350.0 - static let heightConstant: CGFloat = 320.0 + + //-------------------------------------------------- + // MARK: - Property + //-------------------------------------------------- + + let maxWidth: CGFloat = 350 + static let heightConstant: CGFloat = 320 + + //-------------------------------------------------- + // MARK: - Constraints + //-------------------------------------------------- + var heightConstraint: NSLayoutConstraint? - - // MARK: - MVMCoreViewProtocol - open override func updateView(_ size: CGFloat) { - super.updateView(size) - headlineBody.updateView(size) - button.updateView(size) - backgroundImageView.updateView(size) - backgroundImageView.pinEdges(.all) - } - + + //-------------------------------------------------- + // MARK: - Setup + //-------------------------------------------------- + open override func setupView() { super.setupView() + heightConstraint = heightAnchor.constraint(equalToConstant: Self.heightConstant) heightConstraint?.isActive = true backgroundImageView.addSizeConstraintsForAspectRatio = true - + let container = MVMCoreUICommonViewsUtility.commonView() addAndContain(container) container.addSubview(headlineBody) container.addSubview(button) - //Headline view - headlineBody.leadingAnchor.constraint(equalTo: container.leadingAnchor, constant: 0).isActive = true - headlineBody.topAnchor.constraint(equalTo: container.topAnchor, constant: 0).isActive = true - + headlineBody.leadingAnchor.constraint(equalTo: container.leadingAnchor).isActive = true + headlineBody.topAnchor.constraint(equalTo: container.topAnchor).isActive = true + let headLineBodyWidth = headlineBody.widthAnchor.constraint(equalTo: container.widthAnchor, multiplier: 0.67) headLineBodyWidth.priority = UILayoutPriority(rawValue: 999) headLineBodyWidth.isActive = true headlineBody.widthAnchor.constraint(lessThanOrEqualToConstant: maxWidth).isActive = true - //Caret view button.translatesAutoresizingMaskIntoConstraints = false - button.leadingAnchor.constraint(equalTo: container.leadingAnchor, constant: 0).isActive = true - container.bottomAnchor.constraint(greaterThanOrEqualTo: button.bottomAnchor, constant: 0).isActive = true - + button.leadingAnchor.constraint(equalTo: container.leadingAnchor).isActive = true + container.bottomAnchor.constraint(greaterThanOrEqualTo: button.bottomAnchor).isActive = true button.topAnchor.constraint(equalTo: headlineBody.bottomAnchor, constant: PaddingDefault).isActive = true - //Background image view backgroundImageView.translatesAutoresizingMaskIntoConstraints = false backgroundImageView.imageView.contentMode = .scaleAspectFill backgroundImageView.pinEdges(.all) addSubview(backgroundImageView) NSLayoutConstraint.constraintPinSubview(toSuperview: backgroundImageView) sendSubviewToBack(backgroundImageView) - } + isAccessibilityElement = true + accessibilityHint = button.accessibilityHint + accessibilityTraits = button.accessibilityTraits + } + + //-------------------------------------------------- // MARK: - MoleculeViewProtocol + //-------------------------------------------------- + + open override func updateView(_ size: CGFloat) { + super.updateView(size) + headlineBody.updateView(size) + button.updateView(size) + backgroundImageView.updateView(size) + backgroundImageView.pinEdges(.all) + } + open override func reset() { super.reset() headlineBody.reset() backgroundImageView.reset() } - // MARK:- MoleculeViewProtocol public override class func estimatedHeight(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?) -> CGFloat? { return 320 } - public override func set(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?, _ additionalData: [AnyHashable : Any]?) { + public override func set(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?, _ additionalData: [AnyHashable: Any]?) { super.set(with: model, delegateObject, additionalData) + guard let model = model as? BGImageHeadlineBodyButtonModel else { return } + headlineBody.set(with: model.headlineBody, delegateObject, additionalData) button.setOptional(with: model.button, delegateObject, additionalData) button.isHidden = model.button == nil backgroundImageView.set(with: model.image, delegateObject, additionalData) backgroundImageView.pinEdges(.all) + updateAccessibilityLabel() + } + + //---------------------------------------------------- + // MARK: - Accessibility + //---------------------------------------------------- + + func updateAccessibilityLabel() { + + var message = "" + + if let headline = headlineBody.headlineLabel.text, !headline.isEmpty { + message += headline + ", " + } + + if let body = headlineBody.messageLabel.text, !body.isEmpty { + message += body + ", " + } + + if let backgroundImageText = backgroundImageView.accessibilityLabel, !backgroundImageText.isEmpty { + message += backgroundImageText + ", " + } + + if let buttonLabel = button.accessibilityLabel, !buttonLabel.isEmpty { + message += buttonLabel + } + + accessibilityLabel = message + } + + open override func accessibilityActivate() -> Bool { + + return button.accessibilityActivate() } } diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/BGImageHeadlineBodyButtonModel.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/BGImageHeadlineBodyButtonModel.swift index 040b368c..7c4215c2 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/BGImageHeadlineBodyButtonModel.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/BGImageHeadlineBodyButtonModel.swift @@ -6,42 +6,62 @@ // Copyright © 2020 Verizon Wireless. All rights reserved. // -import UIKit public class BGImageHeadlineBodyButtonModel: ContainerModel, MoleculeModelProtocol { + //-------------------------------------------------- + // MARK: - Properties + //-------------------------------------------------- + public static var identifier: String = "bgImageHeadlineBodyButton" public var backgroundColor: Color? public var button: ButtonModel? public var headlineBody: HeadlineBodyModel public var image: ImageViewModel + //-------------------------------------------------- + // MARK: - Initializer + //-------------------------------------------------- + init(headlineBody: HeadlineBodyModel, image: ImageViewModel) { self.headlineBody = headlineBody self.image = image super.init() } - /// Defaults to set + //-------------------------------------------------- + // MARK: - Defaults + //-------------------------------------------------- + public override func setDefaults() { + if useHorizontalMargins == nil { useHorizontalMargins = true } + if useVerticalMargins == nil { useVerticalMargins = true } + if topPadding == nil { topPadding = PaddingDefault } + if bottomPadding == nil { bottomPadding = PaddingDefault } + if image.height == nil { image.height = BGImageHeadlineBodyButton.heightConstant } + button?.size = .tiny button?.style = .secondary } + //-------------------------------------------------- + // MARK: - Keys + //-------------------------------------------------- + private enum CodingKeys: String, CodingKey { case moleculeName case backgroundColor @@ -49,7 +69,11 @@ public class BGImageHeadlineBodyButtonModel: ContainerModel, MoleculeModelProtoc case image case button } - + + //-------------------------------------------------- + // MARK: - Codec + //-------------------------------------------------- + required public init(from decoder: Decoder) throws { let typeContainer = try decoder.container(keyedBy: CodingKeys.self) backgroundColor = try typeContainer.decodeIfPresent(Color.self, forKey: .backgroundColor) @@ -58,7 +82,7 @@ public class BGImageHeadlineBodyButtonModel: ContainerModel, MoleculeModelProtoc button = try typeContainer.decodeIfPresent(ButtonModel.self, forKey: .button) try super.init(from: decoder) } - + public override func encode(to encoder: Encoder) throws { try super.encode(to: encoder) var container = encoder.container(keyedBy: CodingKeys.self) @@ -69,4 +93,3 @@ public class BGImageHeadlineBodyButtonModel: ContainerModel, MoleculeModelProtoc try container.encodeIfPresent(button, forKey: .button) } } - diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/EyebrowHeadlineBodyLink.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/EyebrowHeadlineBodyLink.swift index 12b42e9f..ca76f0fb 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/EyebrowHeadlineBodyLink.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/EyebrowHeadlineBodyLink.swift @@ -6,7 +6,6 @@ // Copyright © 2019 Verizon Wireless. All rights reserved. // -import UIKit @objcMembers open class EyebrowHeadlineBodyLink: View { //-------------------------------------------------- @@ -76,8 +75,9 @@ import UIKit /// Returns the labels text in one message. func getAccessibilityMessage() -> String? { + var message = "" - + if let eyebrowLabel = eyebrow.text { message += eyebrowLabel + ", " } @@ -89,24 +89,31 @@ import UIKit if let bodyLabel = body.text { message += bodyLabel } + return message.count > 0 ? message : nil } /// Returns an array of the appropriate accessibility elements. func getAccessibilityElements() -> [Any]? { + var elements: [UIView] = [] + if eyebrow.hasText { elements.append(eyebrow) } + if headline.hasText { elements.append(headline) } + if body.hasText { elements.append(body) } + if link.titleLabel?.text?.count ?? 0 > 0 { elements.append(link) } + return elements.count > 0 ? elements : nil } } diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/EyebrowHeadlineBodyLinkModel.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/EyebrowHeadlineBodyLinkModel.swift index 0f158c2c..c9410775 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/EyebrowHeadlineBodyLinkModel.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/EyebrowHeadlineBodyLinkModel.swift @@ -6,7 +6,6 @@ // Copyright © 2020 Verizon Wireless. All rights reserved. // -import Foundation public class EyebrowHeadlineBodyLinkModel: MoleculeModelProtocol { //-------------------------------------------------- diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadLineBodyCaretLinkImage.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadLineBodyCaretLinkImage.swift index 114fd3d4..9afc2263 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadLineBodyCaretLinkImage.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadLineBodyCaretLinkImage.swift @@ -6,77 +6,88 @@ // Copyright © 2020 Verizon Wireless. All rights reserved. // -import Foundation + @objcMembers public class HeadLineBodyCaretLinkImage: Container { - let headlineBody = HeadlineBody(frame: .zero) - let caretButton = CaretLink(frame: .zero) + //-------------------------------------------------- + // MARK: - Properties + //-------------------------------------------------- + + let headlineBody = HeadlineBody() + let caretButton = CaretLink() let backgroundImageView = LoadImageView(pinnedEdges: .all) - let maxWidth: CGFloat = 350.0 - static let heightConstant: CGFloat = 320.0 + + //-------------------------------------------------- + // MARK: - Constraints + //-------------------------------------------------- + + let maxWidth: CGFloat = 350 + static let heightConstant: CGFloat = 320 var heightConstraint: NSLayoutConstraint? - - // MARK: - MVMCoreViewProtocol - open override func updateView(_ size: CGFloat) { - super.updateView(size) - headlineBody.updateView(size) - caretButton.updateView(size) - backgroundImageView.updateView(size) - backgroundImageView.pinEdges(.all) - } - + + //-------------------------------------------------- + // MARK: - Setup + //-------------------------------------------------- + open override func setupView() { super.setupView() + heightConstraint = heightAnchor.constraint(equalToConstant: Self.heightConstant) heightConstraint?.isActive = true backgroundImageView.addSizeConstraintsForAspectRatio = true - + let container = MVMCoreUICommonViewsUtility.commonView() addAndContain(container) container.addSubview(headlineBody) container.addSubview(caretButton) - //Headline view headlineBody.leadingAnchor.constraint(equalTo: container.leadingAnchor, constant: 0).isActive = true headlineBody.topAnchor.constraint(equalTo: container.topAnchor, constant: 0).isActive = true - + headlineBody.widthAnchor.constraint(equalTo: container.widthAnchor, multiplier: 0.67).isActive = true let headLineBodyWidth = headlineBody.widthAnchor.constraint(lessThanOrEqualToConstant: maxWidth) headLineBodyWidth.priority = UILayoutPriority(250) headLineBodyWidth.isActive = true - //Caret view - caretButton.translatesAutoresizingMaskIntoConstraints = false caretButton.leadingAnchor.constraint(equalTo: container.leadingAnchor, constant: 0).isActive = true container.bottomAnchor.constraint(equalTo: caretButton.bottomAnchor, constant: 0).isActive = true - caretButton.topAnchor.constraint(greaterThanOrEqualTo: headlineBody.bottomAnchor, constant: PaddingTwo).isActive = true - //Background image view - backgroundImageView.translatesAutoresizingMaskIntoConstraints = false backgroundImageView.imageView.contentMode = .scaleAspectFill backgroundImageView.pinEdges(.all) addSubview(backgroundImageView) NSLayoutConstraint.constraintPinSubview(toSuperview: backgroundImageView) sendSubviewToBack(backgroundImageView) } - + + //-------------------------------------------------- // MARK: - MoleculeViewProtocol + //-------------------------------------------------- + + open override func updateView(_ size: CGFloat) { + super.updateView(size) + headlineBody.updateView(size) + caretButton.updateView(size) + backgroundImageView.updateView(size) + backgroundImageView.pinEdges(.all) + } + open override func reset() { super.reset() headlineBody.reset() backgroundImageView.reset() } - // MARK:- MoleculeViewProtocol public override class func estimatedHeight(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?) -> CGFloat? { return 320 } - public override func set(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?, _ additionalData: [AnyHashable : Any]?) { + public override func set(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?, _ additionalData: [AnyHashable: Any]?) { super.set(with: model, delegateObject, additionalData) + guard let model = model as? HeadlineBodyCaretLinkImageModel else { return } + headlineBody.set(with: model.headlineBody, delegateObject, additionalData) caretButton.setOptional(with: model.caretLink, delegateObject, additionalData) caretButton.isHidden = model.caretLink == nil diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBody.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBody.swift index 93b6fa68..48d6c129 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBody.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBody.swift @@ -6,12 +6,19 @@ // Copyright © 2019 Verizon Wireless. All rights reserved. // -import UIKit open class HeadlineBody: View { + //-------------------------------------------------- + // MARK: - Outlets + //-------------------------------------------------- let headlineLabel = Label(fontStyle: .BoldTitleLarge) let messageLabel = Label(fontStyle: .RegularBodySmall) + + //-------------------------------------------------- + // MARK: - Constraints + //-------------------------------------------------- + var spaceBetweenLabelsConstant = PaddingOne var spaceBetweenLabels: NSLayoutConstraint? var leftConstraintTitle: NSLayoutConstraint? @@ -19,21 +26,30 @@ open class HeadlineBody: View { var leftConstraintMessage: NSLayoutConstraint? var rightConstraintMessage: NSLayoutConstraint? + //-------------------------------------------------- + // MARK: - Methods + //-------------------------------------------------- + func hasText() -> Bool { return headlineLabel.hasText || messageLabel.hasText } // MARK: - Styling func style(with style: HeadlineBodyModel.Style?) { + switch style { case .landingHeader: styleLandingPageHeader() + case .header: stylePageHeader() + case .item: styleListItem() + case .itemHeader: styleListItemDivider() + default: break } } @@ -61,18 +77,14 @@ open class HeadlineBody: View { messageLabel.setFontStyle(.RegularBodySmall) spaceBetweenLabelsConstant = 0 } - - // MARK: - MVMCoreViewProtocol - open override func updateView(_ size: CGFloat) { - super.updateView(size) - headlineLabel.updateView(size) - messageLabel.updateView(size) - setSpacing() - } + + //-------------------------------------------------- + // MARK: - Setup + //-------------------------------------------------- open override func setupView() { super.setupView() - + backgroundColor = .clear clipsToBounds = true @@ -86,35 +98,35 @@ open class HeadlineBody: View { view.addSubview(headlineLabel) view.addSubview(messageLabel) - + headlineLabel.setContentHuggingPriority(.required, for: .vertical) messageLabel.setContentHuggingPriority(.required, for: .vertical) view.setContentHuggingPriority(.required, for: .vertical) - - headlineLabel.topAnchor.constraint(equalTo: view.topAnchor, constant: 0).isActive = true - + + headlineLabel.topAnchor.constraint(equalTo: view.topAnchor).isActive = true + spaceBetweenLabels = messageLabel.topAnchor.constraint(equalTo: headlineLabel.bottomAnchor, constant: spaceBetweenLabelsConstant) spaceBetweenLabels?.isActive = true - + leftConstraintTitle = headlineLabel.leftAnchor.constraint(equalTo: view.leftAnchor) leftConstraintTitle?.isActive = true - + rightConstraintTitle = view.rightAnchor.constraint(equalTo: headlineLabel.rightAnchor) rightConstraintTitle?.isActive = true - + leftConstraintMessage = messageLabel.leftAnchor.constraint(equalTo: view.leftAnchor) leftConstraintMessage?.isActive = true rightConstraintMessage = view.rightAnchor.constraint(equalTo: messageLabel.rightAnchor) rightConstraintMessage?.isActive = true - view.bottomAnchor.constraint(equalTo: messageLabel.bottomAnchor, constant: 0).isActive = true + view.bottomAnchor.constraint(equalTo: messageLabel.bottomAnchor).isActive = true } //-------------------------------------------------- // MARK: - Constraining //-------------------------------------------------- - + public func setSpacing() { if headlineLabel.hasText && messageLabel.hasText { spaceBetweenLabels?.constant = spaceBetweenLabelsConstant @@ -122,11 +134,18 @@ open class HeadlineBody: View { spaceBetweenLabels?.constant = 0 } } - + //-------------------------------------------------- // MARK: - MoleculeViewProtocol //-------------------------------------------------- + open override func updateView(_ size: CGFloat) { + super.updateView(size) + headlineLabel.updateView(size) + messageLabel.updateView(size) + setSpacing() + } + public override class func estimatedHeight(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?) -> CGFloat? { return 58 } @@ -135,7 +154,7 @@ open class HeadlineBody: View { super.set(with: model, delegateObject, additionalData) guard let headlineBodyModel = model as? HeadlineBodyModel else { return } - + style(with: headlineBodyModel.style) headlineLabel.setOptional(with: headlineBodyModel.headline, delegateObject, additionalData) diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyButton.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyButton.swift index 5170d8f2..8e22a1df 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyButton.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyButton.swift @@ -6,8 +6,6 @@ // Copyright © 2019 Verizon Wireless. All rights reserved. // -import UIKit - @objcMembers open class HeadlineBodyButton: View { //------------------------------------------------------ diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyButtonModel.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyButtonModel.swift index cd1912ca..cff8be23 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyButtonModel.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyButtonModel.swift @@ -6,8 +6,6 @@ // Copyright © 2020 Verizon Wireless. All rights reserved. // -import Foundation - public class HeadlineBodyButtonModel: MoleculeModelProtocol { //-------------------------------------------------- @@ -17,7 +15,7 @@ public class HeadlineBodyButtonModel: MoleculeModelProtocol { public static var identifier: String = "headlineBodyButton" public var moleculeName: String = HeadlineBodyButtonModel.identifier public var backgroundColor: Color? - + public var headlineBody: HeadlineBodyModel public var button: ButtonModel public var buttonHeadlinePadding: CGFloat diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyCaretLinkImageModel.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyCaretLinkImageModel.swift index 9fdd8612..2a3d844a 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyCaretLinkImageModel.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyCaretLinkImageModel.swift @@ -6,40 +6,60 @@ // Copyright © 2020 Verizon Wireless. All rights reserved. // -import UIKit public class HeadlineBodyCaretLinkImageModel: ContainerModel, MoleculeModelProtocol { + //-------------------------------------------------- + // MARK: - Properties + //-------------------------------------------------- + public static var identifier: String = "headlineBodyCaretLinkImage" public var backgroundColor: Color? public var caretLink: CaretLinkModel? public var headlineBody: HeadlineBodyModel public var image: ImageViewModel + //-------------------------------------------------- + // MARK: - Initializer + //-------------------------------------------------- + init(headlineBody: HeadlineBodyModel, image: ImageViewModel) { self.headlineBody = headlineBody self.image = image super.init() } + //-------------------------------------------------- + // MARK: - Defaults + //-------------------------------------------------- + /// Defaults to set public override func setDefaults() { + if useHorizontalMargins == nil { useHorizontalMargins = true } + if useVerticalMargins == nil { useVerticalMargins = true } + if topPadding == nil { topPadding = PaddingDefault } + if bottomPadding == nil { bottomPadding = PaddingDefault } + if image.height == nil { image.height = HeadLineBodyCaretLinkImage.heightConstant } } + //-------------------------------------------------- + // MARK: - Keys + //-------------------------------------------------- + private enum CodingKeys: String, CodingKey { case moleculeName case backgroundColor @@ -47,7 +67,11 @@ public class HeadlineBodyCaretLinkImageModel: ContainerModel, MoleculeModelProto case image case caretLink } - + + //-------------------------------------------------- + // MARK: - Codec + //-------------------------------------------------- + required public init(from decoder: Decoder) throws { let typeContainer = try decoder.container(keyedBy: CodingKeys.self) backgroundColor = try typeContainer.decodeIfPresent(Color.self, forKey: .backgroundColor) @@ -56,7 +80,7 @@ public class HeadlineBodyCaretLinkImageModel: ContainerModel, MoleculeModelProto caretLink = try typeContainer.decodeIfPresent(CaretLinkModel.self, forKey: .caretLink) try super.init(from: decoder) } - + public override func encode(to encoder: Encoder) throws { try super.encode(to: encoder) var container = encoder.container(keyedBy: CodingKeys.self) diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyLink.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyLink.swift index da5014a9..550434a8 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyLink.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyLink.swift @@ -6,33 +6,41 @@ // Copyright © 2019 Verizon Wireless. All rights reserved. // -import UIKit @objcMembers public class HeadlineBodyLink: View { - - let headlineBody = HeadlineBody(frame: .zero) + //-------------------------------------------------- + // MARK: - Outlets + //-------------------------------------------------- + + let headlineBody = HeadlineBody() let link = Link() - var spaceBetweenConstant: CGFloat = 0.0 + + //-------------------------------------------------- + // MARK: - Properties + //-------------------------------------------------- + + var spaceBetweenConstant: CGFloat = 0 + + //-------------------------------------------------- + // MARK: - Constraints + //-------------------------------------------------- + var spaceBetween: NSLayoutConstraint? - // MARK: - MVMCoreViewProtocol - open override func updateView(_ size: CGFloat) { - super.updateView(size) - headlineBody.updateView(size) - link.updateView(size) - setSpacing() - } + //-------------------------------------------------- + // MARK: - Setup + //-------------------------------------------------- open override func setupView() { super.setupView() - guard subviews.count == 0 else { - return - } + + guard subviews.isEmpty else { return } + addSubview(headlineBody) addSubview(link) headlineBody.styleListItem() - headlineBody.topAnchor.constraint(equalTo: topAnchor, constant: 0).isActive = true + headlineBody.topAnchor.constraint(equalTo: topAnchor).isActive = true headlineBody.leftAnchor.constraint(equalTo: leftAnchor).isActive = true var constraint = rightAnchor.constraint(equalTo: headlineBody.rightAnchor) constraint.priority = .defaultHigh @@ -49,7 +57,10 @@ import UIKit constraint.isActive = true } - // MARK: - Constraining + //-------------------------------------------------- + // MARK: - Methods + //-------------------------------------------------- + public func setSpacing() { if headlineBody.hasText() && (link.titleLabel?.text?.count ?? 0) > 0 { spaceBetween?.constant = spaceBetweenConstant @@ -58,7 +69,17 @@ import UIKit } } - // MARK: - MoleculeViewProtocol + //-------------------------------------------------- + // MARK: - MVMCoreViewProtocol + //-------------------------------------------------- + + open override func updateView(_ size: CGFloat) { + super.updateView(size) + headlineBody.updateView(size) + link.updateView(size) + setSpacing() + } + open override func reset() { super.reset() headlineBody.reset() @@ -66,7 +87,6 @@ import UIKit link.reset() } - // MARK:- MoleculeViewProtocol open override func set(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?, _ additionalData: [AnyHashable: Any]?) { super.set(with: model, delegateObject, additionalData) guard let model = model as? HeadlineBodyLinkModel else { return } diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyLinkModel.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyLinkModel.swift index 4ef4018b..f8a0d57e 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyLinkModel.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/HeadlineBodyLinkModel.swift @@ -8,13 +8,22 @@ import Foundation + public struct HeadlineBodyLinkModel: MoleculeModelProtocol { + //-------------------------------------------------- + // MARK: - Properties + //-------------------------------------------------- + public static var identifier: String = "headlineBodyLink" public var moleculeName: String = HeadlineBodyLinkModel.identifier public var headlineBody: HeadlineBodyModel public var link: LinkModel public var backgroundColor: Color? - + + //-------------------------------------------------- + // MARK: - Initializer + //-------------------------------------------------- + public init(headlineBody: HeadlineBodyModel, link: LinkModel) { self.headlineBody = headlineBody self.link = link diff --git a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/ThreeHeadlineBodyLink.swift b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/ThreeHeadlineBodyLink.swift index 5926951f..a34107b9 100644 --- a/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/ThreeHeadlineBodyLink.swift +++ b/MVMCoreUI/Atomic/Molecules/VerticalCombinationViews/ThreeHeadlineBodyLink.swift @@ -6,8 +6,6 @@ // Copyright © 2020 Verizon Wireless. All rights reserved. // -import UIKit - open class ThreeHeadlineBodyLink: View { //------------------------------------------------------- diff --git a/MVMCoreUI/Atomic/Organisms/Stack.swift b/MVMCoreUI/Atomic/Organisms/Stack.swift index ad961586..5957f4c9 100644 --- a/MVMCoreUI/Atomic/Organisms/Stack.swift +++ b/MVMCoreUI/Atomic/Organisms/Stack.swift @@ -66,11 +66,12 @@ open class Stack: Container where T: (StackModelProtocol & MoleculeModelProto open func updateContainedMolecules(with models: [MoleculeModelProtocol?], _ delegateObject: MVMCoreUIDelegateObject?, _ additionalData: [AnyHashable: Any]?) { guard var stackModel = stackModel else { return } var needsRestack = false + for (index, item) in stackItems.enumerated() { guard let container = item as? UIView & ContainerProtocol, - let contained = container.view as? MoleculeViewProtocol else { - continue - } + let contained = container.view as? MoleculeViewProtocol + else { continue } + if let model = models[index] { contained.set(with: model, delegateObject, additionalData) if stackModel.molecules[index].gone {