From 61aecf20790899a0d69948aa7f4a4dcacef633e8 Mon Sep 17 00:00:00 2001 From: "Pfeil, Scott Robert" Date: Fri, 29 May 2020 15:51:27 -0400 Subject: [PATCH 1/8] Tab updates --- MVMCore/MVMCore/Models/ActionType/ActionOpenPageModel.swift | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/MVMCore/MVMCore/Models/ActionType/ActionOpenPageModel.swift b/MVMCore/MVMCore/Models/ActionType/ActionOpenPageModel.swift index ac4d537..feb7b4c 100644 --- a/MVMCore/MVMCore/Models/ActionType/ActionOpenPageModel.swift +++ b/MVMCore/MVMCore/Models/ActionType/ActionOpenPageModel.swift @@ -15,11 +15,13 @@ import Foundation public var extraParameters: JSONValueDictionary? public var analyticsData: JSONValueDictionary? public var presentationStyle: String? + public var tabBarIndex: Int? - public init(pageType: String, _ presentationStyle: String? = nil, _ extraParameters: JSONValueDictionary? = nil, _ analyticsData: JSONValueDictionary? = nil) { + public init(pageType: String, presentationStyle: String? = nil, extraParameters: JSONValueDictionary? = nil, analyticsData: JSONValueDictionary? = nil, tabBarIndex: Int? = nil) { self.pageType = pageType self.presentationStyle = presentationStyle self.extraParameters = extraParameters self.analyticsData = analyticsData + self.tabBarIndex = tabBarIndex } } From 90d2df6fb03c7487a890473abb5734f1c5952ea1 Mon Sep 17 00:00:00 2001 From: "Pfeil, Scott Robert" Date: Tue, 2 Jun 2020 13:35:07 -0400 Subject: [PATCH 2/8] iteration one --- .../MVMCoreDismissViewControllerOperation.h | 3 + .../MVMCoreNavigationHandler.h | 12 ++- .../MVMCoreNavigationHandler.m | 91 +++++++++++++++++-- .../MVMCoreNavigationOperation.m | 4 + 4 files changed, 101 insertions(+), 9 deletions(-) diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreDismissViewControllerOperation.h b/MVMCore/MVMCore/PresentationHandling/MVMCoreDismissViewControllerOperation.h index 05fbd92..60b11e0 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreDismissViewControllerOperation.h +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreDismissViewControllerOperation.h @@ -9,9 +9,12 @@ #import "MVMCoreOperation.h" #import +#import @interface MVMCoreDismissViewControllerOperation : MVMCoreOperation +@property (nullable, weak, nonatomic) NSObject *delegate; + // Goes up the presentation chain to only dismiss the top presented. - (nullable instancetype)initAndDismissTopViewController:(nullable UIViewController *)viewController animated:(BOOL)animated; diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h index 32789d0..c235315 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h @@ -14,7 +14,7 @@ @class MVMCoreNavigationObject; @class MVMCoreLoadObject; -@interface MVMCoreNavigationHandler : NSObject +@interface MVMCoreNavigationHandler : NSObject // Returns the shared instance of this singleton + (nullable instancetype)sharedNavigationHandler; @@ -25,6 +25,8 @@ // reference to main navigation controller @property (nullable, weak, nonatomic) UINavigationController *navigationController; +/// A list of possible delegates looking for information. +@property (nonnull, strong, nonatomic) NSPointerArray *delegates; // Will navigate appropriately based on the load style - (void)navigateWithLoadObject:(nullable MVMCoreLoadObject *)loadObject viewController:(nonnull UIViewController *)viewController delegate:(nullable NSObject*)delegate completionHandler:(nullable void (^)(void))completionBlock; @@ -35,6 +37,14 @@ // pops or dimisses as needed - (void)removeCurrentViewController; +#pragma mark - Delegate Handling + +/// Adds a listener for navigation delegate functions +- (void)addDelegate:(nonnull id )delegate; + +/// Removes a listener for navigation delegate functions +- (void)removeDelegate:(nullable id )delegate; + #pragma mark - Navigation Simple // Uses the default navigation controller in app delegate diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m index 260a34f..a6f43d3 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m @@ -19,7 +19,7 @@ #import "MVMCoreLoadingOverlayHandler.h" #import "MVMCoreDispatchUtility.h" -@interface MVMCoreNavigationHandler () +@interface MVMCoreNavigationHandler() @property (strong, nonatomic) NSOperationQueue *navigationQueue; @property (strong, nonatomic) NSOperationQueue *presentationQueue; @@ -47,10 +47,14 @@ self.presentationQueue = [[NSOperationQueue alloc] init]; self.presentationQueue.maxConcurrentOperationCount = 1; + + self.delegates = (NSPointerArray *)[NSPointerArray weakObjectsPointerArray]; } return self; } +#pragma mark - Navigation Helpers + - (void)navigateWithLoadObject:(nullable MVMCoreLoadObject *)loadObject viewController:(nonnull UIViewController *)viewController delegate:(nullable NSObject*)delegate completionHandler:(nullable void (^)(void))completionBlock { BOOL shouldAnimate = !loadObject.requestParameters.shouldNotAnimatePush; @@ -97,8 +101,8 @@ navigationObject.stopLoadingOverlay = YES; MVMCoreNavigationOperation *navigationOperation = [[MVMCoreNavigationOperation alloc] initWithNavigationObject:navigationObject]; - navigationOperation.delegate = delegate; - navigationOperation.completionBlock = completionBlock; + navigationOperation.delegate = self; + navigationOperation.completionBlock = [self getCompletionAndHandleDelegate:delegate completionHandler:completionBlock]; [self.navigationQueue addOperation:navigationOperation]; } @@ -284,8 +288,8 @@ [MVMCoreLoggingHandler addErrorToLog:error]; } else { MVMCorePresentViewControllerOperation *operation = [[MVMCorePresentViewControllerOperation alloc] initWithPresentingViewController:controllerToPresentOn presentedViewController:viewController animated:animated]; - operation.delegate = delegate; - operation.completionBlock = completionBlock; + operation.delegate = self; + operation.completionBlock = [self getCompletionAndHandleDelegate:delegate completionHandler:completionBlock]; [self.presentationQueue addOperation:operation]; } }]; @@ -296,7 +300,8 @@ // Dismiss on the main navigation controller. UIViewController *controllerToPresentOn = self.viewControllerToPresentOn ?: [UIApplication sharedApplication].keyWindow.rootViewController; MVMCoreDismissViewControllerOperation *operation = [[MVMCoreDismissViewControllerOperation alloc] initAndDismissTopViewController:controllerToPresentOn animated:animated]; - operation.completionBlock = completionBlock; + operation.delegate = self; + operation.completionBlock = [self getCompletionAndHandleDelegate:delegate completionHandler:completionBlock]; [[NSOperationQueue mainQueue] addOperation:operation]; }]; } @@ -304,7 +309,8 @@ - (void)dismissViewController:(nonnull UIViewController *)viewController animated:(BOOL)animated delegate:(nullable NSObject*)delegate completionHandler:(nullable void (^)(void))completionBlock { MVMCoreDismissViewControllerOperation *operation = [[MVMCoreDismissViewControllerOperation alloc] initAndDismissViewController:viewController animated:animated]; - operation.completionBlock = completionBlock; + operation.delegate = self; + operation.completionBlock = [self getCompletionAndHandleDelegate:delegate completionHandler:completionBlock]; [[NSOperationQueue mainQueue] addOperation:operation]; } @@ -313,9 +319,78 @@ // Dismiss on the main navigation controller. UIViewController *controllerToPresentOn = self.viewControllerToPresentOn ?: [UIApplication sharedApplication].keyWindow.rootViewController; MVMCoreDismissViewControllerOperation *operation = [[MVMCoreDismissViewControllerOperation alloc] initAndDismissViewController:controllerToPresentOn animated:animated]; - operation.completionBlock = completionBlock; + operation.delegate = self; + operation.completionBlock = [self getCompletionAndHandleDelegate:delegate completionHandler:completionBlock]; [[NSOperationQueue mainQueue] addOperation:operation]; }]; } +#pragma mark - Delegate Handling + +- (void)addDelegate:(nonnull id )delegate { + [self.delegates addPointer:(__bridge void *)(delegate)]; +} + +- (void)removeDelegate:(nullable id )delegate { + NSUInteger index = NSNotFound; + for (NSUInteger i = 0; i < self.delegates.count; i++) { + if (delegate == [self.delegates pointerAtIndex:i]) { + index = i; + break; + } + } + if (index != NSNotFound) { + [self.delegates removePointerAtIndex:index]; + } +} + +- (nullable void (^)(void))getCompletionAndHandleDelegate:(nullable NSObject*)delegate completionHandler:(nullable void (^)(void))completionBlock { + if (!delegate) { + return completionBlock; + } + + [self addDelegate:delegate]; + __weak typeof(delegate) weakDelegate = delegate; + __weak typeof(self) weakSelf = self; + return ^void() { + [weakSelf removeDelegate:weakDelegate]; + completionBlock(); + }; +} + +// Below functions forward to all delegates. +- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated { + for (id delegate in self.delegates) { + if (delegate && [delegate respondsToSelector:@selector(navigationController:willDisplayViewController:)]) { + [delegate navigationController:navigationController willDisplayViewController:viewController]; + } + } +} + +- (void)navigationController:(UINavigationController *)navigationController didShowViewController:(UIViewController *)viewController animated:(BOOL)animated { + for (id delegate in self.delegates) { + if (delegate && [delegate respondsToSelector:@selector(navigationController:displayedViewController:)]) { + [delegate navigationController:navigationController displayedViewController:viewController]; + } + } + // Legacy Notifier: Notify that page has changed + dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ + [[NSNotificationCenter defaultCenter] postNotificationName:MVMCoreNotificationViewControllerChanged object:nil]; + }); +} + +- (nullable id )navigationController:(UINavigationController *)navigationController animationControllerForOperation:(UINavigationControllerOperation)operation fromViewController:(UIViewController *)fromVC toViewController:(UIViewController *)toVC { + if (delegate && [delegate respondsToSelector:@selector(navigationController:animationControllerForOperation:fromViewController:toViewController:)]) { + id animatedTransitioning = [self.delegate navigationController:navigationController animationControllerForOperation:operation fromViewController:fromVC toViewController:toVC]; + if ([animatedTransitioning conformsToProtocol:@protocol(MVMCoreViewControllerAnimatedTransitioning)]) { + [animatedTransitioning addObserver:self forKeyPath:@"interactiveTransitionCanceled" options:NSKeyValueObservingOptionOld | NSKeyValueObservingOptionNew context:nil]; + self.animatedTransitioning = animatedTransitioning; + } + return animatedTransitioning; + } else { + return nil; + } + +} + @end diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m index 5a39b73..ff6e581 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m @@ -13,6 +13,7 @@ #import "MVMCoreLoggingHandler.h" #import "MVMCoreLoadingOverlayHandler.h" #import "MVMCoreViewControllerAnimatedTransitioning.h" +#import "MVMCoreNavigationHandler.h" @interface MVMCoreNavigationOperation () @@ -225,6 +226,8 @@ [super markAsFinished]; } +#pragma mark - Delegate + - (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated { if (self.navigationObject.stopLoadingOverlay) { [[MVMCoreLoadingOverlayHandler sharedLoadingOverlay] stopLoading:YES]; @@ -234,6 +237,7 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(navigationController:willDisplayViewController:)]) { [self.delegate navigationController:navigationController willDisplayViewController:viewController]; } + } - (void)navigationController:(UINavigationController *)navigationController didShowViewController:(UIViewController *)viewController animated:(BOOL)animated { From e21e5b520b9380ef2e9910463c629b524ba05679 Mon Sep 17 00:00:00 2001 From: "Pfeil, Scott Robert" Date: Tue, 2 Jun 2020 14:04:44 -0400 Subject: [PATCH 3/8] Notify other listeners/delegates --- .../MVMCoreDismissViewControllerOperation.h | 3 - .../MVMCoreNavigationHandler.m | 106 +++++------------- .../MVMCoreNavigationOperation.m | 13 ++- .../MVMCorePresentAnimationOperation.m | 11 ++ .../MVMCorePresentationDelegateProtocol.h | 6 + 5 files changed, 55 insertions(+), 84 deletions(-) diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreDismissViewControllerOperation.h b/MVMCore/MVMCore/PresentationHandling/MVMCoreDismissViewControllerOperation.h index 60b11e0..05fbd92 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreDismissViewControllerOperation.h +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreDismissViewControllerOperation.h @@ -9,12 +9,9 @@ #import "MVMCoreOperation.h" #import -#import @interface MVMCoreDismissViewControllerOperation : MVMCoreOperation -@property (nullable, weak, nonatomic) NSObject *delegate; - // Goes up the presentation chain to only dismiss the top presented. - (nullable instancetype)initAndDismissTopViewController:(nullable UIViewController *)viewController animated:(BOOL)animated; diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m index a6f43d3..c6833d9 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m @@ -19,7 +19,7 @@ #import "MVMCoreLoadingOverlayHandler.h" #import "MVMCoreDispatchUtility.h" -@interface MVMCoreNavigationHandler() +@interface MVMCoreNavigationHandler () @property (strong, nonatomic) NSOperationQueue *navigationQueue; @property (strong, nonatomic) NSOperationQueue *presentationQueue; @@ -53,6 +53,25 @@ return self; } +#pragma mark - Delegate Handling + +- (void)addDelegate:(nonnull id )delegate { + [self.delegates addPointer:(__bridge void *)(delegate)]; +} + +- (void)removeDelegate:(nullable id )delegate { + NSUInteger index = NSNotFound; + for (NSUInteger i = 0; i < self.delegates.count; i++) { + if (delegate == [self.delegates pointerAtIndex:i]) { + index = i; + break; + } + } + if (index != NSNotFound) { + [self.delegates removePointerAtIndex:index]; + } +} + #pragma mark - Navigation Helpers - (void)navigateWithLoadObject:(nullable MVMCoreLoadObject *)loadObject viewController:(nonnull UIViewController *)viewController delegate:(nullable NSObject*)delegate completionHandler:(nullable void (^)(void))completionBlock { @@ -101,8 +120,8 @@ navigationObject.stopLoadingOverlay = YES; MVMCoreNavigationOperation *navigationOperation = [[MVMCoreNavigationOperation alloc] initWithNavigationObject:navigationObject]; - navigationOperation.delegate = self; - navigationOperation.completionBlock = [self getCompletionAndHandleDelegate:delegate completionHandler:completionBlock]; + navigationOperation.delegate = delegate; + navigationOperation.completionBlock = completionBlock; [self.navigationQueue addOperation:navigationOperation]; } @@ -288,8 +307,8 @@ [MVMCoreLoggingHandler addErrorToLog:error]; } else { MVMCorePresentViewControllerOperation *operation = [[MVMCorePresentViewControllerOperation alloc] initWithPresentingViewController:controllerToPresentOn presentedViewController:viewController animated:animated]; - operation.delegate = self; - operation.completionBlock = [self getCompletionAndHandleDelegate:delegate completionHandler:completionBlock]; + operation.delegate = delegate; + operation.completionBlock = completionBlock; [self.presentationQueue addOperation:operation]; } }]; @@ -300,8 +319,7 @@ // Dismiss on the main navigation controller. UIViewController *controllerToPresentOn = self.viewControllerToPresentOn ?: [UIApplication sharedApplication].keyWindow.rootViewController; MVMCoreDismissViewControllerOperation *operation = [[MVMCoreDismissViewControllerOperation alloc] initAndDismissTopViewController:controllerToPresentOn animated:animated]; - operation.delegate = self; - operation.completionBlock = [self getCompletionAndHandleDelegate:delegate completionHandler:completionBlock]; + operation.completionBlock = completionBlock; [[NSOperationQueue mainQueue] addOperation:operation]; }]; } @@ -309,8 +327,7 @@ - (void)dismissViewController:(nonnull UIViewController *)viewController animated:(BOOL)animated delegate:(nullable NSObject*)delegate completionHandler:(nullable void (^)(void))completionBlock { MVMCoreDismissViewControllerOperation *operation = [[MVMCoreDismissViewControllerOperation alloc] initAndDismissViewController:viewController animated:animated]; - operation.delegate = self; - operation.completionBlock = [self getCompletionAndHandleDelegate:delegate completionHandler:completionBlock]; + operation.completionBlock = completionBlock; [[NSOperationQueue mainQueue] addOperation:operation]; } @@ -319,78 +336,9 @@ // Dismiss on the main navigation controller. UIViewController *controllerToPresentOn = self.viewControllerToPresentOn ?: [UIApplication sharedApplication].keyWindow.rootViewController; MVMCoreDismissViewControllerOperation *operation = [[MVMCoreDismissViewControllerOperation alloc] initAndDismissViewController:controllerToPresentOn animated:animated]; - operation.delegate = self; - operation.completionBlock = [self getCompletionAndHandleDelegate:delegate completionHandler:completionBlock]; + operation.completionBlock = completionBlock; [[NSOperationQueue mainQueue] addOperation:operation]; }]; } -#pragma mark - Delegate Handling - -- (void)addDelegate:(nonnull id )delegate { - [self.delegates addPointer:(__bridge void *)(delegate)]; -} - -- (void)removeDelegate:(nullable id )delegate { - NSUInteger index = NSNotFound; - for (NSUInteger i = 0; i < self.delegates.count; i++) { - if (delegate == [self.delegates pointerAtIndex:i]) { - index = i; - break; - } - } - if (index != NSNotFound) { - [self.delegates removePointerAtIndex:index]; - } -} - -- (nullable void (^)(void))getCompletionAndHandleDelegate:(nullable NSObject*)delegate completionHandler:(nullable void (^)(void))completionBlock { - if (!delegate) { - return completionBlock; - } - - [self addDelegate:delegate]; - __weak typeof(delegate) weakDelegate = delegate; - __weak typeof(self) weakSelf = self; - return ^void() { - [weakSelf removeDelegate:weakDelegate]; - completionBlock(); - }; -} - -// Below functions forward to all delegates. -- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated { - for (id delegate in self.delegates) { - if (delegate && [delegate respondsToSelector:@selector(navigationController:willDisplayViewController:)]) { - [delegate navigationController:navigationController willDisplayViewController:viewController]; - } - } -} - -- (void)navigationController:(UINavigationController *)navigationController didShowViewController:(UIViewController *)viewController animated:(BOOL)animated { - for (id delegate in self.delegates) { - if (delegate && [delegate respondsToSelector:@selector(navigationController:displayedViewController:)]) { - [delegate navigationController:navigationController displayedViewController:viewController]; - } - } - // Legacy Notifier: Notify that page has changed - dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ - [[NSNotificationCenter defaultCenter] postNotificationName:MVMCoreNotificationViewControllerChanged object:nil]; - }); -} - -- (nullable id )navigationController:(UINavigationController *)navigationController animationControllerForOperation:(UINavigationControllerOperation)operation fromViewController:(UIViewController *)fromVC toViewController:(UIViewController *)toVC { - if (delegate && [delegate respondsToSelector:@selector(navigationController:animationControllerForOperation:fromViewController:toViewController:)]) { - id animatedTransitioning = [self.delegate navigationController:navigationController animationControllerForOperation:operation fromViewController:fromVC toViewController:toVC]; - if ([animatedTransitioning conformsToProtocol:@protocol(MVMCoreViewControllerAnimatedTransitioning)]) { - [animatedTransitioning addObserver:self forKeyPath:@"interactiveTransitionCanceled" options:NSKeyValueObservingOptionOld | NSKeyValueObservingOptionNew context:nil]; - self.animatedTransitioning = animatedTransitioning; - } - return animatedTransitioning; - } else { - return nil; - } - -} - @end diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m index ff6e581..adc28cf 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m @@ -237,7 +237,11 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(navigationController:willDisplayViewController:)]) { [self.delegate navigationController:navigationController willDisplayViewController:viewController]; } - + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates) { + if (delegate && [delegate respondsToSelector:@selector(navigationController:willDisplayViewController:)]) { + [delegate navigationController:navigationController willDisplayViewController:viewController]; + } + } } - (void)navigationController:(UINavigationController *)navigationController didShowViewController:(UIViewController *)viewController animated:(BOOL)animated { @@ -245,8 +249,13 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(navigationController:displayedViewController:)]) { [self.delegate navigationController:navigationController displayedViewController:viewController]; } + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates) { + if (delegate && [delegate respondsToSelector:@selector(navigationController:displayedViewController:)]) { + [delegate navigationController:navigationController displayedViewController:viewController]; + } + } [self markAsFinished]; - // Notify that page has changed + // Legacy notify that page has changed dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ [[NSNotificationCenter defaultCenter] postNotificationName:MVMCoreNotificationViewControllerChanged object:nil]; }); diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m b/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m index 797346c..a93ce12 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m @@ -7,6 +7,7 @@ // #import "MVMCorePresentAnimationOperation.h" +#import "MVMCoreNavigationHandler.h" @interface MVMCorePresentAnimationOperation () @@ -39,12 +40,22 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(viewController:willPresentViewController:)]) { [self.delegate viewController:self.presentingViewController willPresentViewController:self.presentedViewController]; } + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates) { + if (delegate && [delegate respondsToSelector:@selector(viewController:willPresentViewController:)]) { + [delegate viewController:self.presentingViewController willPresentViewController:self.presentedViewController]; + } + } [self.presentingViewController presentViewController:self.presentedViewController animated:self.animate completion:^{ if (self.delegate && [self.delegate respondsToSelector:@selector(viewController:didPresentViewController:)]) { [self.delegate viewController:self.presentingViewController didPresentViewController:self.presentedViewController]; } + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates) { + if (delegate && [delegate respondsToSelector:@selector(viewController:didPresentViewController:)]) { + [delegate viewController:self.presentingViewController didPresentViewController:self.presentedViewController]; + } + } [self markAsFinished]; }]; } diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCorePresentationDelegateProtocol.h b/MVMCore/MVMCore/PresentationHandling/MVMCorePresentationDelegateProtocol.h index 8dc27f4..6acf505 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCorePresentationDelegateProtocol.h +++ b/MVMCore/MVMCore/PresentationHandling/MVMCorePresentationDelegateProtocol.h @@ -37,4 +37,10 @@ // Called when a view controller did be present on another - (void)viewController:(nonnull UIViewController *)presentingViewController didPresentViewController:(nonnull UIViewController *)presentedViewController; +// Called when a view controller will be dismissed off another view controller +- (void)willDismissViewController:(nonnull UIViewController *)viewController; + +// Called when a view controller did dismiss +- (void)didDismissViewController:(nonnull UIViewController *)viewController; + @end From b95cb758c830672f6b780ed0563fd7f7599d29a9 Mon Sep 17 00:00:00 2001 From: "Pfeil, Scott Robert" Date: Tue, 2 Jun 2020 14:44:54 -0400 Subject: [PATCH 4/8] change to hashtable --- .../MVMCoreNavigationHandler.h | 2 +- .../MVMCoreNavigationHandler.m | 15 +++++---------- .../MVMCoreNavigationOperation.m | 4 ++-- .../MVMCorePresentAnimationOperation.m | 4 ++-- 4 files changed, 10 insertions(+), 15 deletions(-) diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h index c235315..13df1fa 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h @@ -26,7 +26,7 @@ @property (nullable, weak, nonatomic) UINavigationController *navigationController; /// A list of possible delegates looking for information. -@property (nonnull, strong, nonatomic) NSPointerArray *delegates; +@property (nonnull, strong, nonatomic) NSHashTable *delegates; // Will navigate appropriately based on the load style - (void)navigateWithLoadObject:(nullable MVMCoreLoadObject *)loadObject viewController:(nonnull UIViewController *)viewController delegate:(nullable NSObject*)delegate completionHandler:(nullable void (^)(void))completionBlock; diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m index c6833d9..107f03f 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m @@ -48,7 +48,7 @@ self.presentationQueue = [[NSOperationQueue alloc] init]; self.presentationQueue.maxConcurrentOperationCount = 1; - self.delegates = (NSPointerArray *)[NSPointerArray weakObjectsPointerArray]; + self.delegates = (NSHashTable *)[NSHashTable weakObjectsHashTable]; } return self; } @@ -56,20 +56,15 @@ #pragma mark - Delegate Handling - (void)addDelegate:(nonnull id )delegate { - [self.delegates addPointer:(__bridge void *)(delegate)]; + [self.delegates addObject:delegate]; } - (void)removeDelegate:(nullable id )delegate { - NSUInteger index = NSNotFound; - for (NSUInteger i = 0; i < self.delegates.count; i++) { - if (delegate == [self.delegates pointerAtIndex:i]) { - index = i; - break; + for (id currentDelegate in [self.delegates allObjects]) { + if (currentDelegate == delegate) { + [self.delegates removeObject:delegate]; } } - if (index != NSNotFound) { - [self.delegates removePointerAtIndex:index]; - } } #pragma mark - Navigation Helpers diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m index adc28cf..999e5d2 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m @@ -237,7 +237,7 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(navigationController:willDisplayViewController:)]) { [self.delegate navigationController:navigationController willDisplayViewController:viewController]; } - for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates) { + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { if (delegate && [delegate respondsToSelector:@selector(navigationController:willDisplayViewController:)]) { [delegate navigationController:navigationController willDisplayViewController:viewController]; } @@ -249,7 +249,7 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(navigationController:displayedViewController:)]) { [self.delegate navigationController:navigationController displayedViewController:viewController]; } - for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates) { + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { if (delegate && [delegate respondsToSelector:@selector(navigationController:displayedViewController:)]) { [delegate navigationController:navigationController displayedViewController:viewController]; } diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m b/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m index a93ce12..85c533f 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m @@ -40,7 +40,7 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(viewController:willPresentViewController:)]) { [self.delegate viewController:self.presentingViewController willPresentViewController:self.presentedViewController]; } - for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates) { + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { if (delegate && [delegate respondsToSelector:@selector(viewController:willPresentViewController:)]) { [delegate viewController:self.presentingViewController willPresentViewController:self.presentedViewController]; } @@ -51,7 +51,7 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(viewController:didPresentViewController:)]) { [self.delegate viewController:self.presentingViewController didPresentViewController:self.presentedViewController]; } - for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates) { + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { if (delegate && [delegate respondsToSelector:@selector(viewController:didPresentViewController:)]) { [delegate viewController:self.presentingViewController didPresentViewController:self.presentedViewController]; } From 31331ead2c8535a1d09037c72a0ee55c049b7f22 Mon Sep 17 00:00:00 2001 From: "Pfeil, Scott Robert" Date: Tue, 2 Jun 2020 15:59:26 -0400 Subject: [PATCH 5/8] review comment update --- .../MVMCore/PresentationHandling/MVMCoreNavigationHandler.h | 2 +- .../MVMCore/PresentationHandling/MVMCoreNavigationHandler.m | 6 +----- .../PresentationHandling/MVMCoreNavigationOperation.m | 4 ++-- .../PresentationHandling/MVMCorePresentAnimationOperation.m | 4 ++-- .../MVMCorePresentationDelegateProtocol.h | 6 ------ 5 files changed, 6 insertions(+), 16 deletions(-) diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h index 13df1fa..2810b3c 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.h @@ -26,7 +26,7 @@ @property (nullable, weak, nonatomic) UINavigationController *navigationController; /// A list of possible delegates looking for information. -@property (nonnull, strong, nonatomic) NSHashTable *delegates; +@property (nonnull, strong, nonatomic) NSHashTable *delegates; // Will navigate appropriately based on the load style - (void)navigateWithLoadObject:(nullable MVMCoreLoadObject *)loadObject viewController:(nonnull UIViewController *)viewController delegate:(nullable NSObject*)delegate completionHandler:(nullable void (^)(void))completionBlock; diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m index 107f03f..5849d9f 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationHandler.m @@ -60,11 +60,7 @@ } - (void)removeDelegate:(nullable id )delegate { - for (id currentDelegate in [self.delegates allObjects]) { - if (currentDelegate == delegate) { - [self.delegates removeObject:delegate]; - } - } + [self.delegates removeObject:delegate]; } #pragma mark - Navigation Helpers diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m index 999e5d2..bdd32eb 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCoreNavigationOperation.m @@ -237,7 +237,7 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(navigationController:willDisplayViewController:)]) { [self.delegate navigationController:navigationController willDisplayViewController:viewController]; } - for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { if (delegate && [delegate respondsToSelector:@selector(navigationController:willDisplayViewController:)]) { [delegate navigationController:navigationController willDisplayViewController:viewController]; } @@ -249,7 +249,7 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(navigationController:displayedViewController:)]) { [self.delegate navigationController:navigationController displayedViewController:viewController]; } - for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { if (delegate && [delegate respondsToSelector:@selector(navigationController:displayedViewController:)]) { [delegate navigationController:navigationController displayedViewController:viewController]; } diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m b/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m index 85c533f..206dd95 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m +++ b/MVMCore/MVMCore/PresentationHandling/MVMCorePresentAnimationOperation.m @@ -40,7 +40,7 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(viewController:willPresentViewController:)]) { [self.delegate viewController:self.presentingViewController willPresentViewController:self.presentedViewController]; } - for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { if (delegate && [delegate respondsToSelector:@selector(viewController:willPresentViewController:)]) { [delegate viewController:self.presentingViewController willPresentViewController:self.presentedViewController]; } @@ -51,7 +51,7 @@ if (self.delegate && [self.delegate respondsToSelector:@selector(viewController:didPresentViewController:)]) { [self.delegate viewController:self.presentingViewController didPresentViewController:self.presentedViewController]; } - for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { + for (NSObject *delegate in [MVMCoreNavigationHandler sharedNavigationHandler].delegates.allObjects) { if (delegate && [delegate respondsToSelector:@selector(viewController:didPresentViewController:)]) { [delegate viewController:self.presentingViewController didPresentViewController:self.presentedViewController]; } diff --git a/MVMCore/MVMCore/PresentationHandling/MVMCorePresentationDelegateProtocol.h b/MVMCore/MVMCore/PresentationHandling/MVMCorePresentationDelegateProtocol.h index 6acf505..8dc27f4 100644 --- a/MVMCore/MVMCore/PresentationHandling/MVMCorePresentationDelegateProtocol.h +++ b/MVMCore/MVMCore/PresentationHandling/MVMCorePresentationDelegateProtocol.h @@ -37,10 +37,4 @@ // Called when a view controller did be present on another - (void)viewController:(nonnull UIViewController *)presentingViewController didPresentViewController:(nonnull UIViewController *)presentedViewController; -// Called when a view controller will be dismissed off another view controller -- (void)willDismissViewController:(nonnull UIViewController *)viewController; - -// Called when a view controller did dismiss -- (void)didDismissViewController:(nonnull UIViewController *)viewController; - @end From 1fd631f0049e0876b775ed84f186278fc8f7492f Mon Sep 17 00:00:00 2001 From: "Pfeil, Scott Robert" Date: Wed, 17 Jun 2020 10:28:00 -0400 Subject: [PATCH 6/8] image registry --- MVMCore/MVMCore/OtherHandlers/MVMCoreCache.h | 13 +++++- MVMCore/MVMCore/OtherHandlers/MVMCoreCache.m | 43 +++++++++++++++++--- 2 files changed, 48 insertions(+), 8 deletions(-) diff --git a/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.h b/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.h index 9d97932..0289b31 100644 --- a/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.h +++ b/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.h @@ -20,6 +20,9 @@ typedef void(^MVMCoreGetImageBlock)(UIImage * _Nullable, NSData * _Nullable, BOO @property (nullable, strong, nonatomic, readonly) NSDictionary *staticStringCache; @property (nonnull, strong, nonatomic) NSOperationQueue *completionQueue; +/// Contains all bundles to search for images. +@property (nonnull, strong, nonatomic) NSMutableArray* imageBundles; + // Returns the shared instance of this singleton + (nullable instancetype)sharedCache; @@ -108,8 +111,14 @@ typedef void(^MVMCoreGetImageBlock)(UIImage * _Nullable, NSData * _Nullable, BOO #pragma mark Image Functions -// Subclass to return the bundle to use -- (nonnull NSBundle *)bundleToUseForImages; +/// Register a bundle as one to search for images in. +- (void)registerBundleForImages:(nonnull NSBundle *)bundle; + +/// Tries to create an image from a registered bundle. +- (nullable UIImage *)getImageFromRegisteredBundles:(nonnull NSString *)imageName; + +/// Tries to get image data from a registered bundle. Can specify the type of extension if desired. +- (nullable NSData *)getImageDataFromRegisteredBundles:(nonnull NSString *)imageName type:(nullable NSString *)type; /// Returns if the imageName pointing to a local image. Currently just checks if it begins with http. + (BOOL)isHostedImage:(nullable NSString *)imageName; diff --git a/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.m b/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.m index 0d552c3..3ea004d 100644 --- a/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.m +++ b/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.m @@ -57,6 +57,8 @@ static NSString * const STATIC_CACHE_COMPONENT = @"StaticCache.txt"; self.moduleQueue.maxConcurrentOperationCount = 1; self.imageCacheQueue = dispatch_queue_create("imgCache", DISPATCH_QUEUE_CONCURRENT); + + self.imageBundles = [NSMutableArray array]; } return self; } @@ -374,8 +376,30 @@ static NSString * const STATIC_CACHE_COMPONENT = @"StaticCache.txt"; #pragma mark - Image Functions -- (nonnull NSBundle *)bundleToUseForImages { - return [MVMCoreGetterUtility bundleForMVMCore]; +- (void)registerBundleForImages:(nonnull NSBundle *)bundle { + [self.imageBundles addObject:bundle]; +} + +- (nullable UIImage *)getImageFromRegisteredBundles:(nonnull NSString *)imageName { + UIImage *image = nil; + for (NSBundle *bundle in self.imageBundles) { + image = [UIImage imageNamed:imageName inBundle:bundle withConfiguration:nil]; + if (image) { + break; + } + } + return image; +} + +- (nullable NSData *)getImageDataFromRegisteredBundles:(nonnull NSString *)imageName type:(nullable NSString *)type { + NSData *imageData = nil; + for (NSBundle *bundle in self.imageBundles) { + imageData = [NSData dataWithContentsOfFile:[bundle pathForResource:imageName ofType:type]]; + if (imageData) { + break; + } + } + return imageData; } - (NSMutableDictionary *)imgCache { @@ -487,8 +511,11 @@ static NSString * const STATIC_CACHE_COMPONENT = @"StaticCache.txt"; // Try Local. Check in memory cache imageData = [self getCachedDataWithName:pathOrName]; if (!imageData) { - NSBundle *imageBundle = localBundle ? : [self bundleToUseForImages]; - imageData = [NSData dataWithContentsOfFile:[imageBundle pathForResource:pathOrName ofType:@"gif"]]; + if (localBundle) { + imageData = [NSData dataWithContentsOfFile:[localBundle pathForResource:pathOrName ofType:@"gif"]]; + } else { + imageData = [self getImageDataFromRegisteredBundles:pathOrName type:@"gif"]; + } if (imageData) { [self addDataToCache:imageData withName:pathOrName]; } @@ -525,7 +552,11 @@ static NSString * const STATIC_CACHE_COMPONENT = @"StaticCache.txt"; // Try native image. Check in memory cache image = [self getCachedImageWithName:pathOrName]; if (!image) { - image = [UIImage imageNamed:pathOrName inBundle:localBundle ?: [self bundleToUseForImages] compatibleWithTraitCollection:nil]; + if (localBundle) { + image = [UIImage imageNamed:pathOrName inBundle:localBundle compatibleWithTraitCollection:nil]; + } else { + image = [self getImageFromRegisteredBundles:pathOrName]; + } if (image) { [self addImageToCache:image withName:pathOrName]; } @@ -585,7 +616,7 @@ static NSString * const STATIC_CACHE_COMPONENT = @"StaticCache.txt"; image = [self getCachedImageWithName:fallbackImageName]; if (!image) { - image = [UIImage imageNamed:fallbackImageName inBundle:[self bundleToUseForImages] compatibleWithTraitCollection:nil]; + image = [self getImageFromRegisteredBundles:fallbackImageName]; if (image) { // Cache the fallback image if not already cached. From 921fbe02fad35e357037fb721082f5feb02b72d0 Mon Sep 17 00:00:00 2001 From: "Pfeil, Scott Robert" Date: Wed, 17 Jun 2020 11:18:11 -0400 Subject: [PATCH 7/8] update --- MVMCore/MVMCore/OtherHandlers/MVMCoreCache.m | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.m b/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.m index 3ea004d..7d5efbb 100644 --- a/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.m +++ b/MVMCore/MVMCore/OtherHandlers/MVMCoreCache.m @@ -383,7 +383,7 @@ static NSString * const STATIC_CACHE_COMPONENT = @"StaticCache.txt"; - (nullable UIImage *)getImageFromRegisteredBundles:(nonnull NSString *)imageName { UIImage *image = nil; for (NSBundle *bundle in self.imageBundles) { - image = [UIImage imageNamed:imageName inBundle:bundle withConfiguration:nil]; + image = [UIImage imageNamed:imageName inBundle:bundle compatibleWithTraitCollection:nil]; if (image) { break; } From 72a82d4d3782115d60d89db25f67c2b1aa3fa4a0 Mon Sep 17 00:00:00 2001 From: "Suresh, Kamlesh" Date: Thu, 18 Jun 2020 00:05:43 -0400 Subject: [PATCH 8/8] oepn --- MVMCore/MVMCore/Models/ActionType/ActionOpenPageModel.swift | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MVMCore/MVMCore/Models/ActionType/ActionOpenPageModel.swift b/MVMCore/MVMCore/Models/ActionType/ActionOpenPageModel.swift index feb7b4c..7478e3a 100644 --- a/MVMCore/MVMCore/Models/ActionType/ActionOpenPageModel.swift +++ b/MVMCore/MVMCore/Models/ActionType/ActionOpenPageModel.swift @@ -8,7 +8,7 @@ import Foundation -@objcMembers public class ActionOpenPageModel: ActionModelProtocol { +@objcMembers open class ActionOpenPageModel: ActionModelProtocol { public static var identifier: String = "openPage" public var actionType: String = ActionOpenPageModel.identifier public var pageType: String