diff --git a/MVMCoreUI.xcodeproj/project.pbxproj b/MVMCoreUI.xcodeproj/project.pbxproj index 8218a76f..d7afb970 100644 --- a/MVMCoreUI.xcodeproj/project.pbxproj +++ b/MVMCoreUI.xcodeproj/project.pbxproj @@ -197,6 +197,8 @@ AA85236C244435A20059CC1E /* RadioSwatchCollectionViewCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = AA85236B244435A20059CC1E /* RadioSwatchCollectionViewCell.swift */; }; AAA74A172410C04600080241 /* HeadersH2NoButtonsBodyText.swift in Sources */ = {isa = PBXBuildFile; fileRef = AAA74A162410C04600080241 /* HeadersH2NoButtonsBodyText.swift */; }; AAA74A192410C05800080241 /* HeadersH2NoButtonsBodyTextModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = AAA74A182410C05800080241 /* HeadersH2NoButtonsBodyTextModel.swift */; }; + AAB7EDEF246ADA1600E54929 /* ListProgressBarThinModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = AAB7EDEE246ADA1600E54929 /* ListProgressBarThinModel.swift */; }; + AAB7EDF1246ADA2A00E54929 /* ListProgressBarThin.swift in Sources */ = {isa = PBXBuildFile; fileRef = AAB7EDF0246ADA2A00E54929 /* ListProgressBarThin.swift */; }; AAB9C10824346F4B00151545 /* RadioSwatches.swift in Sources */ = {isa = PBXBuildFile; fileRef = AAB9C10724346F4B00151545 /* RadioSwatches.swift */; }; AAB9C10A243496DD00151545 /* RadioSwatch.swift in Sources */ = {isa = PBXBuildFile; fileRef = AAB9C109243496DD00151545 /* RadioSwatch.swift */; }; AAC6F167243332E400F295C1 /* RadioSwatchesModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = AAC6F166243332E400F295C1 /* RadioSwatchesModel.swift */; }; @@ -609,6 +611,8 @@ AA85236B244435A20059CC1E /* RadioSwatchCollectionViewCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RadioSwatchCollectionViewCell.swift; sourceTree = ""; }; AAA74A162410C04600080241 /* HeadersH2NoButtonsBodyText.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HeadersH2NoButtonsBodyText.swift; sourceTree = ""; }; AAA74A182410C05800080241 /* HeadersH2NoButtonsBodyTextModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HeadersH2NoButtonsBodyTextModel.swift; sourceTree = ""; }; + AAB7EDEE246ADA1600E54929 /* ListProgressBarThinModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ListProgressBarThinModel.swift; sourceTree = ""; }; + AAB7EDF0246ADA2A00E54929 /* ListProgressBarThin.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ListProgressBarThin.swift; sourceTree = ""; }; AAB9C10724346F4B00151545 /* RadioSwatches.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RadioSwatches.swift; sourceTree = ""; }; AAB9C109243496DD00151545 /* RadioSwatch.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RadioSwatch.swift; sourceTree = ""; }; AAC6F166243332E400F295C1 /* RadioSwatchesModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RadioSwatchesModel.swift; sourceTree = ""; }; @@ -1244,6 +1248,8 @@ D20492F12434CB5F00A5EED6 /* FourColumn */, AA4FC2A323F4F69600E251DB /* RightVariable */, D22B38EB23F4E0AE00490EF6 /* LeftVariable */, + AAB7EDEE246ADA1600E54929 /* ListProgressBarThinModel.swift */, + AAB7EDF0246ADA2A00E54929 /* ListProgressBarThin.swift */, ); path = List; sourceTree = ""; @@ -2181,6 +2187,7 @@ C695A68123C9830D00BFB94E /* NumberedListModel.swift in Sources */, 01EB3684236097C0006832FA /* MoleculeModelProtocol.swift in Sources */, D27CD4102339057800C1DC07 /* EyebrowHeadlineBodyLink.swift in Sources */, + AAB7EDF1246ADA2A00E54929 /* ListProgressBarThin.swift in Sources */, 8D070BB2241B56AD0099AC56 /* ListRightVariableTotalData.swift in Sources */, D264FAA5243F66A500D98315 /* CollectionTemplateItemProtocol.swift in Sources */, D29DF11D21E684A9003B2FB9 /* MVMCoreUISplitViewController.m in Sources */, @@ -2268,6 +2275,7 @@ EA5124FD243601600051A3A4 /* BGImageHeadlineBodyButton.swift in Sources */, 0105618D224BBE7700E1557D /* FormValidator.swift in Sources */, 01509D912327ECE600EF99AA /* CornerLabels.swift in Sources */, + AAB7EDEF246ADA1600E54929 /* ListProgressBarThinModel.swift in Sources */, D21B7F75243BAC8900051ABF /* CarouselItem.swift in Sources */, C695A69823C990C200BFB94E /* DoughnutChartView.swift in Sources */, 8D3BA9BD2433787000D341BA /* ListThreeColumnInternationalDataDividerModel.swift in Sources */, diff --git a/MVMCoreUI/Atomic/MoleculeObjectMapping.swift b/MVMCoreUI/Atomic/MoleculeObjectMapping.swift index 4b3119f2..76c17c6a 100644 --- a/MVMCoreUI/Atomic/MoleculeObjectMapping.swift +++ b/MVMCoreUI/Atomic/MoleculeObjectMapping.swift @@ -162,6 +162,7 @@ import Foundation MoleculeObjectMapping.shared()?.register(viewClass: ListThreeColumnInternationalData.self, viewModelClass: ListThreeColumnInternationalDataModel.self) MoleculeObjectMapping.shared()?.register(viewClass: ListThreeColumnDataUsage.self, viewModelClass: ListThreeColumnDataUsageModel.self) MoleculeObjectMapping.shared()?.register(viewClass: ListFourColumnDataUsageListItem.self, viewModelClass: ListFourColumnDataUsageListItemModel.self) + MoleculeObjectMapping.shared()?.register(viewClass: ListProgressBarThin.self, viewModelClass: ListProgressBarThinModel.self) // Designed Section Dividers MoleculeObjectMapping.shared()?.register(viewClass: ListFourColumnDataUsageDivider.self, viewModelClass: ListFourColumnDataUsageDividerModel.self) diff --git a/MVMCoreUI/Atomic/Molecules/DesignedComponents/List/ListProgressBarThin.swift b/MVMCoreUI/Atomic/Molecules/DesignedComponents/List/ListProgressBarThin.swift new file mode 100644 index 00000000..072be6bb --- /dev/null +++ b/MVMCoreUI/Atomic/Molecules/DesignedComponents/List/ListProgressBarThin.swift @@ -0,0 +1,99 @@ +// +// ListProgressBarThin.swift +// MVMCoreUI +// +// Created by Lekshmi S on 12/05/20. +// Copyright © 2020 Verizon Wireless. All rights reserved. +// + +import Foundation +@objcMembers open class ListProgressBarThin: TableViewCell { + //-------------------------------------------------- + // MARK: - Outlets + //-------------------------------------------------- + public let progressBar = ProgressBar() + public let leftHeadline = Label.commonLabelB1(true) + public let leftBody = Label.commonLabelB2(true) + public let rightBar = Line() + public let rightLabel = Label.commonLabelB2(true) + private let barStackItem: StackItem + private let rightLabelStackItem: StackItem + public var labelStack: Stack + public var horizontalStack: Stack + public var stack: Stack + + //------------------------------------------------------ + // MARK: - Initializers + //------------------------------------------------------ + public override init(style: UITableViewCell.CellStyle, reuseIdentifier: String?) { + //vertical stack with leftHeadline, leftBody + labelStack = Stack.createStack(with: [leftHeadline, leftBody], axis: .vertical, spacing: 2) + + //horizontal stack with leftHeadline, leftBody, bar, rightLabel + barStackItem = StackItem(andContain: rightBar) + rightLabelStackItem = StackItem(andContain: rightLabel) + let horizontalStackItems = [StackItem(andContain: labelStack), barStackItem, rightLabelStackItem] + let horizontalStackModel = StackModel(molecules: [StackItemModel(horizontalAlignment: .leading), StackItemModel(horizontalAlignment: .fill), StackItemModel(spacing: 5, horizontalAlignment: .fill)], + axis: .horizontal) + horizontalStack = Stack(with: horizontalStackModel, stackItems: horizontalStackItems) + + //stack with all components + stack = Stack.createStack(with: [horizontalStack, progressBar], axis: .vertical, spacing: PaddingDefaultVerticalSpacing3) + super.init(style: style, reuseIdentifier: reuseIdentifier) + } + + public required init?(coder aDecoder: NSCoder) { + fatalError("init(coder:) has not been implemented") + } + + open override func alignAccessoryToHero() -> CGPoint? { + // Ensures that the right items are centered with the arrow. + let heroCenter = super.alignAccessoryToHero() + if let heroCenter = heroCenter { + let convertedPoint = horizontalStack.convert(heroCenter, from: self) + barStackItem.containerHelper.alignCenterVerticalConstraint?.constant = convertedPoint.y - horizontalStack.bounds.midY + rightLabelStackItem.containerHelper.alignCenterVerticalConstraint?.constant = convertedPoint.y - horizontalStack.bounds.midY + } + return heroCenter + } + + //------------------------------------------------------- + // MARK: - View Lifecycle + //------------------------------------------------------- + open override func setupView() { + super.setupView() + rightBar.widthAnchor.constraint(equalToConstant: 20).isActive = true + rightLabel.setContentCompressionResistancePriority(UILayoutPriority(rawValue: 900), for: .horizontal) + rightLabel.setContentHuggingPriority(UILayoutPriority(rawValue: 900), for: .horizontal) + rightLabel.numberOfLines = 1 + addMolecule(stack) + stack.restack() + horizontalStack.restack() + labelStack.restack() + } + + //------------------------------------------------------ + // MARK: - Molecule + //------------------------------------------------------ + open override func set(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?, _ additionalData: [AnyHashable : Any]?) { + super.set(with: model, delegateObject, additionalData) + guard let model = model as? ListProgressBarThinModel else { return } + labelStack.updateContainedMolecules(with: [model.leftHeadline, + model.leftBody], delegateObject, additionalData) + progressBar.set(with: model.progressBar, delegateObject, additionalData) + rightBar.set(with: model.rightBar, delegateObject, additionalData) + rightLabel.set(with: model.rightLabel, delegateObject, additionalData) + } + + open override class func estimatedHeight(with model: MoleculeModelProtocol, _ delegateObject: MVMCoreUIDelegateObject?) -> CGFloat { + return 120 + } + + open override func reset() { + super.reset() + leftHeadline.styleB1(true) + leftBody.styleB2(true) + rightLabel.styleB2(true) + rightBar.setStyle(.medium) + } +} diff --git a/MVMCoreUI/Atomic/Molecules/DesignedComponents/List/ListProgressBarThinModel.swift b/MVMCoreUI/Atomic/Molecules/DesignedComponents/List/ListProgressBarThinModel.swift new file mode 100644 index 00000000..acd8e013 --- /dev/null +++ b/MVMCoreUI/Atomic/Molecules/DesignedComponents/List/ListProgressBarThinModel.swift @@ -0,0 +1,65 @@ +// +// ListProgressBarThinModel.swift +// MVMCoreUI +// +// Created by Lekshmi S on 12/05/20. +// Copyright © 2020 Verizon Wireless. All rights reserved. +// + +import Foundation +public class ListProgressBarThinModel: ListItemModel, MoleculeModelProtocol { + public static var identifier = "listPrgBarThin" + public var progressBar: ProgressBarModel + public var leftHeadline: LabelModel + public var leftBody: LabelModel? + public var rightBar: LineModel + public var rightLabel: LabelModel + + public init(progressBar: ProgressBarModel, leftHeadline: LabelModel, leftBody: LabelModel? = nil, rightBar: LineModel, rightLabel: LabelModel) { + self.progressBar = progressBar + self.leftHeadline = leftHeadline + self.leftBody = leftBody + self.rightBar = rightBar + self.rightLabel = rightLabel + super.init() + } + + override public func setDefaults() { + super.setDefaults() + rightBar.type = .medium + if rightBar.backgroundColor == nil { + rightBar.backgroundColor = Color(uiColor: .gray) + } + leftHeadline.hero = 0 + } + + private enum CodingKeys: String, CodingKey { + case moleculeName + case progressBar + case leftHeadline + case leftBody + case rightBar + case rightLabel + } + + public required init(from decoder: Decoder) throws { + let typeContainer = try decoder.container(keyedBy: CodingKeys.self) + progressBar = try typeContainer.decode(ProgressBarModel.self, forKey:.progressBar) + leftHeadline = try typeContainer.decode(LabelModel.self, forKey: .leftHeadline) + leftBody = try typeContainer.decodeIfPresent(LabelModel.self, forKey: .leftBody) + rightBar = try typeContainer.decode(LineModel.self, forKey: .rightBar) + rightLabel = try typeContainer.decode(LabelModel.self, forKey: .rightLabel) + 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) + try container.encode(moleculeName, forKey: .moleculeName) + try container.encode(progressBar, forKey: .progressBar) + try container.encode(leftHeadline, forKey: .leftHeadline) + try container.encodeIfPresent(leftBody, forKey: .leftBody) + try container.encode(rightBar, forKey: .rightBar) + try container.encode(rightLabel, forKey: .rightLabel) + } +}