サトリク
今回は、初心者の方が一番最初につまずくところの画面間での値の受け渡しについて、わかりやすく解説していきたいと思います。
動作環境
Item | Version |
---|---|
Swift | 5.3.2 |
Xcode | 12.3 |
Interface | Storyboard |
画面遷移先に値を渡す方法
画面遷移先に渡す方法は、以下の3パターンあります。
- Segueを使って渡す方法
- Segueを使わずに渡す方法
- UserDefaultsを使って方法
今回の完成イメージ
まずは、今回の完成イメージです。
画面①でTextField
に入力した値を、画面②のLabel
で表示するという単純なアプリです。
これを3パターンの実装方法で紹介していきたいとおもいます。
現在の状態
プロジェクト作成からやるとすごく長くなってしまうので基本部分は割愛します。
画面①には、TextFieldとButtonが配置しており、NavigationControllerがついています。
画面②には、Labelが配置されています。
画面①のプログラムファイルはViewController.swiftで、TextFieldとButtonが紐づいています。
画面②のプログラムファイルは、NextViewController.swiftで、Labelが紐づいています。
という状況です。
サトリク
では早速やっていきましょう。
Segueを使って値を渡す方法
まずは、Segueを使って渡す方法を解説していきたいと思います。
- Segueをつける
- SegueにIDをつける
- 画面②に変数を用意する
- 画面③でSegueで値を渡す
- 画面②で受け取った値をLabelに代入する
まずはSegueを使うので、Segueをつけます。
「画面①へ」のボタンを選択した状態で、controlを押しながら、画面②にドラッグ&ドロップします。
ナビゲーションコントローラーを使っているので、今回は、Showを選択します。
SegueにIDをつけます。
①Segueを選択
② (Show the Attributes inspector)をクリック
③「identifier」にtoNext
と入力
次に、画面②で値を受け取る箱を用意します。
画面②のプログラムファイルに以下のように変数を宣言しましょう。
NextViewController.swift
var str = ""
画面①でこのstr
に代入して、画面②で受け取るというイメージです。
画面①で、画面②のstr
に渡したい値を代入します。
画面①のプログラムファイルに以下のブロックを記述してください。
ViewController.swift
override func prepare(for segue: UIStoryboardSegue, sender: Any?) { if segue.identifier == "toNext" { let nextView = segue.destination as! NextViewController nextView.str = textField.text! } }
画面①から遷移した場合、str
に値が代入されている状態なので、str
をそのままLabel
に代入します。
画面②のプログラムファイルで、Labelにstrを代入します。
NextViewController.swift
label.text = str
これで、値の受け渡しが完了しました!
このように、画面①で入力して画面遷移すると、画面②のLabelに代入されていると思います!
画面①(ViewController.swift)
import UIKit class ViewController: UIViewController { @IBOutlet weak var textField: UITextField! override func viewDidLoad() { super.viewDidLoad() } override func prepare(for segue: UIStoryboardSegue, sender: Any?) { if segue.identifier == "toNext" { let nextView = segue.destination as! NextViewController nextView.str = textField.text! } } @IBAction func toNextButtonAction(_ sender: Any) { //Segueを使って遷移しているため、このブロックはつかわない。 } }
画面②(NextViewController.swift)
import UIKit class NextViewController: UIViewController { @IBOutlet weak var label: UILabel! var str = "" override func viewDidLoad() { super.viewDidLoad() label.text = str } }
これが、Segueを使った画面遷移先に値を渡す方法です。
Segueを使わずに渡す方法
では、次はSegueを使わずに、値を渡す方法を解説していきたいと思います。
- 画面②にStoryboardIDをつける
- 画面②に変数を用意する
- 画面①でボタンを押した時、画面遷移と同時に、値を画面②の変数に代入する
- 画面②で受け取った値をLabelに代入する
Segueなしで画面遷移する場合は、遷移先にStoryboardIDがついていないと遷移できないので、画面遷移先にStoryboardIDをつけます。
①画面②の上のバーをクリック
② (Show the Identity inspector)を選択
③StoryboardIDにNext
と入力
画面②で受け取る箱を用意します。
画面②のプログラムファイルに以下のように変数を宣言しましょう。
NextViewController.swift
var str = ""
画面①のプログラムファイルのボタンを押した時のブロックに、以下の3行を追記しましょう。
ViewController.swift
@IBAction func toNextButtonAction(_ sender: Any) { let nextView = self.storyboard?.instantiateViewController(withIdentifier: "Next") as! NextViewController nextView.str = textField.text! self.navigationController?.pushViewController(nextView, animated: true) }
ここでは、画面遷移と同時に、nextView(NextViewController)
のstr
に値を代入しています。
画面①から遷移した場合、str
に代入されている状態なので、str
をそのままLabelに代入します。
画面②のプログラムファイルで、Labelにstr
を代入します。
NextViewController.swift
label.text = str
これで受け渡しが完了しました。実行して確認してみましょう。
このように、画面①で入力して画面遷移すると、画面②のLabelに代入されていると思います!
画面①(ViewController.swift)
import UIKit class ViewController: UIViewController { @IBOutlet weak var textField: UITextField! override func viewDidLoad() { super.viewDidLoad() } @IBAction func toNextButtonAction(_ sender: Any) { let nextView = self.storyboard?.instantiateViewController(withIdentifier: "Next") as! NextViewController nextView.str = textField.text! self.navigationController?.pushViewController(nextView, animated: true) } }
画面②(NextViewController.swift)
import UIKit class NextViewController: UIViewController { @IBOutlet weak var label: UILabel! var str = "" override func viewDidLoad() { super.viewDidLoad() label.text = str } }
これが、Segueを使わずに画面遷移先に値を渡す方法です。
UserDefaultsを使って方法
次は、UserDefaultsを使って値を渡す方法です。
値を渡すというより、画面遷移する直前に、画面①でUserDefaultsという場所に保存しておいて、画面②でUserDefaultsから取得するという感じです。
この方法は、画面遷移の仕方はSegueありでもなしでどっちでもできます。
今回は、Segueなしの画面遷移でUserDegaultsでの値受け渡しをやっていきたいと思います。
- 画面②にStoryboardIDをつける
- 画面①でボタンを押した時、画面遷移と同時に、UserDefaultsに値を保存する
- 画面②でUserDefaultsに保存された値を取得し、Labelに代入する
Segueなしで画面遷移する場合は、遷移先にIDがついていないと遷移できないので、画面遷移先にIDをつけます。
①画面②の上のバーをクリック
② (Show the Identity inspector)を選択
③StoryboardIDにNext
と入力
画面①のプログラムファイルのボタンが押された時に呼ばれるブロックに、UserDefaultsに値を保存し、画面遷移するコードを追記します。
ViewController.swift
@IBAction func toNextButtonAction(_ sender: Any) { UserDefaults.standard.set(textField.text, forKey: "str") let nextView = self.storyboard?.instantiateViewController(withIdentifier: "Next") as! NextViewController self.navigationController?.pushViewController(nextView, animated: true) }
画面②のプログラムファイルで以下のように、labelにUserDefaultsから取得した値を代入します。
NextViewController.swift
label.text = UserDefaults.standard.string(forKey: "str")
これだけで、画面遷移先に値を受け渡すことができました。
コード量としてはこれが一番少ないです。しかし、UserDefaultsの容量を使ってしまうというデメリットもありますが。。
このように、画面①で入力して画面遷移すると、画面②のLabelに代入されていると思います!
画面①(ViewController.swift)
import UIKit class ViewController: UIViewController { @IBOutlet weak var textField: UITextField! override func viewDidLoad() { super.viewDidLoad() } @IBAction func toNextButtonAction(_ sender: Any) { UserDefaults.standard.set(textField.text, forKey: "str") let nextView = self.storyboard?.instantiateViewController(withIdentifier: "Next") as! NextViewController self.navigationController?.pushViewController(nextView, animated: true) } }
画面②(NextViewController.swift)
import UIKit class NextViewController: UIViewController { @IBOutlet weak var label: UILabel! override func viewDidLoad() { super.viewDidLoad() label.text = UserDefaults.standard.string(forKey: "str") } }
これが、UserDefaultsを使った値の受け渡しです。
まとめ
ここまで画面遷移先に値を渡す方法を3パターン解説してきました。
もしうまくいかない場合は、TwitterのDMなどで教えてください。
サトリク
独学でアプリ開発は厳しくないですか?
このブログ(satorikublog)の筆者サトリクが、初心者の方に教えるサービスをはじめました。
アプリリリースまで全力でサポートします。
気軽にご相談ください!
他にもSwiftの記事を書いているの時間があったら読んでみてください。