如何调用Swift Package中故事板的Storyboard Reference Segue
问题原因
你在Storyboard Reference中填写的字符串"Sample"无法匹配Swift Package自动生成的资源Bundle标识,系统查找失败后会默认回退到主Bundle搜索,因此触发找不到Login故事板的崩溃。

前置检查
首先确认你的Swift Package的Package.swift已经正确配置了故事板资源,确保Login.storyboard会被打包进SPM的资源Bundle中:
// Package.swift 对应target配置示例 .target( name: "Sample", resources: [ // 单个文件配置 .process("Login.storyboard"), // 如果所有资源都放在Resources目录下,也可以直接配置目录 // .process("Resources") ] )
编译后可以右键点击Products目录下的Sample.framework,选择「显示包内容」,确认内部存在Login.storyboardc文件,说明资源打包正常。
解决方案
方案1:手动加载故事板跳转(最稳定)
放弃可视化segue的跳转方式,通过代码手动指定Bundle加载SPM内的故事板,灵活性最高,不会受Bundle ID变更影响:
- 先在SPM的公共代码中暴露本模块的Bundle:
// SPM内部的公共Swift文件中添加 import Foundation public extension Bundle { static let sampleBundle = Bundle.module }
- 在主工程需要跳转的地方调用加载:
// 加载SPM内的Login故事板 let loginSB = UIStoryboard(name: "Login", bundle: .sampleBundle) // 实例化目标控制器,若有指定ID就用instantiateViewController(withIdentifier:) guard let loginVC = loginSB.instantiateInitialViewController() else { return } // 跳转(二选一) navigationController?.pushViewController(loginVC, animated: true) // present(loginVC, animated: true)
方案2:继续使用Storyboard Reference + Segue
如果一定要保留可视化segue的写法,可以通过填写完整的SPM资源Bundle ID解决:
- 先运行代码打印SPM的Bundle ID:
print(Bundle.sampleBundle.bundleIdentifier ?? ""),一般格式为你的组织前缀.Sample.Sample - 将打印得到的完整Bundle ID填写到Storyboard Reference的Bundle输入框中,替换原来的"Sample"即可。
注意:该方案的缺陷是如果后续SPM的Bundle ID发生变更,需要手动同步修改Storyboard中的配置。
内容的提问来源于stack exchange,提问作者Sarath
相关产品推荐
相关产品推荐

