Merge branch 'feature/align_in_view' into 'develop'
Feature/align in view See merge request BPHV_MIPS/mvm_core_ui!86
This commit is contained in:
commit
7e83e0fba9
@ -147,22 +147,26 @@ import MVMCore
|
||||
|
||||
setLabel(label, withHTML: json?.optionalStringForKey("html"))
|
||||
|
||||
if let textColorHex = json?.optionalStringForKey(KeyTextColor), !textColorHex.isEmpty {
|
||||
label.textColor = UIColor.mfGet(forHex: textColorHex)
|
||||
}
|
||||
|
||||
if let backgroundColorHex = json?.optionalStringForKey(KeyBackgroundColor), !backgroundColorHex.isEmpty {
|
||||
label.backgroundColor = UIColor.mfGet(forHex: backgroundColorHex)
|
||||
}
|
||||
|
||||
label.accessibilityLabel = json?.optionalStringForKey("accessibilityText")
|
||||
|
||||
let fontSize = json?["fontSize"] as? CGFloat
|
||||
if let fontStyle = json?.optionalStringForKey("fontStyle") {
|
||||
MFStyler.styleLabel(label, withStyle: fontStyle)
|
||||
} else {
|
||||
let fontSize = json?["fontSize"] as? CGFloat
|
||||
|
||||
if let fontName = json?.optionalStringForKey("fontName") {
|
||||
label.font = MFFonts.mfFont(withName: fontName, size: fontSize ?? label.font.pointSize)
|
||||
} else if let fontSize = fontSize {
|
||||
label.font = label.font.withSize(fontSize)
|
||||
}
|
||||
}
|
||||
|
||||
if let fontName = json?.optionalStringForKey("fontName") {
|
||||
label.font = MFFonts.mfFont(withName: fontName, size: fontSize ?? label.font.pointSize)
|
||||
} else if let fontSize = fontSize {
|
||||
label.font = label.font.withSize(fontSize)
|
||||
if let textColorHex = json?.optionalStringForKey(KeyTextColor), !textColorHex.isEmpty {
|
||||
label.textColor = UIColor.mfGet(forHex: textColorHex)
|
||||
}
|
||||
|
||||
if let attributes = json?.arrayForKey("attributes"), let labelText = label.text {
|
||||
@ -190,18 +194,25 @@ import MVMCore
|
||||
attributedString.addAttribute(.foregroundColor, value: UIColor.mfGet(forHex: colorHex), range: range)
|
||||
}
|
||||
case "font":
|
||||
let fontSize = attribute["size"] as? CGFloat
|
||||
var font: UIFont?
|
||||
|
||||
if let fontName = attribute.optionalStringForKey("name") {
|
||||
font = MFFonts.mfFont(withName: fontName, size: fontSize ?? label.font.pointSize)
|
||||
} else if let fontSize = fontSize {
|
||||
font = label.font.withSize(fontSize)
|
||||
}
|
||||
|
||||
if let font = font {
|
||||
if let fontStyle = attribute.optionalStringForKey("style") {
|
||||
let styles = MFStyler.styleGetAttributedString("0", withStyle: fontStyle)
|
||||
attributedString.removeAttribute(.font, range: range)
|
||||
attributedString.addAttribute(.font, value: font, range: range)
|
||||
attributedString.removeAttribute(.foregroundColor, range: range)
|
||||
attributedString.addAttributes(styles.attributes(at: 0, effectiveRange: nil), range: range)
|
||||
} else {
|
||||
let fontSize = attribute["size"] as? CGFloat
|
||||
var font: UIFont?
|
||||
|
||||
if let fontName = attribute.optionalStringForKey("name") {
|
||||
font = MFFonts.mfFont(withName: fontName, size: fontSize ?? label.font.pointSize)
|
||||
} else if let fontSize = fontSize {
|
||||
font = label.font.withSize(fontSize)
|
||||
}
|
||||
|
||||
if let font = font {
|
||||
attributedString.removeAttribute(.font, range: range)
|
||||
attributedString.addAttribute(.font, value: font, range: range)
|
||||
}
|
||||
}
|
||||
default:
|
||||
continue
|
||||
@ -308,7 +319,7 @@ import MVMCore
|
||||
}
|
||||
|
||||
public func setAsMolecule() {
|
||||
setContentHuggingPriority(.required, for: .vertical)
|
||||
styleB2(true)
|
||||
}
|
||||
|
||||
public func needsToBeConstrained() -> Bool {
|
||||
|
||||
@ -15,9 +15,4 @@
|
||||
// Customize the label.
|
||||
@property (nullable, weak, nonatomic) Label *label;
|
||||
|
||||
// Change the alignment of the label
|
||||
- (void)alignLeft;
|
||||
- (void)alignCenter;
|
||||
- (void)alignRight;
|
||||
|
||||
@end
|
||||
|
||||
@ -11,11 +11,6 @@
|
||||
#import <MVMCoreUI/MVMCoreUI-Swift.h>
|
||||
@interface LabelView ()
|
||||
|
||||
// Change to customize.
|
||||
@property (strong, nonatomic) NSLayoutConstraint *alignCenterPin;
|
||||
@property (strong, nonatomic) NSLayoutConstraint *alignCenterLeftPin;
|
||||
@property (strong, nonatomic) NSLayoutConstraint *alignCenterRightPin;
|
||||
|
||||
// Sets up the view.
|
||||
- (void)setupView;
|
||||
|
||||
@ -36,39 +31,7 @@
|
||||
Label *label = [Label commonLabelB2:YES];
|
||||
[self addSubview:label];
|
||||
self.label = label;
|
||||
|
||||
// Align left and right constants.
|
||||
NSLayoutConstraint *leftPin = [NSLayoutConstraint constraintWithItem:label attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1.0 constant:0];
|
||||
self.leftPin = leftPin;
|
||||
leftPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *topPin = [NSLayoutConstraint constraintWithItem:label attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeTop multiplier:1.0 constant:0];
|
||||
topPin.priority = 999;
|
||||
self.topPin = topPin;
|
||||
topPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *bottomPin = [NSLayoutConstraint constraintWithItem:self attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:label attribute:NSLayoutAttributeBottom multiplier:1.0 constant:0];
|
||||
self.bottomPin = bottomPin;
|
||||
bottomPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *rightPin = [NSLayoutConstraint constraintWithItem:self attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:label attribute:NSLayoutAttributeRight multiplier:1.0 constant:0];
|
||||
rightPin.priority = 999;
|
||||
self.rightPin = rightPin;
|
||||
rightPin.active = YES;
|
||||
|
||||
// Center alignments
|
||||
NSLayoutConstraint *alignCenter = [NSLayoutConstraint constraintWithItem:label attribute:NSLayoutAttributeCenterX relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeCenterX multiplier:1.0 constant:0];
|
||||
self.alignCenterPin = alignCenter;
|
||||
alignCenter.active = YES;
|
||||
|
||||
NSLayoutConstraint *centerLeftPin = [NSLayoutConstraint constraintWithItem:label attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationGreaterThanOrEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1.0 constant:0];
|
||||
self.alignCenterLeftPin = centerLeftPin;
|
||||
centerLeftPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *centerRightPin = [NSLayoutConstraint constraintWithItem:self attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationGreaterThanOrEqual toItem:label attribute:NSLayoutAttributeRight multiplier:1.0 constant:0];
|
||||
self.alignCenterRightPin = centerRightPin;
|
||||
centerRightPin.active = YES;
|
||||
|
||||
[self pinViewToSuperView:label];
|
||||
[self alignLeft];
|
||||
}
|
||||
}
|
||||
@ -79,42 +42,20 @@
|
||||
}
|
||||
|
||||
- (void)alignLeft {
|
||||
self.alignCenterPin.active = NO;
|
||||
self.alignCenterLeftPin.active = NO;
|
||||
self.alignCenterRightPin.active = NO;
|
||||
self.leftPin.active = YES;
|
||||
self.rightPin.active = YES;
|
||||
[super alignLeft];
|
||||
self.label.textAlignment = NSTextAlignmentLeft;
|
||||
}
|
||||
|
||||
- (void)alignCenter {
|
||||
self.alignCenterPin.active = YES;
|
||||
self.alignCenterLeftPin.active = YES;
|
||||
self.alignCenterRightPin.active = YES;
|
||||
self.leftPin.active = NO;
|
||||
self.rightPin.active = NO;
|
||||
- (void)alignCenterHorizontal {
|
||||
[super alignCenterHorizontal];
|
||||
self.label.textAlignment = NSTextAlignmentCenter;
|
||||
}
|
||||
|
||||
- (void)alignRight {
|
||||
self.alignCenterPin.active = NO;
|
||||
self.alignCenterLeftPin.active = NO;
|
||||
self.alignCenterRightPin.active = NO;
|
||||
self.leftPin.active = YES;
|
||||
self.rightPin.active = YES;
|
||||
[super alignRight];
|
||||
self.label.textAlignment = NSTextAlignmentRight;
|
||||
}
|
||||
|
||||
- (void)setLeftPinConstant:(CGFloat)constant {
|
||||
[super setLeftPinConstant:constant];
|
||||
self.alignCenterLeftPin.constant = constant;
|
||||
}
|
||||
|
||||
- (void)setRightPinConstant:(CGFloat)constant {
|
||||
[super setRightPinConstant:constant];
|
||||
self.alignCenterRightPin.constant = constant;
|
||||
}
|
||||
|
||||
- (void)resetConstraints {
|
||||
[super resetConstraints];
|
||||
[self alignLeft];
|
||||
|
||||
@ -15,9 +15,4 @@
|
||||
|
||||
+ (nullable instancetype)createWithDelegate:(nullable id <UITextFieldDelegate, MFTextFieldDelegate>)delegate;
|
||||
|
||||
// Change the alignment of the label
|
||||
- (void)alignLeft;
|
||||
- (void)alignCenter;
|
||||
- (void)alignRight;
|
||||
|
||||
@end
|
||||
|
||||
@ -10,9 +10,6 @@
|
||||
#import "NSLayoutConstraint+MFConvenience.h"
|
||||
|
||||
@interface MVMCoreUITextFieldView ()
|
||||
@property (weak, nonatomic) NSLayoutConstraint *alignCenterPin;
|
||||
@property (weak, nonatomic) NSLayoutConstraint *alignCenterLeftPin;
|
||||
@property (weak, nonatomic) NSLayoutConstraint *alignCenterRightPin;
|
||||
@end
|
||||
|
||||
@implementation MVMCoreUITextFieldView
|
||||
@ -31,74 +28,11 @@
|
||||
mfTextField.translatesAutoresizingMaskIntoConstraints = NO;
|
||||
[self addSubview:mfTextField];
|
||||
self.mvmTextField = mfTextField;
|
||||
|
||||
NSLayoutConstraint *leftPin = [NSLayoutConstraint constraintWithItem:mfTextField attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1.0 constant:0];
|
||||
self.leftPin = leftPin;
|
||||
leftPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *topPin = [NSLayoutConstraint constraintWithItem:mfTextField attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeTop multiplier:1.0 constant:0];
|
||||
self.topPin = topPin;
|
||||
topPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *bottomPin = [NSLayoutConstraint constraintWithItem:self attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:mfTextField attribute:NSLayoutAttributeBottom multiplier:1.0 constant:0];
|
||||
self.bottomPin = bottomPin;
|
||||
bottomPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *rightPin = [NSLayoutConstraint constraintWithItem:self attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:mfTextField attribute:NSLayoutAttributeRight multiplier:1.0 constant:0];
|
||||
self.rightPin = rightPin;
|
||||
rightPin.active = YES;
|
||||
|
||||
// Center alignments
|
||||
NSLayoutConstraint *alignCenter = [NSLayoutConstraint constraintWithItem:mfTextField attribute:NSLayoutAttributeCenterX relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeCenterX multiplier:1.0 constant:0];
|
||||
self.alignCenterPin = alignCenter;
|
||||
alignCenter.active = YES;
|
||||
|
||||
NSLayoutConstraint *centerLeftPin = [NSLayoutConstraint constraintWithItem:mfTextField attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationGreaterThanOrEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1.0 constant:0];
|
||||
self.alignCenterLeftPin = centerLeftPin;
|
||||
centerLeftPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *centerRightPin = [NSLayoutConstraint constraintWithItem:self attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationGreaterThanOrEqual toItem:mfTextField attribute:NSLayoutAttributeRight multiplier:1.0 constant:0];
|
||||
self.alignCenterRightPin = centerRightPin;
|
||||
centerRightPin.active = YES;
|
||||
|
||||
[self pinViewToSuperView:mfTextField];
|
||||
[self alignLeft];
|
||||
}
|
||||
}
|
||||
|
||||
- (void)alignLeft {
|
||||
self.alignCenterPin.active = NO;
|
||||
self.alignCenterLeftPin.active = NO;
|
||||
self.alignCenterRightPin.active = NO;
|
||||
self.leftPin.active = YES;
|
||||
self.rightPin.active = YES;
|
||||
}
|
||||
|
||||
- (void)alignCenter {
|
||||
self.alignCenterPin.active = YES;
|
||||
self.alignCenterLeftPin.active = YES;
|
||||
self.alignCenterRightPin.active = YES;
|
||||
self.leftPin.active = NO;
|
||||
self.rightPin.active = NO;
|
||||
}
|
||||
|
||||
- (void)alignRight {
|
||||
self.alignCenterPin.active = NO;
|
||||
self.alignCenterLeftPin.active = NO;
|
||||
self.alignCenterRightPin.active = NO;
|
||||
self.leftPin.active = YES;
|
||||
self.rightPin.active = YES;
|
||||
}
|
||||
|
||||
- (void)setLeftPinConstant:(CGFloat)constant {
|
||||
self.leftPin.constant = constant;
|
||||
self.alignCenterLeftPin.constant = constant;
|
||||
}
|
||||
|
||||
- (void)setRightPinConstant:(CGFloat)constant {
|
||||
self.rightPin.constant = constant;
|
||||
self.alignCenterRightPin.constant = constant;
|
||||
}
|
||||
|
||||
- (void)resetConstraints {
|
||||
[super resetConstraints];
|
||||
[self alignLeft];
|
||||
|
||||
@ -20,11 +20,6 @@
|
||||
// inits with two buttons.
|
||||
- (nullable instancetype)initWithTwoButtons;
|
||||
|
||||
// Change the alignment of the button. Default is left.
|
||||
- (void)alignLeft;
|
||||
- (void)alignCenter;
|
||||
- (void)alignRight;
|
||||
|
||||
// To add dotted underline below text button, in case of one button
|
||||
- (void)addDotLineBelowButton;
|
||||
|
||||
|
||||
@ -14,10 +14,6 @@
|
||||
#import <MVMCoreUI/UIColor+MFConvenience.h>
|
||||
|
||||
@interface TextButtonView ()
|
||||
|
||||
@property (weak, nonatomic) NSLayoutConstraint *alignCenterPin;
|
||||
@property (weak, nonatomic) NSLayoutConstraint *alignCenterLeftPin;
|
||||
@property (weak, nonatomic) NSLayoutConstraint *alignCenterRightPin;
|
||||
@property (strong, nonatomic) UIView *dotLine;
|
||||
|
||||
// Sets up the view.
|
||||
@ -78,37 +74,7 @@
|
||||
button.translatesAutoresizingMaskIntoConstraints = NO;
|
||||
[self addSubview:button];
|
||||
self.textButton = button;
|
||||
|
||||
// Align left and right constants.
|
||||
NSLayoutConstraint *leftPin = [NSLayoutConstraint constraintWithItem:button attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1.0 constant:0];
|
||||
self.leftPin = leftPin;
|
||||
leftPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *topPin = [NSLayoutConstraint constraintWithItem:button attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeTop multiplier:1.0 constant:0];
|
||||
self.topPin = topPin;
|
||||
topPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *bottomPin = [NSLayoutConstraint constraintWithItem:self attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:button attribute:NSLayoutAttributeBottom multiplier:1.0 constant:0];
|
||||
self.bottomPin = bottomPin;
|
||||
bottomPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *rightPin = [NSLayoutConstraint constraintWithItem:self attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:button attribute:NSLayoutAttributeRight multiplier:1.0 constant:0];
|
||||
self.rightPin = rightPin;
|
||||
rightPin.active = YES;
|
||||
|
||||
// Center alignments
|
||||
NSLayoutConstraint *alignCenter = [NSLayoutConstraint constraintWithItem:button attribute:NSLayoutAttributeCenterX relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeCenterX multiplier:1.0 constant:0];
|
||||
self.alignCenterPin = alignCenter;
|
||||
alignCenter.active = YES;
|
||||
|
||||
NSLayoutConstraint *centerLeftPin = [NSLayoutConstraint constraintWithItem:button attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationGreaterThanOrEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1.0 constant:0];
|
||||
self.alignCenterLeftPin = centerLeftPin;
|
||||
centerLeftPin.active = YES;
|
||||
|
||||
NSLayoutConstraint *centerRightPin = [NSLayoutConstraint constraintWithItem:self attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationGreaterThanOrEqual toItem:button attribute:NSLayoutAttributeRight multiplier:1.0 constant:0];
|
||||
self.alignCenterRightPin = centerRightPin;
|
||||
centerRightPin.active = YES;
|
||||
|
||||
[self pinViewToSuperView:button];
|
||||
[self alignLeft];
|
||||
}
|
||||
}
|
||||
@ -154,40 +120,6 @@
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)alignLeft {
|
||||
self.alignCenterPin.active = NO;
|
||||
self.alignCenterLeftPin.active = NO;
|
||||
self.alignCenterRightPin.active = YES;
|
||||
self.leftPin.active = YES;
|
||||
self.rightPin.active = NO;
|
||||
}
|
||||
|
||||
- (void)alignCenter {
|
||||
self.alignCenterPin.active = YES;
|
||||
self.alignCenterLeftPin.active = YES;
|
||||
self.alignCenterRightPin.active = YES;
|
||||
self.leftPin.active = NO;
|
||||
self.rightPin.active = NO;
|
||||
}
|
||||
|
||||
- (void)alignRight {
|
||||
self.alignCenterPin.active = NO;
|
||||
self.alignCenterLeftPin.active = YES;
|
||||
self.alignCenterRightPin.active = NO;
|
||||
self.leftPin.active = NO;
|
||||
self.rightPin.active = YES;
|
||||
}
|
||||
|
||||
- (void)setLeftPinConstant:(CGFloat)constant {
|
||||
[super setLeftPinConstant:constant];
|
||||
self.alignCenterLeftPin.constant = constant;
|
||||
}
|
||||
|
||||
- (void)setRightPinConstant:(CGFloat)constant {
|
||||
[super setRightPinConstant:constant];
|
||||
self.alignCenterRightPin.constant = constant;
|
||||
}
|
||||
|
||||
- (void)resetConstraints {
|
||||
[super resetConstraints];
|
||||
[self alignLeft];
|
||||
|
||||
@ -17,9 +17,24 @@
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *topPin;
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *bottomPin;
|
||||
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *alignCenterPin;
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *alignCenterLeftPin;
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *alignCenterRightPin;
|
||||
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *alignCenterVerticalPin;
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *alignCenterTopPin;
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *alignCenterBottomPin;
|
||||
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *leftPinLow;
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *rightPinLow;
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *topPinLow;
|
||||
@property (nullable, strong, nonatomic) NSLayoutConstraint *bottomPinLow;
|
||||
|
||||
|
||||
// In updateView, will set horizontal padding to default if set to YES.
|
||||
@property (nonatomic) BOOL updateViewHorizontalDefaults;
|
||||
|
||||
|
||||
// Returns an empty view
|
||||
+ (nonnull ViewConstrainingView *)emptyView;
|
||||
|
||||
@ -43,6 +58,7 @@
|
||||
|
||||
// Pins all edges to its super. 0 constant
|
||||
- (void)pinToSuperView;
|
||||
- (void)pinViewToSuperView:(nonnull UIView *)view;
|
||||
|
||||
// Resets all the constraints to default.
|
||||
- (void)resetConstraints;
|
||||
@ -53,4 +69,17 @@
|
||||
// Add a view to be constrained in this view.
|
||||
- (void)addConstrainedView:(nonnull UIView *)view;
|
||||
|
||||
// Change the alignment of the label
|
||||
- (void)alignLeft;
|
||||
- (void)alignCenterHorizontal;
|
||||
- (void)alignRight;
|
||||
- (void)alignFillHorizontal;
|
||||
- (void)alignTop;
|
||||
- (void)alignCenterVertical;
|
||||
- (void)alignBottom;
|
||||
- (void)alignFillVertical;
|
||||
|
||||
/// Convenience function for getting the alignment from a map.
|
||||
+ (UIStackViewAlignment)getAlignmentForString:(nullable NSString *)alignmentString defaultAlignment:(UIStackViewAlignment)defaultAlignment;
|
||||
|
||||
@end
|
||||
|
||||
@ -45,12 +45,42 @@
|
||||
return constrainingView;
|
||||
}
|
||||
|
||||
- (void)pinToSuperView {
|
||||
NSDictionary *dictionary = [NSLayoutConstraint constraintPinSubviewToSuperview:self];
|
||||
#pragma mark - Constraining
|
||||
|
||||
- (void)pinViewToSuperView:(nonnull UIView *)view {
|
||||
NSDictionary *dictionary = [NSLayoutConstraint constraintPinSubviewToSuperview:view];
|
||||
self.leftPin = dictionary[ConstraintLeading];
|
||||
self.topPin = dictionary[ConstraintTop];
|
||||
self.bottomPin = dictionary[ConstraintBot];
|
||||
self.rightPin = dictionary[ConstraintTrailing];
|
||||
|
||||
self.alignCenterPin = [view.centerXAnchor constraintEqualToAnchor:view.superview.centerXAnchor];
|
||||
self.alignCenterLeftPin = [view.leftAnchor constraintGreaterThanOrEqualToAnchor:view.superview.leftAnchor];
|
||||
self.alignCenterRightPin = [view.superview.rightAnchor constraintGreaterThanOrEqualToAnchor:view.rightAnchor];
|
||||
|
||||
self.alignCenterVerticalPin = [view.centerYAnchor constraintEqualToAnchor:view.superview.centerYAnchor];
|
||||
self.alignCenterTopPin = [view.topAnchor constraintGreaterThanOrEqualToAnchor:view.superview.topAnchor];
|
||||
self.alignCenterBottomPin = [view.superview.bottomAnchor constraintGreaterThanOrEqualToAnchor:view.bottomAnchor];
|
||||
|
||||
self.leftPinLow = [view.leftAnchor constraintEqualToAnchor:view.superview.leftAnchor];
|
||||
self.leftPinLow.priority = 200;
|
||||
self.leftPinLow.active = YES;
|
||||
|
||||
self.topPinLow = [view.topAnchor constraintEqualToAnchor:view.superview.topAnchor];
|
||||
self.topPinLow.priority = 200;
|
||||
self.topPinLow.active = YES;
|
||||
|
||||
self.rightPinLow = [view.superview.rightAnchor constraintEqualToAnchor:view.superview.rightAnchor];
|
||||
self.rightPinLow.priority = 200;
|
||||
self.rightPinLow.active = YES;
|
||||
|
||||
self.bottomPinLow = [view.superview.bottomAnchor constraintEqualToAnchor:view.superview.bottomAnchor];
|
||||
self.bottomPinLow.priority = 200;
|
||||
self.bottomPinLow.active = YES;
|
||||
}
|
||||
|
||||
- (void)pinToSuperView {
|
||||
[self pinViewToSuperView:self];
|
||||
}
|
||||
|
||||
- (void)setPinConstantsWithInsets:(UIEdgeInsets)insets {
|
||||
@ -66,18 +96,26 @@
|
||||
|
||||
- (void)setLeftPinConstant:(CGFloat)constant {
|
||||
self.leftPin.constant = constant;
|
||||
self.alignCenterLeftPin.constant = constant;
|
||||
self.leftPinLow.constant = constant;
|
||||
}
|
||||
|
||||
- (void)setRightPinConstant:(CGFloat)constant {
|
||||
self.rightPin.constant = constant;
|
||||
self.alignCenterRightPin.constant = constant;
|
||||
self.rightPinLow.constant = constant;
|
||||
}
|
||||
|
||||
- (void)setTopPinConstant:(CGFloat)constant {
|
||||
self.topPin.constant = constant;
|
||||
self.alignCenterTopPin.constant = constant;
|
||||
self.topPinLow.constant = constant;
|
||||
}
|
||||
|
||||
- (void)setBottomPinConstant:(CGFloat)constant {
|
||||
self.bottomPin.constant = constant;
|
||||
self.alignCenterBottomPin.constant = constant;
|
||||
self.bottomPinLow.constant = constant;
|
||||
}
|
||||
|
||||
- (void)show {
|
||||
@ -100,30 +138,138 @@
|
||||
view.translatesAutoresizingMaskIntoConstraints = NO;
|
||||
[self addSubview:view];
|
||||
self.constrainedView = view;
|
||||
|
||||
NSLayoutRelation leftRelation;
|
||||
if (alignment == UIStackViewAlignmentFill || alignment == UIStackViewAlignmentLeading || alignment == UIStackViewAlignmentFirstBaseline) {
|
||||
leftRelation = NSLayoutRelationEqual;
|
||||
} else {
|
||||
leftRelation = NSLayoutRelationGreaterThanOrEqual;
|
||||
}
|
||||
NSLayoutRelation rightRelation;
|
||||
if (alignment == UIStackViewAlignmentFill || alignment == UIStackViewAlignmentTrailing || alignment == UIStackViewAlignmentLastBaseline) {
|
||||
rightRelation = NSLayoutRelationEqual;
|
||||
} else {
|
||||
rightRelation = NSLayoutRelationGreaterThanOrEqual;
|
||||
}
|
||||
NSDictionary *dictionary = [NSLayoutConstraint constraintPinSubview:view topRelation:NSLayoutRelationEqual bottomRelation:NSLayoutRelationEqual leftRelation:leftRelation rightRelation:rightRelation];
|
||||
self.leftPin = dictionary[ConstraintLeading];
|
||||
self.topPin = dictionary[ConstraintTop];
|
||||
self.bottomPin = dictionary[ConstraintBot];
|
||||
self.rightPin = dictionary[ConstraintTrailing];
|
||||
[self pinViewToSuperView:view];
|
||||
[self alignHorizontal:alignment];
|
||||
}
|
||||
|
||||
- (void)addConstrainedView:(nonnull UIView *)view {
|
||||
[self addConstrainedView:view alignment:UIStackViewAlignmentFill];
|
||||
}
|
||||
|
||||
- (void)alignLeft {
|
||||
self.alignCenterPin.active = NO;
|
||||
self.alignCenterLeftPin.active = NO;
|
||||
self.alignCenterRightPin.active = YES;
|
||||
self.leftPin.active = YES;
|
||||
self.rightPin.active = NO;
|
||||
}
|
||||
|
||||
- (void)alignCenterHorizontal {
|
||||
self.alignCenterPin.active = YES;
|
||||
self.alignCenterLeftPin.active = YES;
|
||||
self.alignCenterRightPin.active = YES;
|
||||
self.leftPin.active = NO;
|
||||
self.rightPin.active = NO;
|
||||
}
|
||||
|
||||
- (void)alignRight {
|
||||
self.alignCenterPin.active = NO;
|
||||
self.alignCenterLeftPin.active = YES;
|
||||
self.alignCenterRightPin.active = NO;
|
||||
self.leftPin.active = NO;
|
||||
self.rightPin.active = YES;
|
||||
}
|
||||
|
||||
- (void)alignFillHorizontal {
|
||||
self.alignCenterPin.active = NO;
|
||||
self.alignCenterLeftPin.active = NO;
|
||||
self.alignCenterRightPin.active = NO;
|
||||
self.leftPin.active = YES;
|
||||
self.rightPin.active = YES;
|
||||
}
|
||||
|
||||
- (void)alignTop {
|
||||
self.alignCenterVerticalPin.active = NO;
|
||||
self.alignCenterTopPin.active = NO;
|
||||
self.alignCenterBottomPin.active = YES;
|
||||
self.topPin.active = YES;
|
||||
self.bottomPin.active = NO;
|
||||
}
|
||||
|
||||
- (void)alignCenterVertical {
|
||||
self.alignCenterVerticalPin.active = YES;
|
||||
self.alignCenterTopPin.active = YES;
|
||||
self.alignCenterBottomPin.active = YES;
|
||||
self.topPin.active = NO;
|
||||
self.bottomPin.active = NO;
|
||||
}
|
||||
|
||||
- (void)alignBottom {
|
||||
self.alignCenterVerticalPin.active = NO;
|
||||
self.alignCenterTopPin.active = YES;
|
||||
self.alignCenterBottomPin.active = NO;
|
||||
self.topPin.active = NO;
|
||||
self.bottomPin.active = YES;
|
||||
}
|
||||
|
||||
- (void)alignFillVertical {
|
||||
self.alignCenterVerticalPin.active = NO;
|
||||
self.alignCenterTopPin.active = NO;
|
||||
self.alignCenterBottomPin.active = NO;
|
||||
self.topPin.active = YES;
|
||||
self.bottomPin.active = YES;
|
||||
}
|
||||
|
||||
+ (UIStackViewAlignment)getAlignmentForString:(nullable NSString *)alignmentString defaultAlignment:(UIStackViewAlignment)defaultAlignment {
|
||||
if ([alignmentString isEqualToString:@"leading"]) {
|
||||
return UIStackViewAlignmentLeading;
|
||||
} else if ([alignmentString isEqualToString:@"trailing"]) {
|
||||
return UIStackViewAlignmentTrailing;
|
||||
} else if ([alignmentString isEqualToString:@"center"]) {
|
||||
return UIStackViewAlignmentCenter;
|
||||
} else if ([alignmentString isEqualToString:@"fill"]) {
|
||||
return UIStackViewAlignmentFill;
|
||||
} else {
|
||||
return defaultAlignment;
|
||||
}
|
||||
}
|
||||
|
||||
#pragma mark - MVMCoreUIViewConstrainingProtocol
|
||||
|
||||
- (void)alignHorizontal:(UIStackViewAlignment)alignment {
|
||||
switch (alignment) {
|
||||
case UIStackViewAlignmentCenter:
|
||||
[self alignCenterHorizontal];
|
||||
break;
|
||||
case UIStackViewAlignmentLeading:
|
||||
[self alignLeft];
|
||||
break;
|
||||
case UIStackViewAlignmentTrailing:
|
||||
[self alignRight];
|
||||
break;
|
||||
case UIStackViewAlignmentFill:
|
||||
[self alignFillHorizontal];
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
- (void)alignVertical:(UIStackViewAlignment)alignment {
|
||||
switch (alignment) {
|
||||
case UIStackViewAlignmentCenter:
|
||||
[self alignCenterVertical];
|
||||
break;
|
||||
case UIStackViewAlignmentLeading:
|
||||
[self alignTop];
|
||||
break;
|
||||
case UIStackViewAlignmentTrailing:
|
||||
[self alignBottom];
|
||||
break;
|
||||
case UIStackViewAlignmentFill:
|
||||
[self alignFillVertical];
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
- (void)shouldSetHorizontalMargins:(BOOL)shouldSet {
|
||||
self.updateViewHorizontalDefaults = shouldSet;
|
||||
}
|
||||
|
||||
#pragma mark - MVMCoreViewProtocol
|
||||
|
||||
- (void)setupView {
|
||||
[super setupView];
|
||||
self.translatesAutoresizingMaskIntoConstraints = NO;
|
||||
@ -145,14 +291,14 @@
|
||||
}
|
||||
}
|
||||
|
||||
#pragma mark - MVMCoreUIMoleculeViewProtocol
|
||||
|
||||
- (void)reset {
|
||||
if ([self.constrainedView respondsToSelector:@selector(reset)]) {
|
||||
[self.constrainedView performSelector:@selector(reset)];
|
||||
}
|
||||
}
|
||||
|
||||
#pragma mark - MVMCoreUIMoleculeViewProtocol
|
||||
|
||||
- (void)setAsMolecule {
|
||||
self.updateViewHorizontalDefaults = YES;
|
||||
}
|
||||
|
||||
@ -55,7 +55,7 @@ extern NSString * _Nonnull const ConstraintWidth;
|
||||
+ (nullable NSDictionary *)constraintPinView:(nonnull UIView*)view heightConstraint:(BOOL)pinHeight heightConstant:(CGFloat)heightConstant widthConstraint:(BOOL)pinWidth widthConstant:(CGFloat)widthConstant;
|
||||
|
||||
// pins 2 views in same hierarchy
|
||||
+(nullable NSLayoutConstraint *)constraintPinFirstView :(nonnull UIView*)firstView toSecondView :(nonnull UIView*)secondView withConstant :(CGFloat)constant directionVertical :(BOOL)directionVertical;
|
||||
+(nonnull NSLayoutConstraint *)constraintPinFirstView :(nonnull UIView*)firstView toSecondView :(nonnull UIView*)secondView withConstant :(CGFloat)constant directionVertical :(BOOL)directionVertical;
|
||||
|
||||
+(nullable NSDictionary *)constraintAlignView :(nonnull UIView *)firstView toSecondView :(nonnull UIView *)secondView alignX :(BOOL)alignX alignY :(BOOL)alignY;
|
||||
|
||||
|
||||
@ -10,9 +10,6 @@ import UIKit
|
||||
|
||||
@objcMembers open class ButtonView: ViewConstrainingView {
|
||||
open var primaryButton: PrimaryButton? = PrimaryButton.button()
|
||||
open var alignCenterPin: NSLayoutConstraint?
|
||||
open var alignCenterLeftPin: NSLayoutConstraint?
|
||||
open var alignCenterRightPin: NSLayoutConstraint?
|
||||
|
||||
// MARK: - Inits
|
||||
public init() {
|
||||
@ -53,7 +50,7 @@ import UIKit
|
||||
open override func setupView() {
|
||||
super.setupView()
|
||||
setupButton()
|
||||
alignCenter()
|
||||
alignCenterHorizontal()
|
||||
}
|
||||
|
||||
// MARK: - MVMCoreUIMoleculeViewProtocol
|
||||
@ -75,56 +72,9 @@ import UIKit
|
||||
func setupButton() {
|
||||
if let primaryButton = primaryButton, !subviews.contains(primaryButton) {
|
||||
addSubview(primaryButton)
|
||||
setupConstraints(forView: primaryButton)
|
||||
pinView(toSuperView: primaryButton)
|
||||
}
|
||||
}
|
||||
|
||||
func setupConstraints(forView view: UIView) {
|
||||
leftPin = view.leftAnchor.constraint(equalTo: leftAnchor)
|
||||
topPin = view.topAnchor.constraint(equalTo: topAnchor)
|
||||
rightPin = rightAnchor.constraint(equalTo: view.rightAnchor)
|
||||
bottomPin = bottomAnchor.constraint(equalTo: view.bottomAnchor)
|
||||
leftPin?.isActive = true
|
||||
topPin?.isActive = true
|
||||
rightPin?.isActive = true
|
||||
bottomPin?.isActive = true
|
||||
|
||||
alignCenterPin = view.centerXAnchor.constraint(equalTo: centerXAnchor)
|
||||
alignCenterLeftPin = view.leftAnchor.constraint(greaterThanOrEqualTo: leftAnchor)
|
||||
alignCenterRightPin = rightAnchor.constraint(greaterThanOrEqualTo: view.rightAnchor)
|
||||
}
|
||||
|
||||
open func alignLeft() {
|
||||
alignCenterPin?.isActive = false
|
||||
alignCenterLeftPin?.isActive = false
|
||||
alignCenterRightPin?.isActive = true
|
||||
leftPin?.isActive = true
|
||||
rightPin?.isActive = false
|
||||
}
|
||||
|
||||
open func alignCenter() {
|
||||
alignCenterPin?.isActive = true
|
||||
alignCenterLeftPin?.isActive = true
|
||||
alignCenterRightPin?.isActive = true
|
||||
leftPin?.isActive = false
|
||||
rightPin?.isActive = false
|
||||
}
|
||||
|
||||
open func alignRight() {
|
||||
alignCenterPin?.isActive = false
|
||||
alignCenterLeftPin?.isActive = true
|
||||
alignCenterRightPin?.isActive = false
|
||||
leftPin?.isActive = false
|
||||
rightPin?.isActive = true
|
||||
}
|
||||
|
||||
open func alignFill() {
|
||||
alignCenterPin?.isActive = false
|
||||
alignCenterLeftPin?.isActive = false
|
||||
alignCenterRightPin?.isActive = false
|
||||
leftPin?.isActive = true
|
||||
rightPin?.isActive = true
|
||||
}
|
||||
|
||||
open override func setLeftPinConstant(_ constant: CGFloat) {
|
||||
super.setLeftPinConstant(constant)
|
||||
|
||||
@ -27,6 +27,9 @@
|
||||
/// For the molecule list to load more efficiently.
|
||||
+ (CGFloat)estimatedHeightForRow:(nullable NSDictionary *)json;
|
||||
|
||||
/// Allows the molecule to set its name for reuse. Default could be moleculeName.
|
||||
+ (nullable NSString *)nameForReuse:(nullable NSDictionary *)molecule delegateObject:(nullable MVMCoreUIDelegateObject *)delegateObject;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
|
||||
@ -8,10 +8,82 @@
|
||||
|
||||
import UIKit
|
||||
|
||||
public class MoleculeStackView: MFView {
|
||||
var spacingBlock: ((Any) -> UIEdgeInsets)?
|
||||
var moleculesArray: [UIView]?
|
||||
var useMargins: Bool = false
|
||||
public class StackItem {
|
||||
var view: UIView
|
||||
var spacing: CGFloat?
|
||||
var percentage: Int?
|
||||
var verticalAlignment: UIStackView.Alignment?
|
||||
var horizontalAlignment: UIStackView.Alignment?
|
||||
|
||||
init(with view: UIView) {
|
||||
self.view = view
|
||||
}
|
||||
|
||||
init(with view: UIView, json: [AnyHashable: Any]) {
|
||||
self.view = view
|
||||
update(with: json)
|
||||
}
|
||||
|
||||
func update(with json: [AnyHashable: Any]) {
|
||||
spacing = json.optionalCGFloatForKey("spacing")
|
||||
percentage = json["percent"] as? Int
|
||||
if let alignment = json.optionalStringForKey("verticalAlignment") {
|
||||
verticalAlignment = ViewConstrainingView.getAlignmentFor(alignment, defaultAlignment: .fill)
|
||||
}
|
||||
if let alignment = json.optionalStringForKey("horizontalAlignment") {
|
||||
horizontalAlignment = ViewConstrainingView.getAlignmentFor(alignment, defaultAlignment: .fill)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class MoleculeStackView: ViewConstrainingView {
|
||||
var contentView: UIView = MVMCoreUICommonViewsUtility.commonView()
|
||||
var items: [StackItem] = []
|
||||
|
||||
/// For setting the direction of the stack
|
||||
var axis: NSLayoutConstraint.Axis = .vertical {
|
||||
didSet {
|
||||
updateViewHorizontalDefaults = axis == .horizontal
|
||||
if axis != oldValue {
|
||||
restack()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// The spacing to use between each item in the stack.
|
||||
var spacing: CGFloat = 16 {
|
||||
didSet {
|
||||
if spacing != oldValue {
|
||||
restack()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Helpers
|
||||
public func setAxisWithJSON(_ json: [AnyHashable: Any]?) {
|
||||
switch json?.optionalStringForKey("axis") {
|
||||
case "horizontal":
|
||||
axis = .horizontal
|
||||
default:
|
||||
axis = .vertical
|
||||
}
|
||||
}
|
||||
|
||||
public func pinView(_ view: UIView, toView: UIView, attribute: NSLayoutConstraint.Attribute, relation: NSLayoutConstraint.Relation, priority: UILayoutPriority, constant: CGFloat) {
|
||||
let constraint = NSLayoutConstraint(item: view, attribute: attribute, relatedBy: relation, toItem: toView, attribute: attribute, multiplier: 1.0, constant: constant)
|
||||
constraint.priority = priority
|
||||
constraint.isActive = true
|
||||
}
|
||||
|
||||
/// Restacks the existing items.
|
||||
func restack() {
|
||||
MVMCoreUIStackableViewController.remove(contentView.subviews)
|
||||
let stackItems = items
|
||||
items.removeAll()
|
||||
for (index, item) in stackItems.enumerated() {
|
||||
addStackItem(item, lastItem: index == stackItems.count - 1)
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Inits
|
||||
public override init(frame: CGRect) {
|
||||
@ -23,11 +95,6 @@ public class MoleculeStackView: MFView {
|
||||
setWithJSON(json, delegateObject: delegateObject, additionalData: additionalData)
|
||||
}
|
||||
|
||||
public convenience init(withJSON json: [AnyHashable: Any]?, delegateObject: MVMCoreUIDelegateObject?, spacingBlock: ((Any) -> UIEdgeInsets)?) {
|
||||
self.init(withJSON: json, delegateObject: delegateObject, additionalData: nil)
|
||||
self.spacingBlock = spacingBlock
|
||||
}
|
||||
|
||||
public required init?(coder aDecoder: NSCoder) {
|
||||
fatalError("init(coder:) has not been implemented")
|
||||
}
|
||||
@ -35,47 +102,153 @@ public class MoleculeStackView: MFView {
|
||||
// MARK: - MFViewProtocol
|
||||
public override func setupView() {
|
||||
super.setupView()
|
||||
guard contentView.superview == nil else {
|
||||
return
|
||||
}
|
||||
translatesAutoresizingMaskIntoConstraints = false
|
||||
backgroundColor = .clear
|
||||
self.setContentHuggingPriority(UILayoutPriority.required, for: NSLayoutConstraint.Axis.vertical)
|
||||
self.setContentCompressionResistancePriority(UILayoutPriority.required, for: NSLayoutConstraint.Axis.vertical)
|
||||
addConstrainedView(contentView)
|
||||
contentView.setContentHuggingPriority(.defaultHigh, for: .vertical)
|
||||
contentView.setContentHuggingPriority(.defaultHigh, for: .horizontal)
|
||||
}
|
||||
|
||||
public override func updateView(_ size: CGFloat) {
|
||||
super.updateView(size)
|
||||
for view in subviews {
|
||||
if let mvmView = view as? MVMCoreViewProtocol {
|
||||
mvmView.updateView(size)
|
||||
}
|
||||
for item in items {
|
||||
(item.view as? MVMCoreViewProtocol)?.updateView(size)
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - MVMCoreUIMoleculeViewProtocol
|
||||
public override func setAsMolecule() {
|
||||
updateViewHorizontalDefaults = false
|
||||
}
|
||||
|
||||
public override func reset() {
|
||||
backgroundColor = .clear
|
||||
for item in items {
|
||||
if let view = item.view as? MVMCoreUIMoleculeViewProtocol {
|
||||
view.reset?()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
open override func setWithJSON(_ json: [AnyHashable: Any]?, delegateObject: MVMCoreUIDelegateObject?, additionalData: [AnyHashable: Any]?) {
|
||||
let previousJSON = self.json
|
||||
super.setWithJSON(json, delegateObject: delegateObject, additionalData: additionalData)
|
||||
MVMCoreUIStackableViewController.remove(contentView.subviews)
|
||||
|
||||
// If the items in the stack are the same, just update previous items instead of re-allocating.
|
||||
var items: [StackItem]?
|
||||
if MoleculeStackView.name(forReuse: previousJSON, delegateObject: delegateObject) == MoleculeStackView.name(forReuse: json, delegateObject: delegateObject) {
|
||||
items = self.items
|
||||
}
|
||||
self.items = []
|
||||
|
||||
if let colorString = json?.optionalStringForKey(KeyBackgroundColor) {
|
||||
backgroundColor = .mfGet(forHex: colorString)
|
||||
}
|
||||
|
||||
guard let molecules = json?.arrayForKey(KeyMolecules) as? [[String: Any]] else {
|
||||
return
|
||||
}
|
||||
|
||||
// Create the molecules and set the json.
|
||||
var moleculesArray = [] as [UIView]
|
||||
for moleculeJSON in molecules {
|
||||
if let molecule = MVMCoreUIMoleculeMappingObject.shared()?.createMolecule(forJSON: moleculeJSON, delegateObject: delegateObject, constrainIfNeeded: true) {
|
||||
moleculesArray.append(molecule)
|
||||
}
|
||||
}
|
||||
// Sets the stack attributes
|
||||
setAxisWithJSON(json)
|
||||
spacing = json?.optionalCGFloatForKey("spacing") ?? 16
|
||||
|
||||
guard moleculesArray.count > 0 else {
|
||||
return
|
||||
}
|
||||
|
||||
if let spacingBlock = spacingBlock {
|
||||
MVMCoreUIStackableViewController.populateView(self, withUIArray: moleculesArray, useMargins: useMargins, withSpacingBlock: spacingBlock)
|
||||
// Set the alignment for the stack in the containing view. The json driven value is for the axis direction alignment.
|
||||
if axis == .vertical {
|
||||
alignHorizontal(.fill)
|
||||
alignVertical(ViewConstrainingView.getAlignmentFor(json?.optionalStringForKey("alignment"), defaultAlignment: .fill))
|
||||
} else {
|
||||
let separation = json?.optionalCGFloatForKey("separation") ?? PaddingDefault
|
||||
MVMCoreUIStackableViewController.populateView(self, withUIArray: moleculesArray, useMargins: useMargins) { (object) -> UIEdgeInsets in
|
||||
return UIEdgeInsets.init(top: separation, left: 0, bottom: 0, right: 0)
|
||||
alignHorizontal(ViewConstrainingView.getAlignmentFor(json?.optionalStringForKey("alignment"), defaultAlignment: .fill))
|
||||
alignVertical(.leading)
|
||||
}
|
||||
|
||||
// Adds the molecules and sets the json.
|
||||
for (index, map) in molecules.enumerated() {
|
||||
if let moleculeJSON = map.optionalDictionaryForKey(KeyMolecule) {
|
||||
var view: UIView?
|
||||
if let item = items?[index] {
|
||||
(item.view as? MVMCoreUIMoleculeViewProtocol)?.setWithJSON(moleculeJSON, delegateObject: delegateObject, additionalData: additionalData)
|
||||
item.update(with: moleculeJSON)
|
||||
view = item.view
|
||||
addStackItem(item, lastItem: index == molecules.count - 1)
|
||||
} else if let molecule = MVMCoreUIMoleculeMappingObject.shared()?.createMolecule(forJSON: moleculeJSON, delegateObject: delegateObject, constrainIfNeeded: true) {
|
||||
view = molecule
|
||||
addStackItem(StackItem(with: molecule, json: map), lastItem: index == molecules.count - 1)
|
||||
}
|
||||
|
||||
(view as? MVMCoreUIViewConstrainingProtocol)?.shouldSetHorizontalMargins?(axis == .vertical)
|
||||
(view as? MVMCoreUIViewConstrainingProtocol)?.shouldSetVerticalMargins?(false)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public override static func name(forReuse molecule: [AnyHashable : Any]?, delegateObject: MVMCoreUIDelegateObject?) -> String? {
|
||||
// This will aggregate names of molecules to make an id.
|
||||
var name = ""
|
||||
guard let molecules = molecule?.optionalArrayForKey(KeyMolecules) else {
|
||||
return name
|
||||
}
|
||||
for case let item as [AnyHashable: AnyHashable] in molecules {
|
||||
if let moleculeName = item.stringOptionalWithChainOfKeysOrIndexes([KeyMolecule, KeyMoleculeName]) {
|
||||
name.append(moleculeName)
|
||||
}
|
||||
}
|
||||
return name
|
||||
}
|
||||
|
||||
// MARK: - Adding to stack
|
||||
/// Adds the view to the stack.
|
||||
func addView(_ view: UIView, lastItem: Bool) {
|
||||
addStackItem(StackItem(with: view), lastItem: lastItem)
|
||||
}
|
||||
|
||||
/// Adds the stack item to the stack.
|
||||
func addStackItem(_ stackItem: StackItem, lastItem: Bool) {
|
||||
let view = stackItem.view
|
||||
contentView.addSubview(view)
|
||||
view.translatesAutoresizingMaskIntoConstraints = false
|
||||
|
||||
let spacing = stackItem.spacing ?? self.spacing
|
||||
if let view = view as? MVMCoreUIViewConstrainingProtocol {
|
||||
let verticalAlignment = stackItem.verticalAlignment ?? (stackItem.percentage == nil && axis == .vertical ? .fill : (axis == .vertical ? .leading : .center))
|
||||
let horizontalAlignment = stackItem.horizontalAlignment ?? view.alignment?() ?? (axis == .vertical || stackItem.percentage == nil ? .fill : .leading)
|
||||
view.alignHorizontal?(horizontalAlignment)
|
||||
view.alignVertical?(verticalAlignment)
|
||||
}
|
||||
if axis == .vertical {
|
||||
if items.count == 0 {
|
||||
pinView(view, toView: contentView, attribute: .top, relation: .equal, priority: .required, constant: spacing)
|
||||
} else if let previousView = items.last?.view {
|
||||
_ = NSLayoutConstraint(pinFirstView: previousView, toSecondView: view, withConstant: spacing, directionVertical: true)
|
||||
}
|
||||
pinView(view, toView: contentView, attribute: .leading, relation: .equal, priority: .required, constant: 0)
|
||||
pinView(contentView, toView: view, attribute: .trailing, relation: .equal, priority: .required, constant: 0)
|
||||
if let percent = stackItem.percentage {
|
||||
view.heightAnchor.constraint(equalTo: contentView.heightAnchor, multiplier: CGFloat(percent)/100.0).isActive = true
|
||||
}
|
||||
if lastItem {
|
||||
pinView(contentView, toView: view, attribute: .bottom, relation: .equal, priority: .required, constant: 0)
|
||||
}
|
||||
} else {
|
||||
if items.count == 0 {
|
||||
// First horizontal item has no spacing by default unless told otherwise.
|
||||
pinView(view, toView: contentView, attribute: .leading, relation: .equal, priority: .required, constant: stackItem.spacing ?? 0)
|
||||
} else if let previousView = items.last?.view {
|
||||
_ = NSLayoutConstraint(pinFirstView: previousView, toSecondView: view, withConstant: spacing, directionVertical: false)
|
||||
}
|
||||
pinView(view, toView: contentView, attribute: .top, relation: .equal, priority: .required, constant: 0)
|
||||
pinView(contentView, toView: view, attribute: .bottom, relation: .equal, priority: .required, constant: 0)
|
||||
if let percent = stackItem.percentage {
|
||||
view.widthAnchor.constraint(equalTo: contentView.widthAnchor, multiplier: CGFloat(percent)/100.0).isActive = true
|
||||
}
|
||||
}
|
||||
if lastItem {
|
||||
pinView(contentView, toView: view, attribute: .right, relation: .equal, priority: .required, constant: 0)
|
||||
}
|
||||
items.append(stackItem)
|
||||
}
|
||||
}
|
||||
|
||||
@ -43,11 +43,25 @@ import UIKit
|
||||
public func updateView(_ size: CGFloat) {
|
||||
MFStyler.setDefaultMarginsFor(self, size: size, horizontal: true, vertical: true)
|
||||
if #available(iOS 11.0, *) {
|
||||
contentView.directionalLayoutMargins = directionalLayoutMargins
|
||||
if accessoryView != nil {
|
||||
// Smaller left margin if accessory view.
|
||||
var margin = directionalLayoutMargins
|
||||
margin.trailing = 16
|
||||
contentView.directionalLayoutMargins = margin
|
||||
} else {
|
||||
contentView.directionalLayoutMargins = directionalLayoutMargins
|
||||
}
|
||||
topSeparatorView?.setLeftAndRightPinConstant(directionalLayoutMargins.leading)
|
||||
bottomSeparatorView?.setLeftAndRightPinConstant(directionalLayoutMargins.leading)
|
||||
} else {
|
||||
contentView.layoutMargins = layoutMargins
|
||||
if accessoryView != nil {
|
||||
// Smaller left margin if accessory view.
|
||||
var margin = layoutMargins
|
||||
margin.right = 16
|
||||
contentView.layoutMargins = margin
|
||||
} else {
|
||||
contentView.layoutMargins = layoutMargins
|
||||
}
|
||||
topSeparatorView?.setLeftAndRightPinConstant(layoutMargins.left)
|
||||
bottomSeparatorView?.setLeftAndRightPinConstant(layoutMargins.left)
|
||||
}
|
||||
@ -67,7 +81,7 @@ import UIKit
|
||||
}
|
||||
|
||||
// MARK: - MVMCoreUIMoleculeViewProtocol
|
||||
public func setWithJSON(_ json: [AnyHashable : Any]?, delegateObject: MVMCoreUIDelegateObject?, additionalData: [AnyHashable : Any]?) {
|
||||
public func setWithJSON(_ json: [AnyHashable: Any]?, delegateObject: MVMCoreUIDelegateObject?, additionalData: [AnyHashable: Any]?) {
|
||||
self.json = json;
|
||||
guard let json = json, let moleculeJSON = json.optionalDictionaryForKey(KeyMolecule) else {
|
||||
return
|
||||
@ -75,15 +89,17 @@ import UIKit
|
||||
if molecule == nil {
|
||||
if let moleculeView = MVMCoreUIMoleculeMappingObject.shared()?.createMolecule(forJSON: moleculeJSON, delegateObject: delegateObject, constrainIfNeeded: true) {
|
||||
contentView.addSubview(moleculeView)
|
||||
let standardConstraints = (moleculeView as? MVMCoreUIViewConstrainingProtocol)?.useStandardConstraints?() ?? true
|
||||
var standardConstraints = true
|
||||
if let castView = moleculeView as? MVMCoreUIViewConstrainingProtocol {
|
||||
standardConstraints = castView.useStandardConstraints?() ?? true
|
||||
castView.shouldSetHorizontalMargins?(!standardConstraints)
|
||||
castView.shouldSetVerticalMargins?(!standardConstraints)
|
||||
}
|
||||
NSLayoutConstraint.activate(Array(NSLayoutConstraint.pinView(toSuperview: moleculeView, useMargins: standardConstraints).values))
|
||||
if standardConstraints {
|
||||
let constraint = contentView.heightAnchor.constraint(equalToConstant: 80)
|
||||
constraint.priority = .defaultLow
|
||||
constraint.isActive = true
|
||||
if let moleculeView = moleculeView as? ViewConstrainingView {
|
||||
moleculeView.updateViewHorizontalDefaults = false
|
||||
}
|
||||
}
|
||||
molecule = moleculeView
|
||||
}
|
||||
@ -110,15 +126,27 @@ import UIKit
|
||||
molecule?.reset?()
|
||||
}
|
||||
|
||||
public static func estimatedHeight(forRow json: [AnyHashable : Any]?) -> CGFloat {
|
||||
public static func estimatedHeight(forRow json: [AnyHashable: Any]?) -> CGFloat {
|
||||
guard let moleculeJSON = json?.optionalDictionaryForKey(KeyMolecule),
|
||||
let theClass = MVMCoreUIMoleculeMappingObject.shared()?.getMoleculeClass(withJSON: moleculeJSON, delegateObject: nil),
|
||||
let estimatedHeightFor = theClass.estimatedHeight else {
|
||||
return 0
|
||||
return 80
|
||||
}
|
||||
return estimatedHeightFor(moleculeJSON)
|
||||
}
|
||||
|
||||
public static func name(forReuse molecule: [AnyHashable: Any]?, delegateObject: MVMCoreUIDelegateObject?) -> String? {
|
||||
if let molecule = molecule?.optionalDictionaryForKey(KeyMolecule),
|
||||
let moleculeName = molecule.optionalStringForKey(KeyMoleculeName),
|
||||
let moleculeClass = MVMCoreUIMoleculeMappingObject.shared()?.moleculeMapping[moleculeName] as? AnyClass,
|
||||
let castClass = moleculeClass as? MVMCoreUIMoleculeViewProtocol.Type,
|
||||
let nameFunc = castClass.name {
|
||||
return nameFunc(molecule, delegateObject)
|
||||
} else {
|
||||
return molecule?.optionalDictionaryForKey(KeyMolecule)?.optionalStringForKey(KeyMoleculeName)
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Arrow
|
||||
/// Adds the standard mvm style caret to the accessory view
|
||||
public func addCaretViewAccessory() {
|
||||
@ -129,16 +157,12 @@ import UIKit
|
||||
let height: CGFloat = 10
|
||||
caretView = CaretView(lineThickness: CaretView.thin)
|
||||
caretView?.frame = CGRect(x: 0, y: 0, width: width, height: height)
|
||||
caretViewWidthSizeObject = MFSizeObject(scalingStandardSize: width)
|
||||
caretViewHeightSizeObject = MFSizeObject(scalingStandardSize: height)
|
||||
caretViewWidthSizeObject = MFSizeObject(standardSize: width, standardiPadPortraitSize: 9)
|
||||
caretViewHeightSizeObject = MFSizeObject(standardSize: height, standardiPadPortraitSize: 16)
|
||||
accessoryView = caretView
|
||||
}
|
||||
|
||||
// MARK: - MoleculeListCellProtocol
|
||||
public static func moleculeName(_ molecule: [AnyHashable : Any]?, delegateObject: MVMCoreUIDelegateObject?) -> String? {
|
||||
return molecule?.optionalDictionaryForKey(KeyMolecule)?.optionalStringForKey(KeyMoleculeName)
|
||||
}
|
||||
|
||||
/// For when the separator between cells shows using json and frequency. Default is type: standard, frequency: allExceptTop.
|
||||
public func setSeparatorWithJSON(_ json: [AnyHashable: Any]?, delegateObject: MVMCoreUIDelegateObject?, additionalData: [AnyHashable: Any]?, indexPath: IndexPath) {
|
||||
addSeparatorsIfNeeded()
|
||||
@ -155,7 +179,7 @@ import UIKit
|
||||
}
|
||||
}
|
||||
|
||||
public func didSelectCell(atIndex indexPath: IndexPath, delegateObject: MVMCoreUIDelegateObject?, additionalData: [AnyHashable : Any]?) {
|
||||
public func didSelectCell(atIndex indexPath: IndexPath, delegateObject: MVMCoreUIDelegateObject?, additionalData: [AnyHashable: Any]?) {
|
||||
if let actionMap = json?.optionalDictionaryForKey("actionMap") {
|
||||
MVMCoreActionHandler.shared()?.handleAction(with: actionMap, additionalData: additionalData, delegateObject: delegateObject)
|
||||
}
|
||||
|
||||
@ -68,7 +68,6 @@ public class StandardHeaderView: ViewConstrainingView {
|
||||
|
||||
if let separatorView = SeparatorView.separatorAdd(to: self, position: SeparatorPositionBot, withHorizontalPadding: 0) {
|
||||
separatorView.setAsHeavy()
|
||||
separatorView.isHidden = true
|
||||
addSubview(separatorView)
|
||||
self.separatorView = separatorView
|
||||
}
|
||||
|
||||
@ -103,8 +103,8 @@ import UIKit
|
||||
addSubview(viewForButtons)
|
||||
self.viewForButtons = viewForButtons
|
||||
|
||||
setupConstraints(forView: viewForButtons)
|
||||
alignCenter()
|
||||
pinView(toSuperView: viewForButtons)
|
||||
alignCenterHorizontal()
|
||||
|
||||
createPrimaryButton()
|
||||
createSecondaryButton()
|
||||
@ -118,8 +118,8 @@ import UIKit
|
||||
createPrimaryButton()
|
||||
if let primaryButton = primaryButton {
|
||||
addSubview(primaryButton)
|
||||
setupConstraints(forView: primaryButton)
|
||||
alignCenter()
|
||||
pinView(toSuperView: primaryButton)
|
||||
alignCenterHorizontal()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -21,4 +21,14 @@
|
||||
/// Can be used to override any standard constraints that may be added.
|
||||
- (BOOL)useStandardConstraints;
|
||||
|
||||
/// Will align if it can.
|
||||
- (void)alignHorizontal:(UIStackViewAlignment)alignment;
|
||||
- (void)alignVertical:(UIStackViewAlignment)alignment;
|
||||
|
||||
/// Containing Views can tell the contained if they should use horizontal margins.
|
||||
- (void)shouldSetHorizontalMargins:(BOOL)shouldSet;
|
||||
|
||||
/// Containing Views can tell the contained if they should use vertical margins.
|
||||
- (void)shouldSetVerticalMargins:(BOOL)shouldSet;
|
||||
|
||||
@end
|
||||
|
||||
@ -205,6 +205,9 @@ B3 -> Legal
|
||||
|
||||
#pragma mark - 2.0 styles
|
||||
|
||||
/// Will style the label based on the string. Accepted values, H1, H2, H3, H32, B1, B2, B3, B20
|
||||
+ (void)styleLabel:(nonnull UILabel *)label withStyle:(nullable NSString *)style;
|
||||
|
||||
+ (void)styleLabelH1:(nonnull UILabel *)label genericScaling:(BOOL)genericScaling;
|
||||
+ (void)styleLabelH1:(nonnull UILabel *)label;
|
||||
|
||||
@ -250,6 +253,9 @@ B3 -> Legal
|
||||
|
||||
#pragma mark - Attributed Strings
|
||||
|
||||
/// Will style the string based on the string. Accepted values, H1, H2, H3, H32, B1, B2, B3, B20
|
||||
+ (nonnull NSAttributedString *)styleGetAttributedString:(nullable NSString *)string withStyle:(nullable NSString *)style;
|
||||
|
||||
+ (nonnull NSAttributedString *)styleGetAttributedString:(nullable NSString *)string font:(nonnull UIFont *)font color:(nonnull UIColor *)color;
|
||||
+ (nonnull NSAttributedString *)styleGetH1AttributedString:(nullable NSString *)string;
|
||||
+ (nonnull NSAttributedString *)styleGetH2AttributedString:(nullable NSString *)string;
|
||||
|
||||
@ -511,6 +511,26 @@ CGFloat const LabelWithInternalButtonLineSpace = 2;
|
||||
|
||||
#pragma mark - 2.0 Styles
|
||||
|
||||
+ (void)styleLabel:(nonnull UILabel *)label withStyle:(nullable NSString *)style {
|
||||
if ([style isEqualToString:@"H1"]) {
|
||||
[self styleLabelH1:label];
|
||||
} else if ([style isEqualToString:@"H2"]) {
|
||||
[self styleLabelH2:label];
|
||||
} else if ([style isEqualToString:@"H3"]) {
|
||||
[self styleLabelH3:label];
|
||||
} else if ([style isEqualToString:@"H32"]) {
|
||||
[self styleLabelH32:label];
|
||||
} else if ([style isEqualToString:@"B1"]) {
|
||||
[self styleLabelB1:label];
|
||||
} else if ([style isEqualToString:@"B3"]) {
|
||||
[self styleLabelB3:label];
|
||||
} else if ([style isEqualToString:@"B20"]) {
|
||||
[self styleLabelB20:label];
|
||||
} else {
|
||||
[self styleLabelB2:label];
|
||||
}
|
||||
}
|
||||
|
||||
+ (void)styleLabelH1:(nonnull UILabel *)label genericScaling:(BOOL)genericScaling {
|
||||
label.font = [MFStyler fontH1:genericScaling];
|
||||
label.textColor = [UIColor blackColor];
|
||||
@ -630,6 +650,26 @@ CGFloat const LabelWithInternalButtonLineSpace = 2;
|
||||
|
||||
#pragma mark - Attributed Strings
|
||||
|
||||
+ (nonnull NSAttributedString *)styleGetAttributedString:(nullable NSString *)string withStyle:(nullable NSString *)style {
|
||||
if ([style isEqualToString:@"H1"]) {
|
||||
return [self styleGetH1AttributedString:string];
|
||||
} else if ([style isEqualToString:@"H2"]) {
|
||||
return [self styleGetH2AttributedString:string];
|
||||
} else if ([style isEqualToString:@"H3"]) {
|
||||
return [self styleGetH3AttributedString:string];
|
||||
} else if ([style isEqualToString:@"H32"]) {
|
||||
return [self styleGetH32AttributedString:string];
|
||||
} else if ([style isEqualToString:@"B1"]) {
|
||||
return [self styleGetB1AttributedString:string];
|
||||
} else if ([style isEqualToString:@"B3"]) {
|
||||
return [self styleGetB3AttributedString:string];
|
||||
} else if ([style isEqualToString:@"B20"]) {
|
||||
return [self styleGetB20AttributedString:string];
|
||||
} else {
|
||||
return [self styleGetB2AttributedString:string];
|
||||
}
|
||||
}
|
||||
|
||||
+ (nonnull NSAttributedString *)styleGetAttributedString:(nullable NSString *)string font:(nonnull UIFont *)font color:(nonnull UIColor *)color {
|
||||
NSAttributedString *attributedString = nil;
|
||||
if (![string isEqual:[NSNull null]] && string.length > 0) {
|
||||
@ -656,6 +696,10 @@ CGFloat const LabelWithInternalButtonLineSpace = 2;
|
||||
return [MFStyler styleGetAttributedString:string font:[MFStyler fontH3] color:[UIColor blackColor]];
|
||||
}
|
||||
|
||||
+ (nonnull NSAttributedString *)styleGetH32AttributedString:(nullable NSString *)string {
|
||||
return [MFStyler styleGetAttributedString:string font:[MFStyler fontH32] color:[UIColor blackColor]];
|
||||
}
|
||||
|
||||
+ (nonnull NSAttributedString *)styleGetB1AttributedString:(nullable NSString *)string {
|
||||
return [MFStyler styleGetAttributedString:string font:[MFStyler fontB1] color:[UIColor blackColor]];
|
||||
}
|
||||
@ -668,6 +712,10 @@ CGFloat const LabelWithInternalButtonLineSpace = 2;
|
||||
return [MFStyler styleGetAttributedString:string font:[MFStyler fontB3] color:[UIColor mfBattleshipGrey]];
|
||||
}
|
||||
|
||||
+ (nonnull NSAttributedString *)styleGetB20AttributedString:(nullable NSString *)string {
|
||||
return [MFStyler styleGetAttributedString:string font:[MFStyler fontB20] color:[UIColor blackColor]];
|
||||
}
|
||||
|
||||
+ (nonnull NSAttributedString *)styleGetDisabledB1AttributedString:(nullable NSString *)string {
|
||||
return [MFStyler styleGetAttributedString:string font:[MFStyler fontB1] color:[UIColor mfLighterGrayColor]];
|
||||
}
|
||||
|
||||
108
MVMCoreUI/Styles/usage.json
Normal file
108
MVMCoreUI/Styles/usage.json
Normal file
@ -0,0 +1,108 @@
|
||||
{
|
||||
"pageType": "usage",
|
||||
"template": "moleculeList",
|
||||
"header": {
|
||||
"moleculeName":"header",
|
||||
"headline":{
|
||||
"moleculeName": "label",
|
||||
"text":"See who's using what."
|
||||
},
|
||||
"body":{
|
||||
"moleculeName": "label",
|
||||
"text":"Data usage was estimated as of Jun 11."
|
||||
},
|
||||
"molecules": [{
|
||||
"moleculeName": "listItem",
|
||||
"molecule" : {
|
||||
"moleculeName":"moleculeStack",
|
||||
"axis": "horizontal",
|
||||
"molecules": [{
|
||||
"percent": 60,
|
||||
"molecule": {
|
||||
"moleculeName": "label",
|
||||
"text": "Johny Verizon\n555.555.5555\nGo Unlimited",
|
||||
"attributes": [{
|
||||
"location": 0,
|
||||
"length": 13,
|
||||
"type": "font",
|
||||
"style": "B1"
|
||||
}]
|
||||
}
|
||||
},{
|
||||
"horizontalAlignment": "trailing",
|
||||
"molecule": {
|
||||
"moleculeName": "label",
|
||||
"text": "4.55 GB"
|
||||
}
|
||||
}]
|
||||
},
|
||||
"actionMap":{
|
||||
"actionType": "openPage",
|
||||
"pageType": "usageDetails",
|
||||
"extraParameters": {
|
||||
"mdn": "5555555555"
|
||||
}
|
||||
}},{
|
||||
"moleculeName": "listItem",
|
||||
"molecule" : {
|
||||
"moleculeName":"moleculeStack",
|
||||
"axis": "horizontal",
|
||||
"molecules": [{
|
||||
"percent": 60,
|
||||
"molecule": {
|
||||
"moleculeName": "label",
|
||||
"text": "Sree Verizon\n555.555.5556",
|
||||
"attributes": [{
|
||||
"location": 0,
|
||||
"length": 12,
|
||||
"type": "font",
|
||||
"style": "B1"
|
||||
}]
|
||||
}
|
||||
},{
|
||||
"horizontalAlignment": "trailing",
|
||||
"molecule": {
|
||||
"moleculeName": "label",
|
||||
"text": "0 GB"
|
||||
}
|
||||
}]
|
||||
},
|
||||
"actionMap":{
|
||||
"actionType": "openPage",
|
||||
"pageType": "usageDetails",
|
||||
"extraParameters": {
|
||||
"mdn": "5555555556"
|
||||
}
|
||||
}},{
|
||||
"moleculeName": "listItem",
|
||||
"molecule" : {
|
||||
"moleculeName":"moleculeStack",
|
||||
"axis": "horizontal",
|
||||
"molecules": [{
|
||||
"percent": 60,
|
||||
"molecule": {
|
||||
"moleculeName": "label",
|
||||
"text": "Vishal Verizon\n555.555.5557\nGo Unlimited",
|
||||
"attributes": [{
|
||||
"location": 0,
|
||||
"length": 14,
|
||||
"type": "font",
|
||||
"style": "B1"
|
||||
}]
|
||||
}
|
||||
},{
|
||||
"horizontalAlignment": "trailing",
|
||||
"molecule": {
|
||||
"moleculeName": "label",
|
||||
"text": "0 GB"
|
||||
}
|
||||
}]
|
||||
},
|
||||
"actionMap":{
|
||||
"actionType": "openPage",
|
||||
"pageType": "usageDetails",
|
||||
"extraParameters": {
|
||||
"mdn": "5555555557"
|
||||
}
|
||||
}}]
|
||||
}
|
||||
@ -10,8 +10,6 @@
|
||||
|
||||
@protocol MoleculeListCellProtocol <NSObject>
|
||||
@optional
|
||||
/// Can override the molecule name for the given molecule. Otherwise we assume value for key moleculeName.
|
||||
+ (nullable NSString *)moleculeName:(nullable NSDictionary *)molecule delegateObject:(nullable MVMCoreUIDelegateObject *)delegateObject;
|
||||
|
||||
/// Can set the separator according to what the moleculeList commands.
|
||||
- (void)setSeparatorWithJSON:(nullable NSDictionary *)json delegateObject:(nullable MVMCoreUIDelegateObject *)delegateObject additionalData:(nullable NSDictionary *)additionalData indexPath:(nonnull NSIndexPath *)indexPath;
|
||||
|
||||
@ -36,7 +36,7 @@ open class MoleculeListTemplate: ThreeLayerTableViewController {
|
||||
override open func viewForBottom() -> UIView {
|
||||
guard let moleculeJSON = loadObject?.pageJSON?.optionalDictionaryForKey("footer"),
|
||||
let molecule = MVMCoreUIMoleculeMappingObject.shared()?.createMolecule(forJSON: moleculeJSON, delegateObject: delegateObject() as? MVMCoreUIDelegateObject, constrainIfNeeded: true) else {
|
||||
return viewForBottom()
|
||||
return super.viewForBottom()
|
||||
}
|
||||
return molecule
|
||||
}
|
||||
@ -117,7 +117,7 @@ open class MoleculeListTemplate: ThreeLayerTableViewController {
|
||||
guard let map = molecule.molecule, let moleculeName = map.optionalStringForKey(KeyMoleculeName), let moleculeClass = MVMCoreUIMoleculeMappingObject.shared()?.moleculeMapping[moleculeName] as? AnyClass else {
|
||||
return nil
|
||||
}
|
||||
if let moleculeClass = moleculeClass as? MoleculeListCellProtocol.Type, let moleculeNameFunc = moleculeClass.moleculeName {
|
||||
if let moleculeClass = moleculeClass as? MVMCoreUIMoleculeViewProtocol.Type, let moleculeNameFunc = moleculeClass.name {
|
||||
return (moleculeNameFunc(map, delegateObject() as? MVMCoreUIDelegateObject), moleculeClass)
|
||||
} else {
|
||||
return (moleculeName, moleculeClass)
|
||||
|
||||
Loading…
Reference in New Issue
Block a user