Saya baru saja mencelupkan kaki saya untuk pertama kalinya ke dalam pengembangan iOS, dan salah satu hal pertama yang harus saya lakukan adalah menerapkan pengontrol tampilan kontainer khusus - sebut saja SideBarViewController
- yang menukar beberapa kemungkinan pengontrol tampilan anak itu menunjukkan, hampir persis seperti Tab Bar Controller standar . (Ini cukup banyak Tab Bar Controller tetapi dengan menu samping yang dapat disembunyikan, bukan bilah tab.)
Sesuai instruksi dalam dokumentasi Apple, saya menelepon addChildViewController
setiap kali saya menambahkan ViewController anak ke penampung saya. Kode saya untuk menukar pengontrol tampilan anak saat ini yang ditunjukkan oleh SideBarViewController
tampilan seperti ini:
- (void)showViewController:(UIViewController *)newViewController {
UIViewController* oldViewController = [self.childViewControllers
objectAtIndex:0];
[oldViewController removeFromParentViewController];
[oldViewController.view removeFromSuperview];
newViewController.view.frame = CGRectMake(
0, 0, self.view.frame.size.width, self.view.frame.size.height
);
[self addChildViewController: newViewController];
[self.view addSubview: newViewController.view];
}
Kemudian saya mulai mencoba mencari tahu apa yang addChildViewController
terjadi di sini, dan saya menyadari bahwa saya tidak tahu. Selain menempelkan yang baru ViewController
di .childViewControllers
array, tampaknya tidak berpengaruh pada apa pun. Tindakan dan jalan keluar dari pandangan pengontrol anak ke pengontrol anak yang telah saya setel di papan cerita masih berfungsi dengan baik bahkan jika saya tidak pernah menelepon addChildViewController
, dan saya tidak bisa membayangkan apa lagi yang bisa terpengaruh.
Memang, jika saya menulis ulang kode saya untuk tidak menelepon addChildViewController
, dan malah terlihat seperti ini ...
- (void)showViewController:(UIViewController *)newViewController {
// Get the current child from a member variable of `SideBarViewController`
UIViewController* oldViewController = currentChildViewController;
[oldViewController.view removeFromSuperview];
newViewController.view.frame = CGRectMake(
0, 0, self.view.frame.size.width, self.view.frame.size.height
);
[self.view addSubview: newViewController.view];
currentChildViewController = newViewController;
}
... maka aplikasi saya masih berfungsi dengan sempurna, sejauh yang saya tahu!
Dokumentasi Apple tidak menjelaskan banyak tentang apa yang addChildViewController
dilakukannya, atau mengapa kami harus menyebutnya. Keseluruhan deskripsi yang relevan tentang apa yang dilakukan metode atau mengapa metode itu harus digunakan dalam bagiannya di UIViewController
Referensi Kelas adalah, saat ini:
Menambahkan pengontrol tampilan yang diberikan sebagai anak. ... Metode ini hanya dimaksudkan untuk dipanggil dengan implementasi pengontrol tampilan penampung khusus. Jika Anda mengganti metode ini, Anda harus memanggil super dalam implementasi Anda.
Ada juga paragraf ini sebelumnya di halaman yang sama:
Pengontrol tampilan penampung Anda harus mengaitkan pengontrol tampilan anak dengan dirinya sendiri sebelum menambahkan tampilan root anak ke hierarki tampilan. Ini memungkinkan iOS untuk merutekan peristiwa dengan benar ke pengontrol tampilan anak dan tampilan yang dikelola pengontrol tersebut. Demikian pula, setelah menghapus tampilan root anak dari hierarki tampilannya, pengontrol tampilan anak tersebut harus diputuskan dari dirinya sendiri. Untuk membuat atau menghancurkan asosiasi ini, penampung Anda memanggil metode tertentu yang ditentukan oleh kelas dasar. Metode ini tidak dimaksudkan untuk dipanggil oleh klien kelas penampung Anda; mereka hanya akan digunakan oleh implementasi penampung Anda untuk memberikan perilaku penahanan yang diharapkan.
Berikut adalah metode penting yang mungkin perlu Anda panggil:
addChildViewController:
removeFromParentViewController
willMoveToParentViewController:
didMoveToParentViewController:
tetapi tidak menawarkan petunjuk apa pun tentang 'peristiwa' atau 'perilaku penahanan yang diharapkan' yang dibicarakannya, atau mengapa (atau bahkan ketika) menyebut metode ini 'penting'.
Contoh pengontrol tampilan penampung khusus di bagian "Pengontrol Tampilan Penampung Khusus" dari dokumentasi Apple semuanya memanggil metode ini, jadi saya berasumsi bahwa metode ini melayani beberapa tujuan penting lebih dari sekadar memunculkan ViewController anak ke dalam larik, tetapi saya tidak mengerti tahu apa tujuan itu. Apa fungsi metode ini, dan mengapa saya harus menyebutnya?
sumber
Jawaban:
Saya juga bertanya-tanya tentang pertanyaan ini. Saya menonton video Sesi 102 dari WWDC 2011 dan Mr. View Controller, Bruce D. Nilo , mengatakan ini:
Jadi tampaknya panggilan untuk
addChildViewController:
tidak banyak membantu. Efek samping panggilan adalah bagian penting. Mereka berasal dariparentViewController
danchildViewControllers
hubungan. Berikut beberapa efek samping yang saya ketahui:transitionFromViewController:toViewController:…
mana kedua VC harus memiliki induk yang samanavigationController
,tabBarController
, dll sifatsumber
Saya pikir sebuah contoh bernilai seribu kata.
Saya sedang mengerjakan aplikasi perpustakaan dan ingin menunjukkan tampilan notepad bagus yang muncul saat pengguna ingin menambahkan catatan.
Setelah mencoba beberapa solusi, saya akhirnya menemukan solusi khusus saya sendiri untuk menampilkan notepad. Jadi ketika saya ingin menampilkan notepad, saya membuat instance baru
NotepadViewController
dan menambahkan tampilan root-nya sebagai subview ke tampilan utama. Sejauh ini baik.Kemudian saya perhatikan bahwa gambar notepad sebagian tersembunyi di bawah keyboard dalam mode lansekap.
Jadi saya ingin mengubah gambar notepad dan menggesernya ke atas. Dan untuk melakukannya, saya menulis kode yang tepat dalam
willAnimateRotationToInterfaceOrientation:duration:
metode, tetapi ketika saya menjalankan aplikasi tidak ada yang terjadi! Dan setelah debugging saya perhatikan bahwa tidak adaUIViewController
metode rotasi yang benar-benar dipanggilNotepadViewController
. Hanya metode tersebut di pengontrol tampilan utama yang dipanggil.Untuk mengatasi ini, saya perlu memanggil semua metode dari
NotepadViewController
secara manual ketika mereka dipanggil di pengontrol tampilan utama. Ini akan segera membuat segalanya menjadi rumit dan membuat ketergantungan ekstra antara komponen yang tidak terkait dalam aplikasi.Itu terjadi di masa lalu, sebelum konsep pengontrol tampilan anak diperkenalkan. Tapi sekarang, Anda hanya perlu ke
addChildViewController
pengontrol tampilan utama dan semuanya akan berfungsi seperti yang diharapkan tanpa pekerjaan manual lagi.Sunting: Ada dua kategori kejadian yang diteruskan ke pengontrol tampilan anak:
1- Metode Penampilan:
2- Metode Rotasi:
Anda juga dapat mengontrol kategori peristiwa apa yang ingin Anda teruskan secara otomatis dengan mengganti
shouldAutomaticallyForwardRotationMethods
danshouldAutomaticallyForwardAppearanceMethods
.sumber
addChildViewController
ke pengontrol induk.-[UIViewController addChildViewController:]
hanya menambahkan pengontrol tampilan yang diteruskan dalam larik viewControllers yang ingin dijadikan referensi oleh viewController (induk). Anda sebenarnya harus menambahkan sendiri tampilan viewController tersebut di layar dengan menambahkannya sebagai subview dari tampilan lain (misalnya tampilan parentViewController). Ada juga objek praktis di Interface Builder untuk menggunakan childrenViewControllers di Storyboards.Sebelumnya, untuk menyimpan referensi viewController lain yang tampilannya Anda gunakan, Anda harus menyimpan referensi manual di @properties. Memiliki properti bawaan seperti
childViewControllers
dan akibatnyaparentViewController
adalah cara mudah untuk mengelola interaksi tersebut dan membangun viewControllers yang tersusun seperti UISplitViewController yang Anda temukan di aplikasi iPad.Selain itu, childrenViewControllers juga secara otomatis menerima semua kejadian sistem yang diterima induknya: -viewWillAppear, -viewWillDisappear, dll. Sebelumnya Anda harus memanggil metode ini secara manual pada "childrenViewControllers" Anda.
Itu dia.
sumber
iOS "system events"
tidak banyak muntah; Sepertinya bukan istilah yang digunakan Apple?