iOS应用中,空白界面,怎么管理?有数据一个界面,没请求到数据一个界面,没登录一个界面,没网一个界面?

iOS应用中,空白界面,怎么管理?
例如电商应用里面的购物车界面,订单界面,
有数据(商品/订单)一个界面,没请求到数据(没商品/订单)一个界面,没登录(有些应用的购物车界面,没登录,展示带登录按钮的界面)一个界面,没网(监听到没网)一个界面?
怎么处理?
例如:没网络,就展示没网络的界面,有网络,又要换到商品界面了。
我目前是码UIView,

//网络请求方法
- (void)loadOrderItemDetails: (NSString * )orderUrlStr withAnima: (NetworkAnimaLoadMoreBlock) animaBLock{
    __weak typeof(self) blockSelf = self;
    [GetNetWorkDataMethod networkRequest: nil requestType:ZheNetworkingRequestTypePost andWithURLStr:orderUrlStr success:^(NSURLSessionDataTask *task, NSDictionary *responseObject) {
        if(responseObject.count == 0){
            [blockSelf.view addSubview: self.notCorpFavorView ];
            [blockSelf.view bringSubviewToFront: self.notCorpFavorView ];
            return;
            // 没数据,就码上 空白订单界面,提示用户去下单
        }
        for (NSDictionary * tempDict in responseObject) {
            NSError * tempError;
            OrderListModel * orderListModel = [[OrderListModel alloc ] initWithDictionary: tempDict error: &tempError ];
            [blockSelf.orderListArray addObject: orderListModel ];
            [[NSOperationQueue mainQueue ] addOperationWithBlock:^{
                [blockSelf.orderItemDetailsTableView reloadData ];
                //  有数据,就码上订单界面,展示订单
            }];
        }
        
    } exception:^(NSDictionary *responseObject) {    } failure:^(NSError *error) {
    } ]; }

请教一下最佳实践,
感觉这样堆界面,挺Low 的。
有些时候,没网变有网,我还要判断一下,没网的界面是否添加上了。如果是,先移除没网的界面,再换成商品界面。
用嵌套ViewController 吗?

阅读 5.9k
5 个回答

我觉得有这么个办法,如果单纯的是你所说的三种情况对应不同的页面的话(假设不同情况页面是没有共用的情况)

第一种,我当年的做法:可以考虑当前控制器布局有商品的页面。
请求数据回来之后,如果有数据则赋值,没数据就在当前页面上覆盖空数据页面(注意,不要移除,直接遮盖住);
同样的方法,如果失败就在上面遮盖失败的页面;
如果没有登录的话,理论上是转场到一个新的控制器去做。
这个需要你把三种情况的页面封装好,这样逻辑才回清楚。

第二种,三种情况剥离成子控制器,父控制器请求数据和管理子控制器
根据不同情况加载不同的子控制器,这其实就是第一种方法的加强版,把三种情况的视图完全的封装起来。

iOS 项目中会出现空白页的地方大部分情况都是表视图没有数据展示,推荐使用 DZNEmptyDataSet 来管理空白页。
DZNEmptyDataSet 支持 UITableView、UICollectionView 和 UIScrollView 空数据展示页面。
多种展示方式:图片、标题、详细描述和按钮。使用 NSAttributedString 自定义字体颜色。
针对你的三种情况,可以根据三个 Bool 值来判断切换不同的值(如标题:空数据、未登录、网络未连接)展示空白页面。

DZNEmptyDataSet 这个框架是个挺不错的选择哦 - -

可以利用 Container View Controller 来实现。

先贴个官方文档
操作步骤大约是这样:

创建一个 Base View Controller(其实也就是你现在的 View Controller),用来处理网络请求等事务。

@implement BaseViewController
// ...... 省略 ......
    
// MARK: - Network Related Methods

- (void)loadOrderItemDetails: (NSString * )orderUrlStr withAnima: (NetworkAnimaLoadMoreBlock) animaBLock{
    // ...... 处理网络请求等等 ......
}

// ...... 省略 ......
@end

创建用于显示用户未登陆的 View Controller,例如名为

NotLoggedInViewController

在需要显示未登陆界面的时候,添加 NotLoggedInViewController 到 BaseViewController:


// ...... 省略 ......

- (void)loadOrderItemDetails: (NSString * )orderUrlStr withAnima: (NetworkAnimaLoadMoreBlock) animaBLock{
    // ...... 省略 ......
    
    NotLoggedInViewController *notLoggedInViewController = [NotLoggedInViewController new];
    [self addChildViewContrller:notLoggedInViewController];
    
    // 在此处设置 notLoggedInViewController 的 frame
    
    [self.view addSubview:notLoggedInViewController.view];
    
    // 可以在此处设置自动布局约束
    
    [notLoggedInViewController didMoveToParentViewController:self];
    
    // ...... 省略 ......
}

// ...... 省略 ......

如何移除 NotLoggedInViewController:

// ...... 省略 ......
    [notLoggedInViewController willMoveToParentViewController:nil];

    // 去除自动布局约束

    [notLoggedInViewController.view removeFromSuperview];
    [notLoggedInViewController removeFromParentViewController];
    
// ...... 省略 ......

去看 WWDC 2014的 232 advanced user interfaces with collection views

推荐问题