cdts/xdts-ios 3/TreeHole/Code/Base/PYBaseViewController.m

510 lines
16 KiB
Mathematica
Raw Normal View History

2023-07-27 09:20:00 +08:00
//
// PYBaseViewController.m
// Food
//
// Created by ko1o on 2019/7/16.
// Copyright © 2019 ko1o. All rights reserved.
//
#import "PYBaseViewController.h"
#import "UIViewController+BXYStatefulViewController.h"
#import "UIImage+Extender.h"
#import <IQKeyboardManager.h>
#import "UINavigationController+FDFullscreenPopGesture.h"
@interface PYBaseViewController ()<MTStatefulBaseViewDelegate>
@property (nonatomic, strong) UIImage *backupNavgationBarShadowImage;
@property (nonatomic, assign) BOOL hasLoadedStateful;
@property (nonatomic, weak) UIViewController * mt_previousVC;
@property (nonatomic, assign) BOOL isViewAppear;
@property (nonatomic, assign) BOOL isTrackPageEnded;
@property (nonatomic, assign) BOOL stopLoading;
@property (nonatomic, strong) UIView *maskView;
@end
@implementation PYBaseViewController
//MARK: - QM
- (instancetype)init {
if (self = [super init]) {
if ([QMUIHelper.visibleViewController.navigationController isKindOfClass:NSClassFromString(@"THNavigationController")]) {
//QMUIKit
self.hidesBottomBarWhenPushed = YES;
}
}
return self;
}
//MARK: - Other
- (void)dealloc
{
[[NSNotificationCenter defaultCenter] removeObserver:self];
}
- (instancetype)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
if (self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil]) {
self.extendedLayoutIncludesOpaqueBars = YES;
if (![self isSupportFullScreenLayout]) {
self.edgesForExtendedLayout = UIRectEdgeNone;
// self.automaticallyAdjustsScrollViewInsets = NO;
}
self.mt_translucent = NO;
self.mt_nav_barTintColor = [UIColor whiteColor];
self.mt_nav_tintColor = [UIColor blackColor];
self.mt_barStyle = UIBarStyleDefault;
}
return self;
}
- (UIStatusBarStyle)preferredStatusBarStyle
{
if (self.mt_barStyle == UIBarStyleBlack) {
return UIStatusBarStyleLightContent;
}
return UIStatusBarStyleLightContent;
}
- (BOOL)isSupportContentScrollView
{
return NO;
}
- (BOOL)isSupportShare
{
return NO;
}
- (void)viewDidLayoutSubviews
{
[super viewDidLayoutSubviews];
self.bxy_loadingView.centerY = self.bxy_errorView.centerY = self.bxy_emptyView.centerY = self.view.height * 0.5;
self.bxy_emptyView.userInteractionEnabled = NO;
self.bxy_errorView.userInteractionEnabled = NO;
}
- (BOOL)canBack {
return YES;
}
- (BOOL)fd_interactivePopDisabled {
if (![self canBack]) {
return YES;
}
if ([MTAlertView hasAlertViewShowing]) { // AlertView
return YES;
}
return _fd_interactivePopDisabled;
}
- (void)viewDidLoad {
[super viewDidLoad];
//view
if ([self mt_shouldSetupStateful] && self.hasLoadedStateful) {
[self bxy_setupInitialViewState];
}
self.view.backgroundColor = BG_COLOR;
self.maskView = [[UIView alloc] initWithFrame:[UIScreen mainScreen].bounds];
self.maskView.backgroundColor = UIColor.blackColor;
WeakSelf(self);
[self.maskView addTapWithAction:^{
[weakself.view endEditing:YES];
}];
if ([self mt_shouldSetupStateful]) {
self.bxy_loadingView = [[MTStatefulBaseView alloc] initWithFrame:CGRectZero type:MTStatefulViewTypeLoading delegate:self];
self.bxy_emptyView = [[MTStatefulBaseView alloc] initWithFrame:CGRectZero type:MTStatefulViewTypeEmpty delegate:self];
self.bxy_errorView = [[MTStatefulBaseView alloc] initWithFrame:CGRectZero type:MTStatefulViewTypeError delegate:self];
}
if (self.preferredStatusBarStyle == UIStatusBarStyleLightContent) {
self.mt_barStyle = UIBarStyleBlack;
} else {
self.mt_barStyle = UIBarStyleDefault;
}
if ([self isSupportContentScrollView]) {
self.contentScrollView = [[UIScrollView alloc] initWithFrame:self.view.bounds];
self.contentScrollView.backgroundColor = [UIColor clearColor];
self.contentScrollView.showsVerticalScrollIndicator = YES;
self.contentScrollView.alwaysBounceVertical = YES;
[self.view addSubview:self.contentScrollView];
self.contentScrollView.contentInsetAdjustmentBehavior = UIScrollViewContentInsetAdjustmentNever;
// if ([[[UIDevice currentDevice] systemVersion] floatValue] <= 11.0) {
// self.contentScrollView.y = NAVIGATION_BAR_HEIGHT;
// self.contentScrollView.height = self.view.height - self.contentScrollView.y;
// }
}
if (self.navigationController.childViewControllers.count > 1) {
UIBarButtonItem *backItem = [[UIBarButtonItem alloc] initWithImage:ImageNamed(@"TH_back_black") style:UIBarButtonItemStyleDone target:self action:@selector(back)];
self.navigationItem.leftBarButtonItem = backItem;
}
if (![self canBack]) {
self.navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc] initWithCustomView:[UIView new]];
}
[self.navigationController setModalPresentationStyle:UIModalPresentationFullScreen];
self.mt_prefersNavigationBarShadowHidden = YES;
if ([self mt_nagationBarTransparent]) {
self.mt_translucent = YES;
self.extendedLayoutIncludesOpaqueBars = YES;
}
if ([self isSupportShare]) {
self.navigationItem.rightBarButtonItem = [[UIBarButtonItem alloc] initWithImage:ImageNamed(@"share") style:UIBarButtonItemStyleDone target:self action:@selector(shareDidClick)];
}
// if (self.mt_prefersNavigationBarShadowHidden) {
// self.navigationController.navigationBar.shadowImage = [UIImage new];
// }
}
#pragma mark - UITextFieldDelegate
- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField
{
if ([textField.inputView isKindOfClass:NSClassFromString(@"MTPickerView")]) {
textField.tintColor = UIColor.clearColor;
[self showMaskView];
} else {
[IQKeyboardManager sharedManager].enableAutoToolbar = NO;
}
return YES;
}
- (BOOL)textFieldShouldEndEditing:(UITextField *)textField
{
if ([textField.inputView isKindOfClass:NSClassFromString(@"MTPickerView")]) {
[self hideMaskView];
}
return YES;
}
- (void)showMaskView
{
[IQKeyboardManager sharedManager].enableAutoToolbar = NO;
[self.view.window addSubview:self.maskView];
self.maskView.alpha = 0.0;
[self.view.window bringSubviewToFront:self.maskView];
[UIView animateWithDuration:0.25 animations:^{
self.maskView.alpha = 0.3;
}];
}
- (void)hideMaskView
{
[UIView animateWithDuration:0.25 animations:^{
self.maskView.alpha = 0.0;
} completion:^(BOOL finished) {
[IQKeyboardManager sharedManager].enableAutoToolbar = NO;
}];
}
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
[self.view endEditing:animated];
self.isViewAppear = NO;
}
- (void)back {
[self.navigationController popViewControllerAnimated:YES];
}
- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event
{
[super touchesBegan:touches withEvent:event];
[self.view endEditing:YES];
}
- (BOOL)mt_nagationBarTransparent
{
if (self.title.length > 0) { //
return NO;
}
return _mt_nagationBarTransparent;
}
- (BOOL)isSupportFullScreenLayout
{
return YES;
}
- (UIModalPresentationStyle)modalPresentationStyle {
return UIModalPresentationFullScreen;
}
//loading empty error
- (BOOL)mt_shouldSetupStateful
{
return YES;
}
- (NSString *)emptyTips {
return @"空空无也~";
}
- (BOOL)mt_hasContentForStateful
{
return self.stopLoading;
}
- (void)mt_startStatefulLoading:(BOOL)animated
{
if ([self mt_shouldSetupStateful]) {
self.hasLoadedStateful = YES;
dispatch_async(dispatch_get_main_queue(), ^{
[self bxy_startLoading:animated completion:^{
;
}];
});
}
}
- (void)mt_endStatefulLoading:(BOOL)animated error:(NSError *)error
{
if ([self mt_shouldSetupStateful]) {
[self bxy_endLoading:animated error:error completion:^{
;
}];
}
}
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
if (![self isNavigationBarHidden]) {
[self.navigationController setNavigationBarHidden:NO animated:animated];
}
[self mt_applyAppearanceToNavigationBar:self.navigationController.navigationBar];
}
- (BOOL)enableAutoToolbar {
return YES;
}
- (BOOL)isNavigationBarHidden {
return NO;
}
- (void)viewDidAppear:(BOOL)animated
{
//VC
UIViewController *mt_previousViewController;
NSInteger index = [self.navigationController.viewControllers indexOfObject:self];
if (index != NSNotFound && index >= 1) {
mt_previousViewController = [self.navigationController.viewControllers objectAtIndex:index -1];
}
if (self.parentViewController && !mt_previousViewController) { //vc
UIViewController * parent = self.parentViewController;
index = [parent.navigationController.viewControllers indexOfObject:parent];
if (index != NSNotFound && index >= 1) {
mt_previousViewController = [parent.navigationController.viewControllers objectAtIndex:index -1];
}
}
if (!mt_previousViewController) {
mt_previousViewController = self.presentingViewController;
}
self.mt_previousVC = mt_previousViewController;
[super viewDidAppear:animated];
self.isViewAppear = YES;
[self.navigationController setNavigationBarHidden:[self isNavigationBarHidden] animated:NO];
[IQKeyboardManager sharedManager].enableAutoToolbar = [self enableAutoToolbar];
[self mt_applyAppearanceToNavigationBar:self.navigationController.navigationBar];
}
- (void)startLoading
{
self.stopLoading = NO;
[self mt_startStatefulLoading:NO];
}
- (void)endLoading:(NSError *)error
{
self.stopLoading = YES;
[self mt_endStatefulLoading:NO error:error];
}
#pragma mark - StatefulViewControllerProtocol
/**
* Return true if content is available in your controller.
*
* - returns: true if there is content available in your controller.
*/
- (BOOL)hasContent
{
return [self mt_hasContentForStateful];
}
/**
* This method is called if an error occurred, but `hasContent` returned true.
* You would typically display an unobstrusive error message that is easily dismissable
* for the user to continue browsing content.
*
* - parameter error: The error that occurred
*/
- (void)handleErrorWhenContentAvailable:(NSError *)error
{
}
#pragma mark - MTStatefulBaseViewDelegate
- (MTStatefulConfigItem *)statefulConfigItemForStatefulViewType:(MTStatefulViewType)statefulViewType
{
MTStatefulConfigItem *item = [MTStatefulConfigItem new];
WeakSelf(self);
if (statefulViewType == MTStatefulViewTypeEmpty) {
MTStatefulConfigItem *item = [[MTStatefulConfigItem alloc] init];
item.statefulTitle = [self emptyTips];
return item;
}
// else
// if (statefulViewType == MTStatefulViewTypeError) {
// StrongSelf(self);
// MTStatefulConfigItem *item = [[MTStatefulConfigItem alloc] init];
// item.statefulTitle = @"哎哟!网络异常,请稍后…";
// item.shouldShowErrorRefresh = YES;
// item.didClickedRefreshBlock = self.didClickedRefreshBlock;
// return item;
// }
item.shouldShowErrorRefresh = NO;
return item;
}
@end
@interface UIViewControllerMTAppearance : NSObject
@property (nonatomic, assign) BOOL mt_translucent;
@property (nonatomic, assign) BOOL mt_prefersNavigationBarShadowHidden;
@property (nonatomic, strong) UIColor * mt_nav_barTintColor;
@property (nonatomic, strong) UIColor * mt_navbarBackgroundImageColor;
@property (nonatomic, strong) UIColor * mt_nav_tintColor;
@property (nonatomic, strong) NSDictionary * mt_titleTextAttributes;
@property (nonatomic, assign) UIBarStyle mt_barStyle;
@property (nonatomic, strong) UIImage * mt_navbarBackgroundImage;
@end
@implementation UIViewControllerMTAppearance
@end
@interface UIViewController (MTAppearanceInner)
@property (nonatomic, strong) UIViewControllerMTAppearance *mtAppearance;
@end
@implementation UIViewController (MTAppearance)
@dynamic mt_translucent;
@dynamic mt_prefersNavigationBarShadowHidden;
@dynamic mt_nav_barTintColor;
@dynamic mt_navbarBackgroundImageColor;
@dynamic mt_nav_tintColor;
@dynamic mt_titleTextAttributes;
@dynamic mt_navbarBackgroundImage;
- (BOOL)mt_translucent
{
return self.mtAppearance.mt_translucent;
}
- (void)setMt_translucent:(BOOL)mt_translucent
{
self.mtAppearance.mt_translucent = mt_translucent;
}
- (UIViewControllerMTAppearance *)mtAppearance
{
UIViewControllerMTAppearance *mtAppearance = objc_getAssociatedObject(self, _cmd);
if (!mtAppearance) {
mtAppearance = [UIViewControllerMTAppearance new];
objc_setAssociatedObject(self, _cmd, mtAppearance, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
}
return mtAppearance;
}
- (id)forwardingTargetForSelector:(SEL)sel
{
if ([self.mtAppearance respondsToSelector:sel]) {
return self.mtAppearance;
}
return nil;
}
- (void)mt_applyAppearanceToNavigationBar:(UINavigationBar *) navigationBar
{
UIViewController * vc = self;
navigationBar.translucent = vc.mt_translucent;
UIImage *barBackgroundImage = [UIImage new];
if (vc.mt_navbarBackgroundImageColor) {
UIImage *barImage = vc.mt_navbarBackgroundImageColor == [UIColor clearColor] ? [UIImage new] : [UIImage imageWithColor:vc.mt_navbarBackgroundImageColor size:CGSizeMake(10, 10)] ;
barBackgroundImage = barImage;
}
[navigationBar setBackgroundImage:barBackgroundImage forBarMetrics:UIBarMetricsDefault];
if (vc.mt_navbarBackgroundImage) {
[navigationBar setBackgroundImage:vc.mt_navbarBackgroundImage forBarMetrics:UIBarMetricsDefault];
}
vc.mt_nav_barTintColor = [self preferredStatusBarStyle] == UIStatusBarStyleLightContent ? COLOR_WITH_RGB(0x15112D) : [UIColor whiteColor];
navigationBar.barStyle = vc.mt_barStyle;
navigationBar.barTintColor = vc.mt_nav_barTintColor;
UIColor *tintColor = [self preferredStatusBarStyle] == UIStatusBarStyleLightContent ? UIColor.whiteColor : TITLE_COLOR;
navigationBar.tintColor = tintColor;
navigationBar.titleTextAttributes = vc.mt_titleTextAttributes ?: @{NSFontAttributeName : MT_FONT_MEDIUM_SIZE(15), NSForegroundColorAttributeName : tintColor};
navigationBar.shadowImage = [vc mt_prefersNavigationBarShadowHidden] ? [UIImage new] : nil ;
// navigationBar.shadowImage = [UIImage imageWithColor:[UIColor colorWithWhite:1.0 alpha:0.1] size:CGSizeMake(SCREEN_WIDTH, 0.5)];
if (@available(iOS 15.0, *)) {
UINavigationBarAppearance *barApp = [UINavigationBarAppearance new];
barApp.backgroundColor = navigationBar.barTintColor;
barApp.titleTextAttributes = navigationBar.titleTextAttributes;
barApp.shadowImage = navigationBar.shadowImage;
barApp.shadowColor = [UIColor clearColor];
barApp.backgroundImage = barBackgroundImage;
self.navigationController.navigationBar.translucent = [self mt_translucent];
if ([self mt_translucent]) { //
[barApp configureWithTransparentBackground];
} else {
barApp.backgroundImage = [UIImage imageWithColor:navigationBar.barTintColor size:navigationBar.size];
}
self.navigationController.navigationBar.scrollEdgeAppearance = barApp;
self.navigationController.navigationBar.standardAppearance = barApp;
}
}
@end