From 883b22225487a5d62f292a9a12e57ca52d61f896 Mon Sep 17 00:00:00 2001 From: CodeST <694468528@qq.com> Date: Sun, 9 Nov 2025 18:07:47 +0800 Subject: [PATCH] fix --- keyBoard/Class/Shop/VC/KBShopItemVC.h | 11 +- keyBoard/Class/Shop/VC/KBShopItemVC.m | 149 +++++++++++++------------- 2 files changed, 85 insertions(+), 75 deletions(-) diff --git a/keyBoard/Class/Shop/VC/KBShopItemVC.h b/keyBoard/Class/Shop/VC/KBShopItemVC.h index a32b6b2..cf5e84c 100644 --- a/keyBoard/Class/Shop/VC/KBShopItemVC.h +++ b/keyBoard/Class/Shop/VC/KBShopItemVC.h @@ -11,11 +11,16 @@ NS_ASSUME_NONNULL_BEGIN @interface KBShopItemVC : UIViewController -@property (nonatomic, strong) UITableView *tableView; -@property (nonatomic, strong) NSMutableArray *dataSource; +/// 列表:使用 UICollectionView 展示两列皮肤卡片 +@property (nonatomic, strong) UICollectionView *collectionView; +/// 数据源:简单字符串作为标题(演示用) +@property (nonatomic, strong) NSMutableArray *dataSource; +/// 是否需要上拉加载更多 @property (nonatomic, assign) BOOL isNeedFooter; +/// 是否需要下拉刷新 @property (nonatomic, assign) BOOL isNeedHeader; -@property (nonatomic, assign) BOOL isHeaderRefreshed; //默认为YES +/// 首次是否已刷新过(避免重复触发) +@property (nonatomic, assign) BOOL isHeaderRefreshed; // 默认为 YES @end NS_ASSUME_NONNULL_END diff --git a/keyBoard/Class/Shop/VC/KBShopItemVC.m b/keyBoard/Class/Shop/VC/KBShopItemVC.m index 2cd9d90..89da023 100644 --- a/keyBoard/Class/Shop/VC/KBShopItemVC.m +++ b/keyBoard/Class/Shop/VC/KBShopItemVC.m @@ -7,59 +7,55 @@ #import "KBShopItemVC.h" #import -@interface KBShopItemVC () +#import +#import "KBSkinCardCell.h" +/// 商城列表:使用 UICollectionView,两列网格,复用 KBSkinCardCell +@interface KBShopItemVC () @property (nonatomic, copy) void(^scrollCallback)(UIScrollView *scrollView); - @end @implementation KBShopItemVC - (void)viewDidLoad { [super viewDidLoad]; + self.view.backgroundColor = [UIColor whiteColor]; - _tableView = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStylePlain]; - self.tableView.backgroundColor = [UIColor whiteColor]; - self.tableView.tableFooterView = [UIView new]; - self.tableView.dataSource = self; - self.tableView.delegate = self; - [self.tableView registerClass:[UITableViewCell class] forCellReuseIdentifier:@"cell"]; - - [self.view addSubview:self.tableView]; + // 懒加载 collectionView,并添加到视图 + [self.view addSubview:self.collectionView]; + [self.collectionView mas_makeConstraints:^(MASConstraintMaker *make) { + make.edges.equalTo(self.view); // mas 布局:铺满 + }]; - __weak typeof(self)weakSelf = self; + // 刷新组件(演示:2 秒后结束) + __weak typeof(self) weakSelf = self; if (self.isNeedHeader) { - self.tableView.mj_header = [MJRefreshNormalHeader headerWithRefreshingBlock:^{ + self.collectionView.mj_header = [MJRefreshNormalHeader headerWithRefreshingBlock:^{ dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ - [weakSelf.tableView.mj_header endRefreshing]; + [weakSelf.collectionView.mj_header endRefreshing]; }); }]; } if (self.isNeedFooter) { - self.tableView.mj_footer = [MJRefreshAutoNormalFooter footerWithRefreshingBlock:^{ + self.collectionView.mj_footer = [MJRefreshAutoNormalFooter footerWithRefreshingBlock:^{ dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ - [weakSelf.dataSource addObject:@"加载更多成功"]; - [weakSelf.tableView reloadData]; - [weakSelf.tableView.mj_footer endRefreshing]; + [weakSelf.dataSource addObject:@"加载更多成功"]; // 模拟新增一条 + [weakSelf.collectionView reloadData]; + [weakSelf.collectionView.mj_footer endRefreshing]; }); }]; - if (@available(iOS 11.0, *)) { - self.tableView.contentInsetAdjustmentBehavior = UIScrollViewContentInsetAdjustmentNever; - } - } else { - //列表的contentInsetAdjustmentBehavior失效,需要自己设置底部inset -// self.tableView.contentInset = UIEdgeInsetsMake(0, 0, UIApplication.sharedApplication.keyWindow.jx_layoutInsets.bottom, 0); + } + + if (@available(iOS 11.0, *)) { + self.collectionView.contentInsetAdjustmentBehavior = UIScrollViewContentInsetAdjustmentNever; } [self beginFirstRefresh]; } -- (void)viewDidLayoutSubviews { - [super viewDidLayoutSubviews]; - - self.tableView.frame = self.view.bounds; -} +#pragma mark - 刷新控制 +// 首次进入自动触发一次刷新(如果需要) - (void)beginFirstRefresh { if (!self.isHeaderRefreshed) { [self beginRefreshImmediately]; @@ -68,74 +64,83 @@ - (void)beginRefreshImmediately { if (self.isNeedHeader) { - [self.tableView.mj_header beginRefreshing]; + [self.collectionView.mj_header beginRefreshing]; dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ self.isHeaderRefreshed = YES; - [self.tableView reloadData]; - [self.tableView.mj_header endRefreshing]; + [self.collectionView reloadData]; + [self.collectionView.mj_header endRefreshing]; }); - }else { + } else { self.isHeaderRefreshed = YES; - [self.tableView reloadData]; + [self.collectionView reloadData]; } } -#pragma mark - UITableViewDataSource, UITableViewDelegate +#pragma mark - UICollectionView DataSource -- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section { - if (!self.isHeaderRefreshed) { - return 0; - } +- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section { + if (!self.isHeaderRefreshed) return 0; return self.dataSource.count; } -- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { - UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"cell" forIndexPath:indexPath]; - cell.textLabel.text = self.dataSource[indexPath.row]; +- (__kindof UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath { + KBSkinCardCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"KBSkinCardCell" forIndexPath:indexPath]; + NSString *title = (indexPath.item < self.dataSource.count) ? self.dataSource[indexPath.item] : @"Dopamine"; + [cell configWithTitle:title imageURL:nil price:@"20"]; // 价格写死 20(演示) return cell; } -- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath { - return 50; +#pragma mark - UICollectionView DelegateFlowLayout + +- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath { + // 两列布局:左右 16 间距,中间列间距 12 + CGFloat insetLR = 16.0; + CGFloat spacing = 12.0; + CGFloat contentW = collectionView.bounds.size.width - insetLR * 2; + CGFloat itemW = floor((contentW - spacing) / 2.0); + CGFloat itemH = itemW * 0.75 + 56; // KBSkinCardCell 内部高度估算 + return CGSizeMake(itemW, itemH); } -- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath { -// DetailViewController *detailVC = [[DetailViewController alloc] init]; -// detailVC.infoString = self.dataSource[indexPath.row]; -// [self.navigationController pushViewController:detailVC animated:YES]; +- (UIEdgeInsets)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout insetForSectionAtIndex:(NSInteger)section { + return UIEdgeInsetsMake(12, 16, 12, 16); } +- (CGFloat)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout minimumLineSpacingForSectionAtIndex:(NSInteger)section { + return 12.0; +} + +- (CGFloat)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout minimumInteritemSpacingForSectionAtIndex:(NSInteger)section { + return 12.0; +} + +#pragma mark - UIScrollView Delegate(转发给分页容器) - (void)scrollViewDidScroll:(UIScrollView *)scrollView { !self.scrollCallback ?: self.scrollCallback(scrollView); } #pragma mark - JXPagingViewListViewDelegate +- (UIView *)listView { return self.view; } +- (UIScrollView *)listScrollView { return self.collectionView; } +- (void)listViewDidScrollCallback:(void (^)(UIScrollView *))callback { self.scrollCallback = callback; } +- (void)listWillAppear { NSLog(@"%@:%@", self.title, NSStringFromSelector(_cmd)); } +- (void)listDidAppear { NSLog(@"%@:%@", self.title, NSStringFromSelector(_cmd)); } +- (void)listWillDisappear { NSLog(@"%@:%@", self.title, NSStringFromSelector(_cmd)); } +- (void)listDidDisappear { NSLog(@"%@:%@", self.title, NSStringFromSelector(_cmd)); } -- (UIView *)listView { - return self.view; +#pragma mark - Lazy +- (UICollectionView *)collectionView { + if (!_collectionView) { + UICollectionViewFlowLayout *layout = [UICollectionViewFlowLayout new]; + layout.scrollDirection = UICollectionViewScrollDirectionVertical; + _collectionView = [[UICollectionView alloc] initWithFrame:CGRectZero collectionViewLayout:layout]; + _collectionView.backgroundColor = [UIColor whiteColor]; + _collectionView.dataSource = self; + _collectionView.delegate = self; + // 注册皮肤卡片 cell + [_collectionView registerClass:KBSkinCardCell.class forCellWithReuseIdentifier:@"KBSkinCardCell"]; // 复用标识 + } + return _collectionView; } -- (UIScrollView *)listScrollView { - return self.tableView; -} - -- (void)listViewDidScrollCallback:(void (^)(UIScrollView *))callback { - self.scrollCallback = callback; -} - -- (void)listWillAppear { - NSLog(@"%@:%@", self.title, NSStringFromSelector(_cmd)); -} - -- (void)listDidAppear { - NSLog(@"%@:%@", self.title, NSStringFromSelector(_cmd)); -} - -- (void)listWillDisappear { - NSLog(@"%@:%@", self.title, NSStringFromSelector(_cmd)); -} - -- (void)listDidDisappear { - NSLog(@"%@:%@", self.title, NSStringFromSelector(_cmd)); -} @end