cdts/xdts-ios 3/TreeHole/CYHResetCode/CYH/QMUIKit/QMUIMainFrame/QMUICommonTableViewController.m

324 lines
14 KiB
Mathematica
Raw Permalink Normal View History

2023-07-27 09:20:00 +08:00
/**
* Tencent is pleased to support the open source community by making QMUI_iOS available.
* Copyright (C) 2016-2021 THL A29 Limited, a Tencent company. All rights reserved.
* Licensed under the MIT License (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at
* http://opensource.org/licenses/MIT
* Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License.
*/
//
// QMUICommonTableViewController.m
// qmui
//
// Created by QMUI Team on 14-6-24.
//
#import "QMUICommonTableViewController.h"
#import "QMUICore.h"
#import "QMUITableView.h"
#import "QMUIEmptyView.h"
#import "QMUITableViewHeaderFooterView.h"
#import "UIScrollView+QMUI.h"
#import "UITableView+QMUI.h"
#import "UICollectionView+QMUI.h"
#import "UIView+QMUI.h"
#import "UIViewController+QMUI.h"
NSString *const QMUICommonTableViewControllerSectionHeaderIdentifier = @"QMUISectionHeaderView";
NSString *const QMUICommonTableViewControllerSectionFooterIdentifier = @"QMUISectionFooterView";
@interface QMUICommonTableViewController ()
@property(nonatomic, assign) BOOL hasHideTableHeaderViewInitial;
@end
@implementation QMUICommonTableViewController
- (instancetype)initWithStyle:(UITableViewStyle)style {
if (self = [super initWithNibName:nil bundle:nil]) {
[self didInitializeWithStyle:style];
}
return self;
}
- (instancetype)init {
return [self initWithStyle:UITableViewStylePlain];
}
- (instancetype)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil {
return [self init];
}
- (nullable instancetype)initWithCoder:(NSCoder *)aDecoder {
if (self = [super initWithCoder:aDecoder]) {
[self didInitializeWithStyle:UITableViewStylePlain];
}
return self;
}
- (void)didInitializeWithStyle:(UITableViewStyle)style {
_style = style;
self.hasHideTableHeaderViewInitial = NO;
}
- (void)dealloc {
// 线self.xxx访tableViewdeallocself.viewself.tableViewloadView
_tableView.dataSource = nil;
_tableView.delegate = nil;
}
- (NSString *)description {
#ifdef DEBUG
if (![self isViewLoaded]) {
return [super description];
}
NSString *tableView = [NSString stringWithFormat:@"<%@: %p>", NSStringFromClass(self.tableView.class), self.tableView];
NSString *result = [NSString stringWithFormat:@"%@\ntableView:\t\t\t\t%@", [super description], tableView];
NSInteger sections = [self.tableView.dataSource respondsToSelector:@selector(numberOfSectionsInTableView:)] ? [self.tableView.dataSource numberOfSectionsInTableView:self.tableView] : 1;
if (sections > 0) {
NSMutableString *sectionCountString = [[NSMutableString alloc] init];
[sectionCountString appendFormat:@"\ndataCount(%@):\t\t\t(\n", @(sections)];
for (NSInteger i = 0; i < sections; i++) {
NSInteger rows = [self.tableView.dataSource tableView:self.tableView numberOfRowsInSection:i];
[sectionCountString appendFormat:@"\t\t\t\t\t\t\tsection%@ - rows%@%@\n", @(i), @(rows), i < sections - 1 ? @"," : @""];
}
[sectionCountString appendString:@"\t\t\t\t\t\t)"];
result = [result stringByAppendingString:sectionCountString];
}
return result;
#else
return [super description];
#endif
}
- (void)viewDidLoad {
[super viewDidLoad];
if (self.tableView.backgroundColor) {
self.view.backgroundColor = self.tableView.backgroundColor;// self.view UITableViewStyle
}
}
- (void)initSubviews {
[super initSubviews];
[self initTableView];
}
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
if (!self.tableView.allowsMultipleSelection) {
[self qmui_animateAlongsideTransition:^(id<UIViewControllerTransitionCoordinatorContext> _Nonnull context) {
[self.tableView qmui_clearsSelection];
} completion:nil];
}
}
- (void)viewDidLayoutSubviews {
[super viewDidLayoutSubviews];
[self layoutTableView];
[self hideTableHeaderViewInitialIfCanWithAnimated:NO force:NO];
[self layoutEmptyView];
}
#pragma mark -
@synthesize tableView = _tableView;
- (__kindof QMUITableView *)tableView {
if (!_tableView) {
[self loadViewIfNeeded];
}
return _tableView;
}
- (void)setTableView:(__kindof QMUITableView *)tableView {
if (_tableView != tableView) {
if (_tableView) {
// delegatedataSource self QMUIMultipleDelegate weak
if (self.isViewLoaded && _tableView.superview == self.view) {
[_tableView removeFromSuperview];
}
}
_tableView = tableView;
[_tableView registerClass:[QMUITableViewHeaderFooterView class] forHeaderFooterViewReuseIdentifier:QMUICommonTableViewControllerSectionHeaderIdentifier];
[_tableView registerClass:[QMUITableViewHeaderFooterView class] forHeaderFooterViewReuseIdentifier:QMUICommonTableViewControllerSectionFooterIdentifier];
// nib loadView tableView self.view loadView isViewLoaded NO addSubview self.view loadView
// https://github.com/Tencent/QMUI_iOS/issues/1156
if (tableView.superview && self.nibName && !self.isViewLoaded) {
} else {
// loadView
[self.view addSubview:_tableView];
}
}
}
- (void)hideTableHeaderViewInitialIfCanWithAnimated:(BOOL)animated force:(BOOL)force {
if (self.tableView.tableHeaderView && [self shouldHideTableHeaderViewInitial] && (force || !self.hasHideTableHeaderViewInitial)) {
CGPoint contentOffset = CGPointMake(self.tableView.contentOffset.x, -self.tableView.adjustedContentInset.top + CGRectGetHeight(self.tableView.tableHeaderView.frame));
[self.tableView setContentOffset:contentOffset animated:animated];
self.hasHideTableHeaderViewInitial = YES;
}
}
- (void)contentSizeCategoryDidChanged:(NSNotification *)notification {
[super contentSizeCategoryDidChanged:notification];
if (self.viewLoaded) {
[self.tableView reloadData];
}
}
#pragma mark - QMUIEmptyView
- (void)handleTableViewContentInsetChangeEvent {
if (self.isEmptyViewShowing) {
[self layoutEmptyView];
}
}
- (void)showEmptyView {
[self.tableView addSubview:self.emptyView];
[self layoutEmptyView];
}
// emptyView tableView.contentInset tableView.contentInset emptyView
- (BOOL)layoutEmptyView {
if (!_emptyView || !_emptyView.superview) {
return NO;
}
UIEdgeInsets insets = self.tableView.adjustedContentInset;
// tableHeaderView emptyView tableView headerView
if (self.tableView.tableHeaderView) {
self.emptyView.frame = CGRectMake(0, CGRectGetMaxY(self.tableView.tableHeaderView.frame), CGRectGetWidth(self.tableView.bounds) - UIEdgeInsetsGetHorizontalValue(insets), CGRectGetHeight(self.tableView.bounds) - UIEdgeInsetsGetVerticalValue(insets) - CGRectGetMaxY(self.tableView.tableHeaderView.frame));
} else {
self.emptyView.frame = CGRectMake(0, 0, CGRectGetWidth(self.tableView.bounds) - UIEdgeInsetsGetHorizontalValue(insets), CGRectGetHeight(self.tableView.bounds) - UIEdgeInsetsGetVerticalValue(insets));
}
return YES;
}
#pragma mark - <QMUITableViewDelegate, QMUITableViewDataSource>
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return 0;
}
- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section {
NSString *title = [self tableView:tableView realTitleForHeaderInSection:section];
if (title) {
QMUITableViewHeaderFooterView *headerView = [tableView dequeueReusableHeaderFooterViewWithIdentifier:QMUICommonTableViewControllerSectionHeaderIdentifier];
headerView.parentTableView = tableView;
headerView.type = QMUITableViewHeaderFooterViewTypeHeader;
headerView.titleLabel.text = title;
return headerView;
}
return nil;
}
- (UIView *)tableView:(UITableView *)tableView viewForFooterInSection:(NSInteger)section {
NSString *title = [self tableView:tableView realTitleForFooterInSection:section];
if (title) {
QMUITableViewHeaderFooterView *footerView = [tableView dequeueReusableHeaderFooterViewWithIdentifier:QMUICommonTableViewControllerSectionFooterIdentifier];
footerView.parentTableView = tableView;
footerView.type = QMUITableViewHeaderFooterViewTypeFooter;
footerView.titleLabel.text = title;
return footerView;
}
return nil;
}
- (CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section {
if ([tableView.delegate respondsToSelector:@selector(tableView:viewForHeaderInSection:)]) {
// tableView:viewForHeaderInSection: return nil header tableView:heightForHeaderInSection: 0/CGFLOAT_MAX self-sizing header
UIView *view = [tableView.delegate tableView:tableView viewForHeaderInSection:section];
if (view) {
return UITableViewAutomaticDimension;
}
}
// iOS 13 Plain tableView header / footer 使 0 Grouped tableView header / footer 使 CGFLOAT_MIN
return PreferredValueForTableViewStyle(tableView.style, 0, TableViewGroupedSectionHeaderDefaultHeight, TableViewInsetGroupedSectionHeaderDefaultHeight);
}
- (CGFloat)tableView:(UITableView *)tableView heightForFooterInSection:(NSInteger)section {
if ([tableView.delegate respondsToSelector:@selector(tableView:viewForFooterInSection:)]) {
// tableView:viewForFooterInSection: return nil footer tableView:heightForFooterInSection: 0/CGFLOAT_MAX self-sizing footer
UIView *view = [tableView.delegate tableView:tableView viewForFooterInSection:section];
if (view) {
return UITableViewAutomaticDimension;
}
}
// iOS 13 Plain tableView header / footer 使 0 Grouped tableView header / footer 使 CGFLOAT_MIN
return PreferredValueForTableViewStyle(tableView.style, 0, TableViewGroupedSectionFooterDefaultHeight, TableViewInsetGroupedSectionFooterDefaultHeight);
}
// sectionheader title
- (NSString *)tableView:(UITableView *)tableView realTitleForHeaderInSection:(NSInteger)section {
if ([tableView.dataSource respondsToSelector:@selector(tableView:titleForHeaderInSection:)]) {
NSString *sectionTitle = [tableView.dataSource tableView:tableView titleForHeaderInSection:section];
if (sectionTitle && sectionTitle.length > 0) {
return sectionTitle;
}
}
return nil;
}
// sectionfooter title
- (NSString *)tableView:(UITableView *)tableView realTitleForFooterInSection:(NSInteger)section {
if ([tableView.dataSource respondsToSelector:@selector(tableView:titleForFooterInSection:)]) {
NSString *sectionFooter = [tableView.dataSource tableView:tableView titleForFooterInSection:section];
if (sectionFooter && sectionFooter.length > 0) {
return sectionFooter;
}
}
return nil;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
return [[UITableViewCell alloc] init];
}
/**
* contentInset emptyView layoutEmptyView
*/
- (void)scrollViewDidChangeAdjustedContentInset:(UIScrollView *)scrollView {
if (_tableView != scrollView) return;
[self handleTableViewContentInsetChangeEvent];
}
@end
@implementation QMUICommonTableViewController (QMUISubclassingHooks)
- (void)initTableView {
if (!_tableView) {
self.tableView = [[QMUITableView alloc] initWithFrame:self.isViewLoaded ? self.view.bounds : CGRectZero style:self.style];
// setDataSource: tableView reload setDelegate: setDelegate: reload 访 dataSource
// estimated viewDidLoad tableHeaderView setTableHeaderView: setDataSource: tableView numberOfSections 1 numberOfRows numberOfRows indexPath 访
_tableView.dataSource = self;
_tableView.delegate = self;
}
}
- (void)layoutTableView {
BOOL shouldChangeTableViewFrame = !CGRectEqualToRect(self.view.bounds, self.tableView.frame);
if (shouldChangeTableViewFrame) {
self.tableView.qmui_frameApplyTransform = self.view.bounds;
}
}
- (BOOL)shouldHideTableHeaderViewInitial {
return NO;
}
@end