ちょっと話題の記事

[iOS] チーム開発するなら Storyboard を分割セヨ

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

はじめに

チームで開発する際には、ソースコードを Git で管理していることが多いかと思いますが、いくら注意していたとしていても起こるのがコンフリクトです。
コンフリクトすること自体は大した問題ではありません。手動で差分を取り込めばそれでOKです。

Storyboard を除いて。。

Storyboard のコンフリクト

実際に経験したことのある人はよくご存知かと思いますが、Storyboard のコンフリクト解消は一筋縄にはいきません。 Storyboard のコンフリクトは解消できないわけではないですが、多くの時間がかかり開発効率を悪化させるので、できるなら避けたいことです。

Storyboard を分割しよう

アプリに複数の機能があると、タブで画面切替を実現することがよくあると思います。こういった場合にタブの遷移先の画面毎に Storyboard を分割すれば、複数ブランチで同時にUIの実装をしてもそれぞれ別画面の Storyboard を更新する分にはコンフリクトは発生しません。
今回は、特にタブで画面遷移をするようなアプリでの Storyboard の分割方法をご紹介します。

分割されていない Storyboard

この StoryboardXcode の新規プロジェクト作成で Tabbed Application を選択して自動で作成されたものです。今回は、この Storyboard を分割していきます。

スクリーンショット 2015-09-06 19.57.53

Storyboard を追加する

タブ遷移の数だけの Storyboard を追加します。
ここでは、元からあるMain.storyboardのほかに、First.storyboardSecond.storyboardを追加しました。ここで新たに追加された StoryboardViewController たちの引越し先となります。

スクリーンショット 2015-09-06 23.46.59

ViewController の引越し

新しく追加した StoryboardMain.storyboard内にある ViewController を移動します。
今回のケースのようにすでに ViewController が存在する場合は、シンプルに ViewController を切り取って引越し先の Storyboard に貼り付けるのが手っ取り早いのでオススメです。

それぞれに対応する Storyboard を開いて ViewController を貼り付けていきます。

スクリーンショット 2015-09-06 20.41.32 スクリーンショット 2015-09-06 20.41.57

このとき、Is Initial View Controller にチェックを入れるのを忘れずに!!

スクリーンショット_2015-09-06_20_20_16

TabBarController はひとりぼっちになりました。

スクリーンショット 2015-09-06 20.42.15

TabBarController をカスタムする

ここまでで、形だけは分割できましたが、分割したことで TabBarController から生えていた segue が切断されているので TabBarController のサブクラスを作成して遷移の処理を記述します。

MainTabBarController.m

#import "MainTabBarController.h"

@interface MainTabBarController ()

@end

@implementation MainTabBarController

- (void)viewDidLoad {
    [super viewDidLoad];
    
    NSMutableArray *viewControllers = [NSMutableArray new];
    
    // 名前を指定して UIStoryboard を生成 
    UIStoryboard *firstStoryboard = [UIStoryboard storyboardWithName:@"First" bundle:[NSBundle mainBundle]];
    
    // 生成した UIStoryboard から InitialViewController を取得する
    UIViewController *firstViewController = [firstStoryboard instantiateInitialViewController];
    
    // 配列に ViewController を追加する
    [viewControllers addObject:firstViewController];
    
    // 以下繰り返す
    UIStoryboard *secondStoryboard = [UIStoryboard storyboardWithName:@"Second" bundle:[NSBundle mainBundle]];
    UIViewController *secondViewController = [secondStoryboard instantiateInitialViewController];
    [viewControllers addObject:secondViewController];

    // TabBarController の持つ ViewController の配列に代入
    self.viewControllers = viewControllers;
}

@end

それぞれ、Storyboard から Initial View Controller を取得してself.viewControllersViewController をまとめた配列をセットしているだけです。前述したとおりに、分割した StoryboardViewControllerIs Initial View Controller にチェックが入っていないと 18行目ViewController が取得できないので注意してください。

ただ TabBarController のサブクラスを作っただけでは何も起こらないので、ひとりぼっちになった TabBarController のカスタムクラスにセットしましょう。

スクリーンショット 2015-09-06 20.42.42 スクリーンショット_2015-09-07_0_48_36

動作確認

ちゃんと画面が表示されるか確認してみます。

スクリーンショット 2015-09-06 20.49.21

このように Storyboard を分割する前と同じようになれば Storyboard の分割 は完了です。

おわりに

実際のチーム開発ではほぼ確実に Storyboard を分割し、タブ毎に分割したあとにも Storyboard が大きくなってくればその中でもまた分割して複数のメンバーで作業しやすいようにします。
たったひとつの Storyboard でも開発はできるのですが、規模が大きくなるにつれチームでも個人でも開発効率が低下することは明白です。
非効率なことやコンフリクトの解消のような非生産的な作業を少しでも減らすためにも Storyboard の分割を活用してみてはいかがでしょうか。