質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.51%
Swift

Swiftは、アップルのiOSおよびOS Xのためのプログラミング言語で、Objective-CやObjective-C++と共存することが意図されています

Q&A

解決済

1回答

1123閲覧

DatePickerの値を完了ボタンを押されたタイミングで取り出したい

LunarStrain

総合スコア14

Swift

Swiftは、アップルのiOSおよびOS Xのためのプログラミング言語で、Objective-CやObjective-C++と共存することが意図されています

0グッド

0クリップ

投稿2018/07/08 08:18

前提・実現したいこと

Swift歴 約1ヶ月の初心者です。

ストップウォッチのラップタイムの様に、過去の時間がセットされたtableview cellがあり、タップするとDate Pickerが現れて、そのセルのデータが書き換えられる様にしたいです。

Date Pickerと完了ボタンを表示しており、完了ボタンを押した時にセットされているDate Pickerの値で、元のデータを更新したいです。

発生している問題・エラーメッセージ

完了ボタンを押した時にDate Pickerや完了ボタンを消すことは何とかできましたが、そのタイミングで値を取り出すことができません。

どの様なコードを書けば実現可能か、ご教示頂けると助かります。

該当のソースコード

Swift4

1 //セルをタップするとDatePickerを呼び出す 2 func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) { 3 4 tableView.deselectRow(at: indexPath as IndexPath, animated: true) 5 6 //元のデータは、2次元配列に過去時間を入れてある 7 let beforeChangeDate:String! = self.thingsList[self.pathNumber!][indexPath.row + 1] 8 9 let datePicker: UIDatePicker = UIDatePicker() 10 11 //日時データのフォーマット設定 12 let dateFormatter = DateFormatter() 13 dateFormatter.locale = Locale(identifier: "ja_JP") 14 dateFormatter.dateStyle = .long 15 dateFormatter.timeStyle = .medium 16 dateFormatter.dateFormat = "yyyy年M月d日 H時mm分ss秒" 17 let beforeChangeDateTypeDate = dateFormatter.date(from: (beforeChangeDate)) 18 19 // ピッカー設定 20 datePicker.datePickerMode = UIDatePickerMode.date 21 datePicker.locale = Locale(identifier: "ja_JP") 22 datePicker.frame = CGRect(x:0, y:(self.view.frame.height / 1 - 240), width:self.view.frame.width, height:240) 23 datePicker.backgroundColor = UIColor.white 24 datePicker.tag = 2 25 26 // ピッカー初期値に元データを代入 27 if let beforeChangeDateTypeDate = beforeChangeDateTypeDate { 28 datePicker.date = beforeChangeDateTypeDate 29 } 30 31 // ピッカーの表示 32 view.addSubview(datePicker) 33 34 // 完了ボタンのツールバー設定 35 let toolbar = UIToolbar(frame: CGRect(x: 0, y: (self.view.frame.height / 1 - 240 ), width: view.frame.size.width, height: 35)) 36 let spacelItem = UIBarButtonItem(barButtonSystemItem: .flexibleSpace, target: self, action: nil) 37 let doneItem = UIBarButtonItem(barButtonSystemItem: .done, target: self, action: #selector (doneButton)) 38 toolbar.setItems([spacelItem, doneItem], animated: true) 39 toolbar.tag = 2 40 41 // ツールバーの表示 42 view.addSubview(toolbar) 43 44 45 //ここの部分(元データの更新処理)を完了ボタンが押された時に動作させたい 46 // @objc funcの中に移動させてもdatePickerの値やindexPath.rowの値が引き継がれない 47 let pickerDate = datePicker.date 48 let strPickerDate = "(dateFormatter.string(from:pickerDate))" 49 50 self.thingsList[self.pathNumber!][indexPath.row + 1] = strPickerDate 51 52 tableView.reloadData() 53 //ここまで 54 55 } 56 57 // 完了ボタン押下 (ここの処理ももっと良い書き方があるのかと思いますが、、) 58 @objc func doneButton(parentView:UIView,sender:UIBarButtonItem) { 59 //ピッカーを消す 60 let delview = self.view.viewWithTag(2) 61 delview?.removeFromSuperview() 62 //ツールバーを消す 63 let delview2 = self.view.viewWithTag(2) 64 delview2?.removeFromSuperview() 65 } 66 67

試したこと

@objc funcの中に元データの更新処理部分を移動させてもdatePickerの値やindexPath.rowの値の取得の仕方がわからず、詰まってしまいました。

補足情報(FW/ツールのバージョンなど)

xcode9.4.1 , swift4

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

自己解決

この辺を見て、少し理解できました。

”#selector" に複数の引数を持たせたいです

【UIButton】addTargetのSelector経由でString型パラメタを渡す【Swift3.0】

"#selector"には複数の引数を持たせることはできないので、サブクラスを作ってプロパティに埋め込むという方法をとるそう。

fuzzballさんからコメントを頂きまして、以下の通りに直したらやりたかったことができました。
もっとまだシンプルにできそうですが、それはまたこれからの勉強ということで。

ありがとうございました。

//引き渡したいデータを入れるプロパティ用のサブクラス準備 class DoneButton:UIBarButtonItem { var pickerSend = UIDatePicker() var index:Int = 0 var tableData = UITableView() var toolBarForm = UIToolbar() } //セルをタップするとDatePickerを呼び出す func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {   tableView.deselectRow(at: indexPath as IndexPath, animated: true) //元のデータは、2次元配列に過去時間を入れてある let beforeChangeDate:String! = self.thingsList[self.pathNumber!][indexPath.row + 1] let datePicker: UIDatePicker = UIDatePicker() let dateFormatter = DateFormatter() dateFormatter.locale = Locale(identifier: "ja_JP") dateFormatter.dateStyle = .long dateFormatter.timeStyle = .medium dateFormatter.dateFormat = "yyyy年M月d日 H時mm分ss秒" // ピッカー設定 datePicker.datePickerMode = UIDatePickerMode.date datePicker.locale = Locale(identifier: "ja_JP") datePicker.frame = CGRect(x:0, y:(self.view.frame.height / 1 - 240), width:self.view.frame.width, height:240) datePicker.backgroundColor = UIColor.white // ピッカーの表示 view.addSubview(datePicker) // 完了ボタンのツールバー設定 let toolbar = UIToolbar(frame: CGRect(x: 0, y: (self.view.frame.height / 1 - 240 ), width: view.frame.size.width, height: 35)) let spacelItem = UIBarButtonItem(barButtonSystemItem: .flexibleSpace, target: self, action: nil) //完了ボタンが押されるとfunc doneButtonへ let doneItem = DoneButton(barButtonSystemItem: .done, target: self, action: #selector (doneButton)) //その時に持っていくデータをサブクラスのプロパティに放り込んでおく doneItem.pickerSend = datePicker doneItem.toolBarForm = toolbar doneItem.index = indexPath.row doneItem.tableData = tableView // ツールバーの表示 toolbar.setItems([spacelItem, doneItem], animated: true) view.addSubview(toolbar) } // 完了ボタン押下 @objc func doneButton(_ sender:DoneButton) { let dateFormatter = DateFormatter() dateFormatter.locale = Locale(identifier: "ja_JP") dateFormatter.dateStyle = .long dateFormatter.timeStyle = .medium dateFormatter.dateFormat = "yyyy年M月d日 H時mm分ss秒" //ピッカーから値を取り出して、String型へ変更 let pickerDate = sender.pickerSend.date let strPickerDate = "(dateFormatter.string(from:pickerDate))" //タップされたセルの行数とtable viewを呼び出して、更新された値でtable再表示 let sendIndexPath = sender.index let tableView = sender.tableData tableView.reloadData()   //保存用変数を更新 thingsList[pathNumber!][sendIndexPath + 1] = strPickerDate //サブビュー2つを消す let datePicker = sender.pickerSend datePicker.removeFromSuperview() let toolbar = sender.toolBarForm toolbar.removeFromSuperview() }

投稿2018/07/08 13:23

編集2018/07/10 12:45
LunarStrain

総合スコア14

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

fuzzball

2018/07/09 00:30 編集

これは回答ではなく質問に追記すべきだと思いますが、それはさておき‥ Pickerから値を取るのは完了ボタンを押した後ですよね? であれば、DoneButtonにPickerを渡して、ボタンを押した後で値を取得(& remove)して下さい。 ツールバーも渡してやればremove時に楽でしょう。(viewWithTag()使う必要なし)
LunarStrain

2018/07/09 14:03 編集

ありがとうございました。実現することができました。 removeの方も修正できました。 作法も慣れずに失礼いたしました。 こうしてしまうと、折角答えていただいたのにベストアンサーがつけられず、自己解決になってしまうのですね。。。
fuzzball

2018/07/09 23:55

この回答のコードを修正して、自己解決にすれば問題ないですよ。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.51%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問