Merge branch 'bugfix/delegate_decoding' into 'develop'
Bugfix/delegate decoding See merge request BPHV_MIPS/mvm_core!115
This commit is contained in:
commit
c44ce8e068
@ -16,8 +16,12 @@ extension JSONDecoder: AnyDecoder {}
|
||||
extension PropertyListDecoder: AnyDecoder {}
|
||||
|
||||
extension Data {
|
||||
public func decode<T: Decodable>(using decoder: AnyDecoder = JSONDecoder()) throws -> T {
|
||||
return try decoder.decode(T.self, from: self)
|
||||
public func decode<T: Decodable>(using decoder: AnyDecoder = JSONDecoder(), delegateObject: DelegateObject? = nil) throws -> T {
|
||||
if let decoder = decoder as? JSONDecoder {
|
||||
return try decoder.decode(T.self, from: self, delegateObject: delegateObject)
|
||||
} else {
|
||||
return try decoder.decode(T.self, from: self)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -35,10 +39,10 @@ extension KeyedDecodingContainerProtocol {
|
||||
}
|
||||
|
||||
extension Decodable {
|
||||
public static func decode(jsonDict: [String: Any]) throws -> Self {
|
||||
public static func decode(jsonDict: [String: Any], delegateObject: DelegateObject? = nil) throws -> Self {
|
||||
let jsonData = try JSONSerialization.data(withJSONObject: jsonDict)
|
||||
do {
|
||||
return try jsonData.decode()
|
||||
return try jsonData.decode(delegateObject: delegateObject)
|
||||
} catch {
|
||||
throw JSONError.other(error: error)
|
||||
}
|
||||
@ -73,6 +77,14 @@ public extension JSONDecoder {
|
||||
}
|
||||
userInfo.updateValue(delegateObject, forKey: key)
|
||||
}
|
||||
|
||||
/// Decodes a top-level value of the given type from the given JSON representation, and adds the delegate object if provided.
|
||||
func decode<T>(_ type: T.Type, from data: Data, delegateObject: DelegateObject?) throws -> T where T : Decodable {
|
||||
if let delegateObject = delegateObject {
|
||||
try add(delegateObject: delegateObject)
|
||||
}
|
||||
return try decode(T.self, from: data)
|
||||
}
|
||||
}
|
||||
|
||||
public extension Decoder {
|
||||
|
||||
@ -116,6 +116,9 @@
|
||||
// Use this to pop to the root of the stack. If no navigation controller is provided, will use the main one in app delegate.
|
||||
- (void)popToRootAnimated:(BOOL)animated navigationController:(nullable UINavigationController *)navigationController delegate:(nullable NSObject<MVMCorePresentationDelegateProtocol>*)delegate completionHandler:(nullable void (^)(void))completionBlock;
|
||||
|
||||
/// Returns the view controllers of the navigation controller. Takes into account navigation controller animation states.
|
||||
- (nullable NSArray<UIViewController *> *)getViewControllersForNavigationController:(nullable UINavigationController *)navigationController;
|
||||
|
||||
#pragma mark - Presentation Simple
|
||||
|
||||
// Use this to present.
|
||||
|
||||
@ -263,6 +263,27 @@
|
||||
[self startNavigationWithNavigationObject:navigationObject delegate:delegate completionHandler:completionBlock];
|
||||
}
|
||||
|
||||
- (nullable NSArray<UIViewController *> *)getViewControllersForNavigationController:(nullable UINavigationController *)navigationController {
|
||||
// Check if we are currently animating.
|
||||
NSInteger index = [self.navigationQueue.operations indexOfObjectPassingTest:^BOOL(__kindof MVMCoreNavigationOperation * _Nonnull operation, NSUInteger idx, BOOL * _Nonnull stop) {
|
||||
if (operation.isExecuting) {
|
||||
*stop = YES;
|
||||
return YES;
|
||||
} else {
|
||||
return NO;
|
||||
}
|
||||
}];
|
||||
|
||||
if (index != NSNotFound) {
|
||||
MVMCoreNavigationOperation *operation = [self.navigationQueue.operations objectAtIndex:index];
|
||||
if (operation.navigationObject.navigationController == navigationController && operation.futureViewControllers) {
|
||||
// Return the future state if animating.
|
||||
return operation.futureViewControllers;
|
||||
}
|
||||
}
|
||||
return navigationController.viewControllers;
|
||||
}
|
||||
|
||||
#pragma mark - Presentation Simple
|
||||
|
||||
- (void)presentViewController:(nonnull UIViewController *)viewController animated:(BOOL)animated {
|
||||
|
||||
@ -15,8 +15,12 @@
|
||||
|
||||
@interface MVMCoreNavigationOperation : MVMCoreOperation <UINavigationControllerDelegate>
|
||||
|
||||
@property (nonnull, strong, nonatomic) MVMCoreNavigationObject *navigationObject;
|
||||
@property (nullable, weak, nonatomic) NSObject<MVMCorePresentationDelegateProtocol> *delegate;
|
||||
|
||||
/// Used to keep track of future view controller state because .viewControllers is not reliable during animation.
|
||||
@property (nullable, strong, nonatomic) NSArray <UIViewController *>*futureViewControllers;
|
||||
|
||||
- (nullable instancetype)initWithNavigationObject:(nonnull MVMCoreNavigationObject *)navigationObject;
|
||||
|
||||
@end
|
||||
|
||||
@ -17,7 +17,6 @@
|
||||
|
||||
@interface MVMCoreNavigationOperation ()
|
||||
|
||||
@property (strong, nonatomic) MVMCoreNavigationObject *navigationObject;
|
||||
@property (strong, nonatomic) id animatedTransitioning;
|
||||
|
||||
@end
|
||||
@ -95,7 +94,7 @@
|
||||
switch (self.navigationObject.navigationType) {
|
||||
case NavigationTypePush:
|
||||
{
|
||||
[self.navigationObject.navigationController pushViewController:self.navigationObject.viewController animated:self.navigationObject.animated];
|
||||
[self pushViewController];
|
||||
}
|
||||
break;
|
||||
case NavigationTypeSet:
|
||||
@ -114,7 +113,7 @@
|
||||
} else {
|
||||
|
||||
// Just push
|
||||
[self.navigationObject.navigationController pushViewController:self.navigationObject.viewController animated:self.navigationObject.animated];
|
||||
[self pushViewController];
|
||||
}
|
||||
}
|
||||
break;
|
||||
@ -129,13 +128,15 @@
|
||||
} else {
|
||||
|
||||
// Just push
|
||||
[self.navigationObject.navigationController pushViewController:self.navigationObject.viewController animated:self.navigationObject.animated];
|
||||
[self pushViewController];
|
||||
}
|
||||
}
|
||||
break;
|
||||
case NavigationTypePop:
|
||||
{
|
||||
if (self.navigationObject.navigationController.viewControllers.count > 1) {
|
||||
// Although the post animation state is currently fine with pop, store anyway as a precaution
|
||||
self.futureViewControllers = [self.navigationObject.navigationController.viewControllers subarrayWithRange:NSMakeRange(0, self.navigationObject.navigationController.viewControllers.count - 1)];
|
||||
[self.navigationObject.navigationController popViewControllerAnimated:self.navigationObject.animated];
|
||||
} else {
|
||||
[self markAsFinished];
|
||||
@ -179,6 +180,10 @@
|
||||
}
|
||||
|
||||
if (self.navigationObject.viewController && (self.navigationObject.viewController != self.navigationObject.navigationController.topViewController)) {
|
||||
// Store post animation state.
|
||||
NSInteger index = [[self.navigationObject.navigationController viewControllers] indexOfObject:self.navigationObject.viewController];
|
||||
self.futureViewControllers = [self.navigationObject.navigationController.viewControllers subarrayWithRange:NSMakeRange(0, index + 1)];
|
||||
|
||||
[self.navigationObject.navigationController popToViewController:self.navigationObject.viewController animated:self.navigationObject.animated];
|
||||
} else {
|
||||
[self markAsFinished];
|
||||
@ -188,6 +193,9 @@
|
||||
case NavigationTypePopToRoot:
|
||||
{
|
||||
if (self.navigationObject.navigationController.viewControllers.count > 1) {
|
||||
// Store post animation state.
|
||||
self.futureViewControllers = @[self.navigationObject.navigationController.viewControllers.firstObject];
|
||||
|
||||
[self.navigationObject.navigationController popToRootViewControllerAnimated:self.navigationObject.animated];
|
||||
} else {
|
||||
[self markAsFinished];
|
||||
@ -202,8 +210,14 @@
|
||||
}]];
|
||||
}
|
||||
|
||||
- (void)pushViewController {
|
||||
// Although the post animation state is currently fine with push, store anyway as a precaution
|
||||
self.futureViewControllers = [self.navigationObject.navigationController.viewControllers arrayByAddingObject:self.navigationObject.viewController];
|
||||
[self.navigationObject.navigationController pushViewController:self.navigationObject.viewController animated:self.navigationObject.animated];
|
||||
}
|
||||
|
||||
- (void)setViewControllers:(NSArray *)viewControllers {
|
||||
|
||||
self.futureViewControllers = viewControllers;
|
||||
if (![self.navigationObject.navigationController.viewControllers isEqualToArray:viewControllers]) {
|
||||
[self.navigationObject.navigationController setViewControllers:viewControllers animated:self.navigationObject.animated];
|
||||
} else {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user