基于Storyboard创建多分支NavigationController的方法

简介:

遇到的问题

我在写程序的时候碰到这样一个简单的需求,用户点击“我的XX”这样的功能时候,需要判断当前用户是否已经登录,如果已经登录了,则显示该用户的相关信息并且可以切换到更多界面:

VFZBvuf.png

如果没有登录,则显示登录界面并且可以选择登录还是注册:

yQn2YfV.png

后来继续了解到其实不止一个功能需要有这样的需求,任何需要登录后才能进行的功能,当用户点击时,都需要做这样的判断。

那我怎样才能把上述两种情况有机地结合在一起,并且能在多个地方复用呢?

当时的第一想法是在代码里根据当前用户登录还是不登录手动替换NavigationController的RootViewController,但是我目前的程序完全是基于Storyboard来写的,因此界面的流转关系是完全体现在Storyboard上的。我想这个功能也能继续维持这样的状态,能在Storyboard上清晰地体现出来(这里不讨论Storyboard的优劣,只是想说明工程代码的表现形式要一致)。

由于年少不懂事,当时以为只要做出下图的这种关系就可以了,当然很快就发现这是不可能的

vYRZJzQ.png

后来发现其实 NavigationController内部也是实现了类似于ContainerViewController的机制 (可能需FQ),所以只需要替换ContainerViewController的内容,自然也就替换了相应的界面。

多分支NavigationController的方法

根据上述的讨论,具体的方案已经呼之欲出了(关于具体的自定义ContainerViewController的技术细节就不再阐述了,上面的链接已经解释的很清楚了,这里主要是讨论如何使之应用到我们的场景中)。

我是先自己在Storyboard上建立一个RootViewController,名字暂且定为ConditionContainerViewController(具体代码后面会介绍到),如下图:

BZ7Jr2.png

然后再继承UIStoryboardSegue,新建一个Segue,名字暂且定为ConditionShowSegue

1
2
3
4
5
6
7
8
9
   - (void)perform {
   UIViewController *srcVC = self.sourceViewController;
   UIViewController *destVC = self.destinationViewController;
 
   [srcVC addChildViewController:destVC];
   [srcVC.view addSubview:destVC.view];
   destVC.view.frame = CGRectMake(0, 0, CGRectGetWidth(srcVC.view.frame), CGRectGetHeight(srcVC.view.frame));
   [destVC didMoveToParentViewController:srcVC];
   }

如果上面代码暂时不能理解,请回到之前发的链接再仔细理解里面的内容(我当时也是看了好几遍,呵呵)。

随后就可以在Storyboard中使用这个Segue了,可以看到菜单里多了一种“Condition Show”:

67RJzem.png

用新的Segue来连接之前在本文一开始就展示的两段分开的业务线,使之结合在一起

JbaaEb.png

然后分别定义这两个Segue的Identifier为“ShowNeedLogin”以及“ShowLoggedIn”。

接下来我们再回过头来看ConditionContainerViewController的代码,其实主要代码非常简单就是重载viewWillAppear:这个方法

1
2
3
4
5
6
7
8
9
10
   - (void)viewWillAppear:(BOOL)animated {
     [ super  viewWillAppear:animated];
 
     if  (isLogin) {
       [self performSegueWithIdentifier:@ "ShowHasLogined"  sender:self];
     }
     else  {
       [self performSegueWithIdentifier:@ "ShowLoggedIn"  sender:self];
     }
   }

isLogin这个你可以使用各种方法来实现,比如自定义一个变量或者全局有一个用户管理类来暴露一个isLogin属性等。

其实目前程序已经可以根据你当前登录的情况来自动切换展示的界面了,但是现在还有一个问题,登录成功之后又怎么跳回已经登录的界面的?只要在需要登录成功后调用如下代码:

1
2
3
4
5
6
7
8
   // 普通情况下直接调用popToRootViewControllerAnimated即可
   // 然后ConditionContainerViewController会通过viewWillAppear来判断
   NSArray *poppedViewcontrollers = [self popToRootViewControllerAnimated:animated];
   // 但是如果是从上面那个图的Need Login这个界面返回,这个时候已经在RootViewController了
   // 因此需要手动调用viewWillAppear
   if  (poppedViewcontrollers == nil) {
      [[self.viewControllers firstObject] viewWillAppear:YES];
   }

好了,接下来我们还需要一些清理代码,在ConditionContainerViewController写入以下函数:

1
2
3
4
5
6
7
8
9
10
11
   @property (nonatomic, strong) UIViewController *lastViewController;
   ...
   
   - (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
     if  (segue.destinationViewController != self.lastViewController) {
       [self.lastViewController willMoveToParentViewController:nil];
       [self.lastViewController.view removeFromSuperview];
       [self.lastViewController removeFromParentViewController];
     }
     self.lastViewController = segue.destinationViewController;
   }

这个清理代码应该有更好地方来写,目前我只能想到放在这里,希望大家可以给一些建议。

当然,一开始我也提到这种方法是要可以复用的,且在Storyboard上能清晰地表示出来,最后我就展示一张简单的Storyboard来说明:

zuMrem.png

























本文转自ljianbing51CTO博客,原文链接:http://blog.51cto.com/ljianbing/1949175 ,如需转载请自行联系原作者


相关文章
|
9天前
|
机器人 API 调度
基于 DMS Dify+Notebook+Airflow 实现 Agent 的一站式开发
本文提出“DMS Dify + Notebook + Airflow”三位一体架构,解决 Dify 在代码执行与定时调度上的局限。通过 Notebook 扩展 Python 环境,Airflow实现任务调度,构建可扩展、可运维的企业级智能 Agent 系统,提升大模型应用的工程化能力。
|
人工智能 前端开发 API
前端接入通义千问(Qwen)API:5 分钟实现你的 AI 问答助手
本文介绍如何在5分钟内通过前端接入通义千问(Qwen)API,快速打造一个AI问答助手。涵盖API配置、界面设计、流式响应、历史管理、错误重试等核心功能,并提供安全与性能优化建议,助你轻松集成智能对话能力到前端应用中。
689 154
|
15天前
|
人工智能 数据可视化 Java
Spring AI Alibaba、Dify、LangGraph 与 LangChain 综合对比分析报告
本报告对比Spring AI Alibaba、Dify、LangGraph与LangChain四大AI开发框架,涵盖架构、性能、生态及适用场景。数据截至2025年10月,基于公开资料分析,实际发展可能随技术演进调整。
960 152
|
负载均衡 Java 微服务
OpenFeign:让微服务调用像本地方法一样简单
OpenFeign是Spring Cloud中声明式微服务调用组件,通过接口注解简化远程调用,支持负载均衡、服务发现、熔断降级、自定义拦截器与编解码,提升微服务间通信开发效率与系统稳定性。
360 156
|
7天前
|
分布式计算 监控 API
DMS Airflow:企业级数据工作流编排平台的专业实践
DMS Airflow 是基于 Apache Airflow 构建的企业级数据工作流编排平台,通过深度集成阿里云 DMS(Data Management Service)系统的各项能力,为数据团队提供了强大的工作流调度、监控和管理能力。本文将从 Airflow 的高级编排能力、DMS 集成的特殊能力,以及 DMS Airflow 的使用示例三个方面,全面介绍 DMS Airflow 的技术架构与实践应用。
|
8天前
|
人工智能 自然语言处理 前端开发
Qoder全栈开发实战指南:开启AI驱动的下一代编程范式
Qoder是阿里巴巴于2025年发布的AI编程平台,首创“智能代理式编程”,支持自然语言驱动的全栈开发。通过仓库级理解、多智能体协同与云端沙箱执行,实现从需求到上线的端到端自动化,大幅提升研发效率,重塑程序员角色,引领AI原生开发新范式。
485 2