From 46b11c2585ac1abe4df7c17f35390f845c359c00 Mon Sep 17 00:00:00 2001 From: Vasavi Kanamarlapudi Date: Wed, 31 Jul 2024 14:52:02 +0530 Subject: [PATCH] Digital ACT-191 ONEAPP-9311 story: refactored code and resolved constraint issues --- .../InputStepper/InputStepper.swift | 90 +++++++++++-------- 1 file changed, 51 insertions(+), 39 deletions(-) diff --git a/VDS/Components/InputStepper/InputStepper.swift b/VDS/Components/InputStepper/InputStepper.swift index 63288e96..37c82a88 100644 --- a/VDS/Components/InputStepper/InputStepper.swift +++ b/VDS/Components/InputStepper/InputStepper.swift @@ -37,21 +37,33 @@ open class InputStepper: EntryFieldBase { case large, small } + /// Enum used to describe the width of a fixed value or percentage of the input stepper control. + public enum ControlWidth { + case percentage(CGFloat) + case value(CGFloat) + } + //-------------------------------------------------- // MARK: - Public Properties //-------------------------------------------------- - /// Accepts a string or number value to control the width of input stepper. - /// auto(default) - The control's width is determined by the combined width of the value, trailing text and padding - /// Value - The control's width can be set to a fixed pixel. - open var controlWidth: String? = "auto" { didSet { setNeedsUpdate() } } - - /// Accepts percentage value to controlWidth of input stepper. - open var controlWidthPercentage: CGFloat? { - didSet { - if let percentage = controlWidthPercentage, percentage > 100 { - controlWidthPercentage = 100 + /// If there is a width that is larger than this size's minimumWidth, the input stepper will resize to this width. + open var controlWidth: ControlWidth? { + get { _controlWidth } + set { + if let newValue { + switch newValue { + case .percentage(let percentage): + if percentage <= 100.0 { + _controlWidth = newValue + } + case .value(let value): + if value > 0 && value > containerSize.width { + _controlWidth = newValue + } + } + } else { + _controlWidth = nil } - updateControlWidthPercentage() setNeedsUpdate() } } @@ -62,7 +74,6 @@ open class InputStepper: EntryFieldBase { if let percentage = widthPercentage, percentage > 100 { widthPercentage = 100 } - updatePercentageWidth() setNeedsUpdate() } } @@ -109,6 +120,8 @@ open class InputStepper: EntryFieldBase { //-------------------------------------------------- // MARK: - Private Properties //-------------------------------------------------- + private var _controlWidth: ControlWidth? = nil + /// Default Int value of the input stepper, defaults to '0'. internal var defaultIntValue: Int { guard let intValue = defaultValue as? Int else { return 0 } @@ -236,8 +249,8 @@ open class InputStepper: EntryFieldBase { updateButtonStates() // Update stepper container border and corner radius. - setControlWidth(controlWidth) - updateControlWidthPercentage() + updateContainerWidthWithPercentage() + updateInputStepperWidth() updateStepperView() setNeedsLayout() } @@ -271,8 +284,7 @@ open class InputStepper: EntryFieldBase { super.reset() textLabel.reset() textLabel.textStyle = .boldBodyLarge - controlWidth = "auto" - controlWidthPercentage = nil + controlWidth = nil widthPercentage = nil id = nil minValue = 0 @@ -286,6 +298,7 @@ open class InputStepper: EntryFieldBase { // MARK: - Overrides //-------------------------------------------------- internal override func updateContainerWidth() { + stepperWidthConstraint?.deactivate() widthConstraint?.deactivate() trailingLessThanEqualsConstraint?.deactivate() trailingEqualsConstraint?.deactivate() @@ -361,17 +374,25 @@ open class InputStepper: EntryFieldBase { } // Set control width to input stepper. - private func setControlWidth(_ text: String?) { - if let text, text == "auto" { - stepperWidthConstraint?.deactivate() - } else if let controlWidth = Int(text ?? "") { - // Set controlWidth provided which is either pixel or percentage - let width = width ?? CGFloat(containerView.frame.size.width) - updateStepperContainerWidth(controlWidth: CGFloat(controlWidth), width: width) + private func updateInputStepperWidth() { + guard let controlWidth else { + return + } + + switch controlWidth { + case .percentage(let percentage): + // Set the inputStepper's controlWidth based on percentage received relative to its parentView's frame. + let superWidth = width ?? CGFloat(containerView.frame.size.width) + let value = max(superWidth * ((percentage) / 100), minWidth) + updateStepperContainerWidth(controlWidth: value, width: superWidth) + + case .value(let value): + let superWidth = width ?? CGFloat(containerView.frame.size.width) + updateStepperContainerWidth(controlWidth: value, width: superWidth) } } - // Handling the controlwidth without going beyond the width of the parent container. + // Handling the controlwidth without exceeding the width of the parent container. private func updateStepperContainerWidth(controlWidth: CGFloat, width: CGFloat) { if controlWidth >= containerSize.width && controlWidth <= width { stepperWidthConstraint?.deactivate() @@ -384,30 +405,21 @@ open class InputStepper: EntryFieldBase { } } - private func updateControlWidthPercentage() { - let superWidth = width ?? CGFloat(containerView.frame.size.width) - - // Set the inputStepper's controlWidth based on the controlWidth percentage received relative to its parentView's frame. - if let controlWidthPercentage { - controlWidth = String( Int( max(superWidth * ((controlWidthPercentage) / 100), minWidth))) - setControlWidth(controlWidth) - } - } - - private func updatePercentageWidth() { + // Update the container view width based on the percentage received. + private func updateContainerWidthWithPercentage() { guard let superWidth = superview?.frame.width else { return } // Set width of Parent container based on width perecentage received relative to its superview frame. if let widthPercentage { - width = max(superWidth * ((widthPercentage) / 100), minWidth) - if controlWidthPercentage != nil { - updateControlWidthPercentage() - } + // test value vs minimum width and take the greater value + width = max(superWidth * (widthPercentage / 100), minWidth) + updateContainerWidth() } } + // Add border and update constratints to stepper view. private func updateStepperView() { fieldStackView.removeConstraints() fieldStackView.pinTop().pinLeading().pinBottom().pinTrailingLessThanOrEqualTo()