iOS 应用进入黑屏
iOS App Goes to Black Screen
我在我的 Swift 应用程序中使用启动屏幕故事板和主故事板。有时应用程序会显示启动故事板,然后进入黑屏。其他时候它会正确地转到主故事板入口点。它几乎看起来像是依赖于构建的,因为如果我清理并重建几次,就会弹出一个行为正常的构建。知道是什么原因造成的吗?
添加一些说明:
- SplashScreen.storyboard是在target settings中设置的(好问题)。
- 这在真实设备和模拟器中都会发生,但并非总是如此。
- 我在这个阶段没有做任何网络(同步或其他)
- 停电似乎只在转换到一个特定视图时发生
- 视图的 viewWillDisplay 等代码即使在停电时也会执行,只是没有显示任何 VISIBLE
这可能会有所帮助:我在有问题的视图中输入了以下代码:
override func viewDidAppear(animated: Bool) {
print(self.view.layer.bounds.width);
print(self.view.layer.bounds.height);
}
出现黑屏问题时,我得到 260 和 17。当视图正确显示时,我得到 5s(模拟器)尺寸为 320 和 568。这对任何人有帮助吗?
我会说问题出在这一行:
dispatch_async(dispatch_get_main_queue(), {
self.performSegueWithIdentifier("toWelcomeView", sender: self);
});
您正在尝试转至另一个视图,而此视图尚未出现(视图 将 出现)。这非常不确定,这就是为什么有时它实际上会失败的原因。我有点惊讶您没有报告在控制台中看到一条错误消息,警告您正在尝试从视图尚未在界面中的视图控制器继续。
作为一项临时措施,您可以将对 self.RetrieveRegistration()
的呼叫移至 viewDidAppear:
,看看是否有帮助。
但从长远来看,您只是在以错误的方式解决问题。您的目标似乎是在某些情况下启动一个视图控制器,在其他情况下启动另一个视图控制器。将所有这些逻辑放在前面的地方 applicationDidFinishLaunching
,因此您的 rootViewController
本身会根据情况而有所不同。
例如,想象一下以下非常简单的情况:我们的故事板仅包含两个视图控制器,RegistrationViewController 和 RootViewController(具有故事板标识符 "root"
),从第一个到第二个呈现顺序。在 RegistrationViewController 中,我们请求注册信息,例如 "username"
,我们将其放置在 NSUserDefaults 中。然后我们转到 RootViewController。一切都很好,但我们此后的目标是用户应该再也不会看到 RegistrationViewController。这在应用程序委托中很容易处理:
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
if let rvc = self.window?.rootViewController {
if NSUserDefaults.standardUserDefaults().objectForKey("username") as? String != nil {
self.window!.rootViewController = rvc.storyboard!.instantiateViewControllerWithIdentifier("root")
}
}
return true
}
我终于解决了这个问题。经过数周的斗争并尝试了一切,从撕掉我的所有代码,事实证明我在情节提要中的视图的视图出口已经双重链接到 "View" 和我在该视图中的一个文本字段.像这样:
我已经删除了文本字段的链接,但在此处显示正确的链接:
有趣的是,我无法在 UI 中重现这个意外连接,所以我不确定这是怎么发生的。无论如何,我希望这对可能遇到此问题的其他人有所帮助。
我的设备遇到了同样的问题。我设法通过 xcode 设置应用程序的主界面来修复它: MyApplication → Main Interface → LaunchScreen.storyboard
(或Main.storyboard
).
干杯! :)
确保您的第一个视图控制器(在我的例子中是导航控制器)是初始控制器。 Find more details here.
此外,确保在使用 Segue 连接 Initial 和 Second Controller 时按 "Root View Controller" Relationship as you can see on picture here。
希望对您有所帮助!
我通过将此 属性 值对添加到 Info.plist
文件中的值数组 Application Scene Manifest
→ Scene Configuration
→ [=14= 中解决了这个问题] → Item 0 (Default Configuration)
.
<key>UISceneStoryboardFile</key>
<string>Main</string>
默认情况下,上述值实际上存在于 Info.plist
中,前一段时间我不小心删除了它。
我今天遇到了同样的问题,调试了 2 小时后我得到了修复
有几件事要记住。
- 故事板名称在以下方面应相同:
- 目标 > 'Main target' > 常规 > 部署信息 > 主界面
- 目标 > 'Main target' > 构建设置 > UIKit 主故事板文件基名
- Info.plist > 应用程序场景清单 > 场景配置 > 应用程序会话角色 > 项目 0 > 故事板名称
- 确保在您的情节提要标识符下方,在您上面设置的情节提要中的 main/default ViewController 上选中“是初始视图控制器”。
- 如果您已删除
main.storyboard
并使用另一个故事板作为主界面或视图层次调试器未显示任何内容,则意味着您必须在 SceneDelegate[ 中手动将其设置为根目录.
To do that refer following code of SceneDelegate.swift
func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
guard let windowScene = (scene as? UIWindowScene) else { return }
window = UIWindow(windowScene: windowScene)
let sb = UIStoryboard(name: "HomeLanding", bundle: nil)
let vc = sb.instantiateViewController(withIdentifier: "HomeLandingVC")
window?.rootViewController = vc
window?.makeKeyAndVisible()
}
注意:设置window = UIWindow(frame: UIScreen.main.bounds)
会破坏UISceneSession系统,这就是我们从当前场景设置它的原因
- 现在您必须在 AppDelegate
中设置 sceneConfig 委托 class
To do that refer to the following code of AppDelegate.swift
func application(_ application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration {
let config = UISceneConfiguration(name: nil, sessionRole: connectingSceneSession.role)
config.delegateClass = SceneDelegate.self
return config
}
对我来说,我的问题是我不小心删除了 Info.plist 中的“Application Scene Manifest”,确保它在里面!
我在我的 Swift 应用程序中使用启动屏幕故事板和主故事板。有时应用程序会显示启动故事板,然后进入黑屏。其他时候它会正确地转到主故事板入口点。它几乎看起来像是依赖于构建的,因为如果我清理并重建几次,就会弹出一个行为正常的构建。知道是什么原因造成的吗?
添加一些说明:
- SplashScreen.storyboard是在target settings中设置的(好问题)。
- 这在真实设备和模拟器中都会发生,但并非总是如此。
- 我在这个阶段没有做任何网络(同步或其他)
- 停电似乎只在转换到一个特定视图时发生
- 视图的 viewWillDisplay 等代码即使在停电时也会执行,只是没有显示任何 VISIBLE
这可能会有所帮助:我在有问题的视图中输入了以下代码:
override func viewDidAppear(animated: Bool) {
print(self.view.layer.bounds.width);
print(self.view.layer.bounds.height);
}
出现黑屏问题时,我得到 260 和 17。当视图正确显示时,我得到 5s(模拟器)尺寸为 320 和 568。这对任何人有帮助吗?
我会说问题出在这一行:
dispatch_async(dispatch_get_main_queue(), {
self.performSegueWithIdentifier("toWelcomeView", sender: self);
});
您正在尝试转至另一个视图,而此视图尚未出现(视图 将 出现)。这非常不确定,这就是为什么有时它实际上会失败的原因。我有点惊讶您没有报告在控制台中看到一条错误消息,警告您正在尝试从视图尚未在界面中的视图控制器继续。
作为一项临时措施,您可以将对 self.RetrieveRegistration()
的呼叫移至 viewDidAppear:
,看看是否有帮助。
但从长远来看,您只是在以错误的方式解决问题。您的目标似乎是在某些情况下启动一个视图控制器,在其他情况下启动另一个视图控制器。将所有这些逻辑放在前面的地方 applicationDidFinishLaunching
,因此您的 rootViewController
本身会根据情况而有所不同。
例如,想象一下以下非常简单的情况:我们的故事板仅包含两个视图控制器,RegistrationViewController 和 RootViewController(具有故事板标识符 "root"
),从第一个到第二个呈现顺序。在 RegistrationViewController 中,我们请求注册信息,例如 "username"
,我们将其放置在 NSUserDefaults 中。然后我们转到 RootViewController。一切都很好,但我们此后的目标是用户应该再也不会看到 RegistrationViewController。这在应用程序委托中很容易处理:
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
if let rvc = self.window?.rootViewController {
if NSUserDefaults.standardUserDefaults().objectForKey("username") as? String != nil {
self.window!.rootViewController = rvc.storyboard!.instantiateViewControllerWithIdentifier("root")
}
}
return true
}
我终于解决了这个问题。经过数周的斗争并尝试了一切,从撕掉我的所有代码,事实证明我在情节提要中的视图的视图出口已经双重链接到 "View" 和我在该视图中的一个文本字段.像这样:
我已经删除了文本字段的链接,但在此处显示正确的链接:
有趣的是,我无法在 UI 中重现这个意外连接,所以我不确定这是怎么发生的。无论如何,我希望这对可能遇到此问题的其他人有所帮助。
我的设备遇到了同样的问题。我设法通过 xcode 设置应用程序的主界面来修复它: MyApplication → Main Interface → LaunchScreen.storyboard
(或Main.storyboard
).
干杯! :)
确保您的第一个视图控制器(在我的例子中是导航控制器)是初始控制器。 Find more details here.
此外,确保在使用 Segue 连接 Initial 和 Second Controller 时按 "Root View Controller" Relationship as you can see on picture here。
希望对您有所帮助!
我通过将此 属性 值对添加到 Info.plist
文件中的值数组 Application Scene Manifest
→ Scene Configuration
→ [=14= 中解决了这个问题] → Item 0 (Default Configuration)
.
<key>UISceneStoryboardFile</key>
<string>Main</string>
默认情况下,上述值实际上存在于 Info.plist
中,前一段时间我不小心删除了它。
我今天遇到了同样的问题,调试了 2 小时后我得到了修复
有几件事要记住。
- 故事板名称在以下方面应相同:
- 目标 > 'Main target' > 常规 > 部署信息 > 主界面
- 目标 > 'Main target' > 构建设置 > UIKit 主故事板文件基名
- Info.plist > 应用程序场景清单 > 场景配置 > 应用程序会话角色 > 项目 0 > 故事板名称
- 确保在您的情节提要标识符下方,在您上面设置的情节提要中的 main/default ViewController 上选中“是初始视图控制器”。
- 如果您已删除
main.storyboard
并使用另一个故事板作为主界面或视图层次调试器未显示任何内容,则意味着您必须在 SceneDelegate[ 中手动将其设置为根目录.
To do that refer following code of
SceneDelegate.swift
func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
guard let windowScene = (scene as? UIWindowScene) else { return }
window = UIWindow(windowScene: windowScene)
let sb = UIStoryboard(name: "HomeLanding", bundle: nil)
let vc = sb.instantiateViewController(withIdentifier: "HomeLandingVC")
window?.rootViewController = vc
window?.makeKeyAndVisible()
}
注意:设置window = UIWindow(frame: UIScreen.main.bounds)
会破坏UISceneSession系统,这就是我们从当前场景设置它的原因
- 现在您必须在 AppDelegate
To do that refer to the following code of
AppDelegate.swift
func application(_ application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration {
let config = UISceneConfiguration(name: nil, sessionRole: connectingSceneSession.role)
config.delegateClass = SceneDelegate.self
return config
}
对我来说,我的问题是我不小心删除了 Info.plist 中的“Application Scene Manifest”,确保它在里面!