如何在没有Storyboard的情况下在Xcode中创建一个空应用程序


146

Xcode6Empty Application在创建新项目时已删除模板。Xcode6与早期版本一样,我们如何在上方和上方创建一个空的应用程序(没有Storyboard)?




最新的教程,iOS9和Xcode的7:medium.com/frozen-fire-studios/...
瑞安Poolos

Answers:


270

XCode6更高版本中,没有任何选项可以像在XCode5早期版本中那样直接创建空应用程序。但是我们仍然可以Storyboard通过以下步骤创建应用程序:

  1. 创建一个Single View Application
  2. 删除Main.storyboardLaunchScreen.xib(选择它们,单击鼠标右键,然后选择将其从项目中删除,或完全删除)。
  3. 删除“主要情节提要文件的基本名称”和“启动屏幕界面文件的基本名称”中的条目 Info.plist
  4. 打开AppDelegate.m,然后编辑applicationDidFinishLaunchingWithOptions,使其如下所示:

Swift 3及更高版本:

    func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool 
    {
        self.window = UIWindow(frame: UIScreen.main.bounds)
        self.window?.backgroundColor = UIColor.white
        self.window?.makeKeyAndVisible()
        return true
    }

Swift 2.x:

    func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool 
    {
        self.window = UIWindow(frame: UIScreen.mainScreen().bounds)
        self.window?.backgroundColor = UIColor.whiteColor()
        self.window?.makeKeyAndVisible()
        return true
    }

目标C:

    - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
    {
        self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
        // Override point for customization after application launch.
        self.window.rootViewController = [[ViewController alloc] init];
        self.window.backgroundColor = [UIColor whiteColor];
        [self.window makeKeyAndVisible];
        return YES;
    }

22
我喜欢保留LaunchScreen.xib相应的Info.plist条目。没有它,该应用程序将无法在较大的iPhone上占用整个屏幕尺寸,这很丑陋。
tboyce12

2
我喜欢自己保留分镜脚本。创建各种东西很方便,但是我需要不依赖情节提要而进行初始设置。
Mazyod 2015年

也许是Xcode 7中的一个错误,我根本无法从项目信息设置屏幕中删除Main.storyboard。我使用了@Silentwarrior提到的Xcode 5空应用程序模板。
2015年

3
除非您手动安装根ViewController,否则此答案会在XCode7中生成运行时错误:“ NSInternalInconsistencyException”,原因:“应用程序窗口应在应用程序启动结束时具有根视图控制器”

11
请同时添加以下代码:self.window.rootViewController = [[ViewController alloc] init]; 在您的AppDelegate.m中的didFinishLaunchingWithOptions方法下。否则,您将得到以下错误:“应用程序窗口应在应用程序启动结束时具有一个根视图控制器”
Rizwan Ahmed

32

一种简单的方法是将XCode 5Empty Application模板复制到XCode的模板目录。

您可以从此处下载XCode 5Empty Application模板,然后将其解压缩并复制到目录中。 /Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/Library/Xcode/Templates/Project Templates/iOS/Application

附言:这种方法也可以迅速使用!

编辑
正如@harrisg在下面的注释中建议的那样,您可以将上述模板放在~/Library/Developer/Xcode/Templates/Project Templates/iOS/Application/文件夹中,以便即使Xcode更新也可以使用。
如果没有这样的目录存在,那么你可能需要创建此目录结构:Templates/Project Templates/iOS/Application/~/Library/Developer/Xcode/

使用这种简单的方法,我可以创建一个Empty Applicationin XCode 6。(下面的截图)

Xcode空应用程序模板 希望这可以帮助!


谢谢。注意,您需要在Xcode更新后替换此模板。
elliotrock

1
如果将它放到〜/ Library / Developer / Xcode / Templates / Project Templates / iOS / Application /中,则不必在每次Xcode更新时都将其替换
危害

@harrisg在优胜美地找不到此目录。你能确认它的存在吗?谢谢
S1LENT WARRIOR

1
此方法适用于Xcode 7.1,但是创建了某些人可能不需要的LaunchScreen.storyboard。我最终使用了它,因为它不会干扰我手动创建的视图。
bitsand

1
切记将文件解压缩到目录中,复制是不够的。
Balaban Mario 2016年

17

您还需要执行几个步骤:

  1. 添加前缀文件。(如果需要)
  2. 要添加默认启动图像,否则在iPhone 5上应用程序大小为320x480。

所以这是一个完整的教程:

  1. 删除Main.storyboard文件
  2. 删除LaunchScreen.xib文件
  3. 删除Info.plist中的“主故事板文件库名称”属性
  4. 删除Info.plist中的“启动屏幕界面文件库名称”属性
  5. 将“ [应用名称] -Prefix.pch”文件添加到具有以下内容的支持文件中:

    #import <Availability.h>
    
    #ifndef __IPHONE_3_0
    #warning "This project uses features only available in iOS SDK 3.0 and later."
    #endif
    
    #ifdef __OBJC__
    #import <UIKit/UIKit.h>
    #import <Foundation/Foundation.h>
    #endif
  6. 将“ $ SRCROOT / $ PROJECT_NAME / [pch文件名]”添加到项目设置->构建设置-> Apple LLVM 6.0-语言->“前缀标题”

  7. 将“是”添加到项目设置->构建设置-> Apple LLVM 6.0-语言->“预编译前缀头”
  8. 打开“ Image.xcassets”并添加LaunchImage
  9. 生成项目,然后会出现关于缺少默认启动图像的警告,只需按一下警告并选择添加默认值,这将添加“ Default-568h @ 2x”或-如果您要使用“ Images”中的启动图像.xcassets”,转到项目设置->目标->常规->在“启动图像源”中选择使用资产目录,它将创建一个新的目录,您可以选择然后将其用作现有目录中的资产目录。
  10. 实现application:didFinishLaunchingWithOptions:方法:

    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    //Override point for customization after application launch.
    self.window.backgroundColor = [UIColor whiteColor];
    [self.window makeKeyAndVisible];
    
    return YES;

16

阿基尔斯的答案是完全正确的。对于使用Swift的我们来说,就像这样:

func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
    self.window = UIWindow(frame: UIScreen.mainScreen().bounds)
    self.window?.backgroundColor = UIColor.whiteColor()
    self.window?.makeKeyAndVisible()
    return true
}

12

Xcode 9.3.1Swift 4

  1. 首先,您需要在项目导航器菜单中删除Main.storyboard
  2. 然后在Info.plist中删除行Main Storyboard文件的基本名称
  3. 并且不要忘记在Project Target - General - Deployment Info中删除单元的Main Interface(只是删除Main) 。
  4. 之后,转到AppDelegate.swift并在didFinishLaunchingWithOptions函数中编写以下内容:

    func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
        // Override point for customization after application launch.
    
        window = UIWindow(frame: UIScreen.main.bounds)
        window?.makeKeyAndVisible()
        window?.rootViewController = UINavigationController(rootViewController: ViewController())
    
        return true
    }

Xcode 11.2.1Swift 5

  1. 首先,您需要在项目导航器菜单中删除Main.storyboard
  2. 然后在Info.plist中删除行Main Storyboard文件的基本名称
  3. 并且不要忘记在Project Target-General-Deployment Info中删除单元的Main Interface(只是删除Main)。
  4. 这一步很重要,而在以前的Xcode和Swift版本中却没有。在Info.plist中,转到:应用程序场景清单场景配置应用程序会话角色项目0,然后在此处删除Storyboard.name行。
  5. 之后,转到SceneDelegate并在函数场景中编写下一个:

    func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
        // Use this method to optionally configure and attach the UIWindow `window` to the provided UIWindowScene `scene`.
        // If using a storyboard, the `window` property will automatically be initialized and attached to the scene.
        // This delegate does not imply the connecting scene or session are new (see `application:configurationForConnectingSceneSession` instead).
        guard let windowScene = (scene as? UIWindowScene) else { return }
    
        window = UIWindow(frame: windowScene.coordinateSpace.bounds)
        window?.windowScene = windowScene
        window?.rootViewController = ViewController()
        window?.makeKeyAndVisible()
    }

10

您还需要执行一个步骤:

1)在plist文件中删除Main Storyboard文件的基本名称

//AppDelegate.h


@property (strong, nonatomic) UIViewController *viewController;
@property (strong, nonatomic) UINavigationController *nav;

//AppDelegate.m

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {`enter code here`
    // Override point for customization after application launch.

    CGRect screenBounds = [[UIScreen mainScreen] bounds];

    UIWindow *window = [[UIWindow alloc] initWithFrame:screenBounds];


    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];



    self.viewController = [[UIViewController alloc] initWithNibName:@"ViewController" bundle:nil];

    self.nav = [[UINavigationController alloc] initWithRootViewController:self.viewController];

    [window setRootViewController:  self.nav];

    [window makeKeyAndVisible];

    [self setWindow:window];

    return YES;
}

2
有一个边界问题,UIScreen.mainScreen()。bounds正在打印出:(0.0,0.0,320.0,480.0)。这是为什么?
Esqarrouth,2015年

9

更新:Swift 5和iOS 13:

  1. 创建一个单视图应用程序。
  2. 删除Main.storyboard(右键单击并删除)。
  3. 从Info.plist文件的默认场景配置中删除“故事板名称”: 在此处输入图片说明
  4. 打开SceneDelegate.swiftfunc scene从以下位置更改:
func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
    // Use this method to optionally configure and attach the UIWindow `window` to the provided UIWindowScene `scene`.
    // If using a storyboard, the `window` property will automatically be initialized and attached to the scene.
    // This delegate does not imply the connecting scene or session are new (see `application:configurationForConnectingSceneSession` instead).
    guard let _ = (scene as? UIWindowScene) else { return }
}

 func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
    // Use this method to optionally configure and attach the UIWindow `window` to the provided UIWindowScene `scene`.
    // If using a storyboard, the `window` property will automatically be initialized and attached to the scene.
    // This delegate does not imply the connecting scene or session are new (see `application:configurationForConnectingSceneSession` instead).x

    if let windowScene = scene as? UIWindowScene {
        let window = UIWindow(windowScene: windowScene)
        window.rootViewController = ViewController()
        self.window = window
        window.makeKeyAndVisible()
    }
}

2
您还必须从Info.plist中删除“主故事板文件库名称”,否则会收到错误“找不到名为“主”的故事板”
Ziad Hilal19年

6

我有原始的Empty Application模板,该模板在Xcode 6之前的Xcode版本中使用过。我已经在这里上传了它。

您可以下载它并手动将其粘贴到Xcode模板目录中,也可以使用Xcode的软件包管理器Alcatraz进行安装。只需搜索Xcode空应用程序


5

删除Main.storyboard文件

可以简单地将其删除。

更新ProjectName-Info.plist文件

拔下Main storyboard base file name钥匙。

创建一个nib文件并链接到项目的视图控制器

1.创建一个笔尖文件(文件–>新建–>文件–>视图)

2,将File's Owner's类更新为项目的视图控制器

3.将File's Owner's view插座链接到viewnib文件中的对象

更新应用程序委托

1.导入项目的视图控制器的头文件

2.更新申请:didFinishLaunchingWithOptions:方法:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
    // Override point for customization after application launch.
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    MyViewController *viewController = [[MyViewController alloc] initWithNibName:@"MyViewController" bundle:nil];
    self.window.rootViewController = viewController;
    [self.window makeKeyAndVisible];
    return YES;
}

5

对于Xcode 8Swift 3 只需删除.storyboard文件,它将自动从您的文件中删除相应的引用,.plist并在您AppDelegate.swift添加以下代码。

    let initialViewController = UIViewController()
    initialViewController.view.backgroundColor = .white
    window = UIWindow(frame: UIScreen.main.bounds)
    window?.rootViewController = initialViewController
    window?.makeKeyAndVisible()

您可以编写自己的自定义ViewCountroller并将其AppDelegate.swift用作self.window?.rootViewController,只需在上面的代码中将UIViewController替换为您自己的ViewController。


1
使用Xcode 9.1和Swift 4,如果我只是删除情节提要文件而未从.plist中手动删除相应的引用,则会出现错误“在捆绑包中找不到名为'Main'的情节提要”。似乎我必须手动删除引用。
Peacetype '17

3

我正在使用XCode6 Beta,我通过从XCode5.xx向XCode6 Beta添加Empty模板来搜索此问题的另一种解决方案。

为此,右键单击“应用程序”中的XCode5.xx,单击“显示包内容”,然后从给定路径复制“ Empty Application.xctemplate”

内容/开发人员/平台/iPhoneOS.platform/开发人员/库/ Xcode /模板/项目模板/应用程序

现在退出窗口并打开XCode6的给定路径

内容/开发人员/平台/iPhoneOS.platform/Developer/Library/Xcode/Templates/Project Templates / iOS / Application /

将“ Empty Application.xctemplate”粘贴到Application文件夹中。现在,通过退出并创建新项目来重新启动XCode6。您将获得“空应用程序”选项。

现在,当我创建新的Empty项目时,将在项目中自动添加一个.pch文件(我们必须在XCode6中手动添加)

希望它能工作


1

是的,或者仅使用以前的Beta版之一进行创建,然后继续使用最新版本。



1

其他人已经解释了如何摆脱情节提要,所以我将在这里跳过。这就是我更喜欢在代码中使用较少的可选链接(用Swift 3.1编写)的方式:

func application(_ application: UIApplication,
                 didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {

    let window = UIWindow(frame: UIScreen.main.bounds)
    window.backgroundColor = .white
    window.rootViewController = MyRootViewController()
    window.makeKeyAndVisible()
    self.window = window

    return true
}

1

在Xcode 11和ios 13上进行了更新。设置完所有内容但仍然看到黑屏后,这是因为生命周期由UISceneDelegate处理,并且在创建新项目时,它将自动生成UISceneDelegate.m和UISceneDelegate.h。回到以前,我们习惯了UISceneDelegate。以下步骤可能会有所帮助:

  1. 在plist中删除Application Scene Manifest。

  2. 删除应用程序场景Manifest.h和应用程序场景Manifest.m

  3. 删除#pragma标记下的代码-APPdelegate.m中的UISceneSession生命周期

  4. 添加@property(强的,非原子的)UIWindow *窗口;在APPdelegate.h中

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.