refactoring for validation based on group

This commit is contained in:
Suresh, Kamlesh 2019-08-30 15:33:05 -04:00
parent 6b71115eb0
commit 062edc5d41
11 changed files with 124 additions and 52 deletions

View File

@ -17,9 +17,10 @@
@import MVMCore.MVMCoreGetterUtility; @import MVMCore.MVMCoreGetterUtility;
@import MVMCore.NSDictionary_MFConvenience; @import MVMCore.NSDictionary_MFConvenience;
@interface PrimaryButton() <FormValidationProtocol> @interface PrimaryButton() <FormValidationEnableDisableProtocol>
@property (nonatomic) BOOL validationRequired; @property (nonatomic) BOOL validationRequired;
@property (nonatomic, strong) NSArray *requiredFieldsList;
@property (nonatomic) BOOL smallButton; @property (nonatomic) BOOL smallButton;
@property (assign, nonatomic) BOOL tinyButton; @property (assign, nonatomic) BOOL tinyButton;
@property (nonatomic) CGFloat sizeForSizing; @property (nonatomic) CGFloat sizeForSizing;
@ -697,6 +698,7 @@
self.disabledBorderColor = [UIColor mfGetColorForHex:color]; self.disabledBorderColor = [UIColor mfGetColorForHex:color];
} }
self.validationRequired = [json boolForKey:@"validationRequired"]; self.validationRequired = [json boolForKey:@"validationRequired"];
self.requiredFieldsList = [json array:@"requiredFields"];
NSString *size = [json string:@"size"]; NSString *size = [json string:@"size"];
if ([size isEqualToString:@"small"]) { if ([size isEqualToString:@"small"]) {
@ -773,7 +775,11 @@
} }
} }
#pragma mark - FormValidationProtocol #pragma mark - FormValidationEnableDisableProtocol
- (NSArray<NSString *> *)requiredFields {
return self.requiredFieldsList;
}
- (void)enableField:(BOOL)enable { - (void)enableField:(BOOL)enable {
if (!self.validationRequired) { if (!self.validationRequired) {

View File

@ -43,9 +43,10 @@
@property (nonatomic,getter=isEnabled) BOOL enabled; @property (nonatomic,getter=isEnabled) BOOL enabled;
// To set the placeholder and text // To set the placeholder and text
@property (nullable, weak, nonatomic) NSString *text; @property (nullable, strong, nonatomic) NSString *text;
@property (nullable, weak, nonatomic) NSString *formText; @property (nullable, strong, nonatomic) NSString *formText;
@property (nullable, weak, nonatomic) NSString *fieldKey; @property (nullable, strong, nonatomic) NSString *fieldKey;
@property (nullable, strong, nonatomic) NSString *groupName;
@property (nullable, weak, nonatomic) NSString *placeholder; // will move out in Feb release @property (nullable, weak, nonatomic) NSString *placeholder; // will move out in Feb release

View File

@ -18,7 +18,7 @@
@import MVMCore.NSDictionary_MFConvenience; @import MVMCore.NSDictionary_MFConvenience;
@import MVMCore.MVMCoreJSONConstants; @import MVMCore.MVMCoreJSONConstants;
@interface MFTextField() <FormValidationProtocol> @interface MFTextField() <FormValidationFormFieldProtocol>
@property (strong, nonatomic) UIColor *customPlaceHolderColor; @property (strong, nonatomic) UIColor *customPlaceHolderColor;
@property (weak, nonatomic) IBOutlet NSLayoutConstraint *separatorHeightConstraint; @property (weak, nonatomic) IBOutlet NSLayoutConstraint *separatorHeightConstraint;
@ -303,28 +303,20 @@
return; return;
} }
NSString *string = [map string:KeyLabel]; self.formText = [map string:KeyLabel];;
if (string.length > 0) { self.groupName = [map string:@"groupName"];
self.formText = string; self.errMessage = [map string:KeyErrorMessage];
} self.fieldKey = [map string:KeyFieldKey];
string = [map string:KeyValue];
if (string.length > 0) { NSString *string = [map stringForKey:KeyValue];
if (string.length) {
self.text = string; self.text = string;
} }
string = [map stringForKey:KeyDisable]; string = [map stringForKey:KeyDisable];
if ([string isEqual:StringY] || [map boolForKey:KeyDisable]) { if ([string isEqual:StringY] || [map boolForKey:KeyDisable]) {
[self enable:NO]; [self enable:NO];
} }
string = [map string:KeyErrorMessage];
if (string.length > 0) {
self.errMessage = string;
}
// key used to send text value to server
string = [map string:KeyFieldKey];
if (string.length > 0) {
self.fieldKey = string;
}
string = [map string:KeyType]; string = [map string:KeyType];
if ([string isEqualToString:@"dropDown"]) { if ([string isEqualToString:@"dropDown"]) {
@ -588,5 +580,9 @@
- (nullable id)formFieldValue { - (nullable id)formFieldValue {
return self.text; return self.text;
} }
- (NSString * _Nullable)formFieldGroupName {
return self.groupName;
}
@end @end

View File

@ -21,7 +21,7 @@
static const CGFloat FaultTolerance = 20.f; static const CGFloat FaultTolerance = 20.f;
static const CGFloat CheckBoxHeightWidth = 18.0; static const CGFloat CheckBoxHeightWidth = 18.0;
@interface MVMCoreUICheckBox () <FormValidationProtocol, MVMCoreUIMoleculeViewProtocol> @interface MVMCoreUICheckBox () <FormValidationFormFieldProtocol, MVMCoreUIMoleculeViewProtocol>
@property (nonatomic, readwrite) BOOL isSelected; @property (nonatomic, readwrite) BOOL isSelected;
@property (weak, nonatomic) UIView *checkedSquare; @property (weak, nonatomic) UIView *checkedSquare;

View File

@ -12,16 +12,26 @@ import Foundation
// Getter method to get the FormValidator form the delegate (Mostly from the parent View Controller) // Getter method to get the FormValidator form the delegate (Mostly from the parent View Controller)
@objc optional func formValidatorModel() -> FormValidator? @objc optional func formValidatorModel() -> FormValidator?
}
@objc public protocol FormValidationFormFieldProtocol: FormValidationProtocol {
// Used to check the validity of the field, to enable/disable the primary button. // Used to check the validity of the field, to enable/disable the primary button.
@objc optional func isValidField() -> Bool @objc func isValidField() -> Bool
// The Field name key value pair for sending to server
@objc func formFieldName() -> String?
// Returns the group name for validation
@objc func formFieldGroupName() -> String?
// The Field value key value pair for sending to server
@objc func formFieldValue() -> Any?
}
@objc public protocol FormValidationEnableDisableProtocol: FormValidationProtocol {
// Based on the isValidField(), the fields which needs to be enabled can call this method // Based on the isValidField(), the fields which needs to be enabled can call this method
@objc optional func enableField(_ enable: Bool) @objc optional func enableField(_ enable: Bool)
// The Field name key value pair for sending to server // Returns the list of field keys required to enable/disable
@objc optional func formFieldName() -> String? @objc optional func requiredFields() -> [String]?
// The Field value key value pair for sending to server
@objc optional func formFieldValue() -> Any?
} }

View File

@ -16,9 +16,9 @@ import Foundation
@objc func getFormParams() -> [String: Any] { @objc func getFormParams() -> [String: Any] {
var extraParam: [String: Any] = [:] var extraParam: [String: Any] = [:]
MVMCoreDispatchUtility.performSyncBlock(onMainThread: { MVMCoreDispatchUtility.performSyncBlock(onMainThread: {
for molecule in self.molecules { for molecule in self.fieldMolecules {
if let formFieldName = molecule.formFieldName?(), if let formFieldName = molecule.formFieldName(),
let formFieldValue = molecule.formFieldValue?() { let formFieldValue = molecule.formFieldValue() {
extraParam[formFieldName] = formFieldValue extraParam[formFieldName] = formFieldValue
} }
} }

View File

@ -8,16 +8,22 @@
import Foundation import Foundation
import UIKit import UIKit
import MVMCore
@objcMembers public class FormValidator: NSObject { @objcMembers public class FormValidator: NSObject {
var delegate: FormValidationProtocol? var delegate: FormValidationProtocol?
var molecules: [FormValidationProtocol] = [] var fieldMolecules: [FormValidationFormFieldProtocol] = []
var extraValidationBlock: (() -> Bool)? var enableDisableMolecules: [FormValidationEnableDisableProtocol] = []
var radioButtonsModelByGroup: [String: RadioButtonModel] = [:] var radioButtonsModelByGroup: [String: RadioButtonModel] = [:]
public func insertMolecule(_ molecule: FormValidationProtocol) { public func insertMolecule(_ molecule: FormValidationProtocol) {
molecules.append(molecule) if let molecule = molecule as? FormValidationFormFieldProtocol {
fieldMolecules.append(molecule)
}
if let molecule = molecule as? FormValidationEnableDisableProtocol {
enableDisableMolecules.append(molecule)
}
} }
public static func enableByValidationWith(delegate: FormValidationProtocol?) { public static func enableByValidationWith(delegate: FormValidationProtocol?) {
@ -39,18 +45,25 @@ import UIKit
} }
public func enableByValidation() { public func enableByValidation() {
var valid = true var groupValue: [String: Bool] = [:]
for molecule in molecules { for molecule in fieldMolecules {
valid = valid && (molecule.isValidField?() ?? true) let valid = molecule.isValidField()
if let grouName = molecule.formFieldGroupName() {
groupValue[grouName] = valid && (groupValue[grouName] ?? true)
}
} }
let enableField = valid && (extraValidationBlock?() ?? true) shouldEnable(groupValue)
shouldEnable(enableField)
} }
public func shouldEnable(_ enable: Bool) { public func shouldEnable(_ groupValue: [String: Bool]) {
for molecule in molecules { for molecule in enableDisableMolecules {
molecule.enableField?(enable) var valid = false
for groupName in molecule.requiredFields?() ?? [] {
valid = groupValue[groupName] ?? false
}
molecule.enableField?(valid)
} }
} }
} }

View File

@ -9,9 +9,9 @@
import UIKit import UIKit
@objcMembers open class RadioButton: ViewConstrainingView { @objcMembers open class RadioButton: ViewConstrainingView, FormValidationFormFieldProtocol {
let radioButton = MFRadioButton() public let radioButton = MFRadioButton()
var delegateObject: MVMCoreUIDelegateObject? var delegateObject: MVMCoreUIDelegateObject?
var dummyButton: MFCustomButton? var dummyButton: MFCustomButton?
let label = Label() let label = Label()
@ -20,10 +20,11 @@ import UIKit
var formValue: Bool? var formValue: Bool?
var isRequired: Bool = false var isRequired: Bool = false
var radioButtonModel: RadioButtonModel? var radioButtonModel: RadioButtonModel?
lazy var groupName: String? = { lazy var groupName: String? = {
[unowned self] in [unowned self] in
return json?.optionalStringForKey("groupName") ?? json?.optionalStringForKey("fieldKey") return json?.optionalStringForKey("radioGroupName") ?? json?.optionalStringForKey("fieldKey")
}() }()
// MARK: - Inits // MARK: - Inits
@ -106,6 +107,22 @@ import UIKit
FormValidator.enableByValidationWith(delegate: delegateObject?.formValidationProtocol) FormValidator.enableByValidationWith(delegate: delegateObject?.formValidationProtocol)
changeAccessibilityLabel() changeAccessibilityLabel()
} }
public func isValidField() -> Bool {
return radioButton.isSelected
}
public func formFieldName() -> String? {
return json?.optionalStringForKey("fieldKey")
}
public func formFieldGroupName() -> String? {
return json?.optionalStringForKey("radioGroupName")
}
public func formFieldValue() -> Any? {
return radioButton.isSelected
}
} }
// MARK: - MVMCoreUIMoleculeViewProtocol // MARK: - MVMCoreUIMoleculeViewProtocol

View File

@ -12,14 +12,16 @@ import UIKit
@objcMembers public class RadioButtonModel: NSObject { @objcMembers public class RadioButtonModel: NSObject {
private var selectedRadioButton: RadioButton? private var selectedRadioButton: RadioButton?
private var fieldGroupName: String?
public static func setupForRadioButtonGroup(radioButton: RadioButton, formValidator: FormValidator?) -> RadioButtonModel { public static func setupForRadioButtonGroup(radioButton: RadioButton, formValidator: FormValidator?) -> RadioButtonModel {
guard let groupName = radioButton.groupName, guard let groupName = radioButton.groupName,
let formValidator = formValidator else { let formValidator = formValidator else {
return RadioButtonModel() return RadioButtonModel()
} }
let radioButtonModel = formValidator.radioButtonsModelByGroup[groupName] ?? RadioButtonModel() let radioButtonModel = formValidator.radioButtonsModelByGroup[groupName] ?? RadioButtonModel()
radioButtonModel.fieldGroupName = radioButton.formFieldGroupName()
formValidator.radioButtonsModelByGroup[groupName] = radioButtonModel formValidator.radioButtonsModelByGroup[groupName] = radioButtonModel
return radioButtonModel return radioButtonModel
} }
@ -32,7 +34,11 @@ import UIKit
} }
// MARK: - FormValidationProtocol // MARK: - FormValidationProtocol
extension RadioButtonModel: FormValidationProtocol { extension RadioButtonModel: FormValidationFormFieldProtocol {
public func formFieldGroupName() -> String? {
return selectedRadioButton?.formFieldGroupName() ?? self.fieldGroupName
}
// Used to check the validity of the field, to enable/disable the primary button. // Used to check the validity of the field, to enable/disable the primary button.
@objc public func isValidField() -> Bool { @objc public func isValidField() -> Bool {
return selectedRadioButton != nil ? true : false return selectedRadioButton != nil ? true : false

View File

@ -8,7 +8,7 @@
import UIKit import UIKit
@objcMembers public class Switch: ViewConstrainingView, FormValidationProtocol{ @objcMembers public class Switch: ViewConstrainingView, FormValidationFormFieldProtocol {
public var mvmSwitch = MVMCoreUISwitch() public var mvmSwitch = MVMCoreUISwitch()
var isRequired = false var isRequired = false
var delegateObject: DelegateObject? var delegateObject: DelegateObject?
@ -76,6 +76,10 @@ import UIKit
return mvmSwitch.isOn return mvmSwitch.isOn
} }
public func formFieldGroupName() -> String? {
return json?.optionalStringForKey("groupName")
}
public override func needsToBeConstrained() -> Bool { public override func needsToBeConstrained() -> Bool {
return true return true
} }

View File

@ -8,7 +8,9 @@
import UIKit import UIKit
@objcMembers public class SwitchLineItem: ViewConstrainingView, FormValidationProtocol{ @objcMembers public class SwitchLineItem: ViewConstrainingView, FormValidationFormFieldProtocol {
public var mvmSwitch = Switch() public var mvmSwitch = Switch()
public var label = Label() public var label = Label()
public var leftContainerView = UIView() public var leftContainerView = UIView()
@ -116,6 +118,23 @@ import UIKit
public override func alignment() -> UIStackView.Alignment { public override func alignment() -> UIStackView.Alignment {
return UIStackView.Alignment.leading return UIStackView.Alignment.leading
} }
public func isValidField() -> Bool {
return mvmSwitch.isValidField()
}
public func formFieldName() -> String? {
return mvmSwitch.formFieldName()
}
public func formFieldGroupName() -> String? {
return mvmSwitch.formFieldGroupName()
}
public func formFieldValue() -> Any? {
return mvmSwitch.formFieldValue()
}
} }