Dengan SDK iOS:
Saya memiliki UIView
dengan UITextField
s yang memunculkan keyboard. Saya membutuhkannya untuk dapat:
Izinkan menggulir konten
UIScrollView
untuk melihat bidang teks lainnya setelah keyboard ditampilkanSecara otomatis "melompat" (dengan menggulir ke atas) atau memendek
Saya tahu bahwa saya membutuhkan UIScrollView
. Saya sudah mencoba mengubah kelas saya UIView
menjadi UIScrollView
tetapi saya masih tidak dapat menggulir kotak teks ke atas atau ke bawah.
Apakah saya harus baik UIView
dan UIScrollView
? Apakah satu masuk ke yang lain?
Apa yang perlu diterapkan untuk menggulir secara otomatis ke bidang teks aktif?
Idealnya sebanyak mungkin pengaturan komponen mungkin dilakukan di Interface Builder. Saya hanya ingin menulis kode untuk apa yang membutuhkannya.
Catatan: UIView
(atau UIScrollView
) yang saya kerjakan ditampilkan oleh tabbar ( UITabBar
), yang perlu berfungsi seperti biasa.
Sunting: Saya menambahkan bilah gulir hanya untuk saat keyboard muncul. Meskipun itu tidak diperlukan, saya merasa seperti itu menyediakan antarmuka yang lebih baik karena dengan begitu pengguna dapat menggulir dan mengubah kotak teks, misalnya.
Saya sudah membuatnya bekerja di mana saya mengubah ukuran bingkai UIScrollView
ketika keyboard naik dan turun. Saya hanya menggunakan:
-(void)textFieldDidBeginEditing:(UITextField *)textField {
//Keyboard becomes visible
scrollView.frame = CGRectMake(scrollView.frame.origin.x,
scrollView.frame.origin.y,
scrollView.frame.size.width,
scrollView.frame.size.height - 215 + 50); //resize
}
-(void)textFieldDidEndEditing:(UITextField *)textField {
//keyboard will hide
scrollView.frame = CGRectMake(scrollView.frame.origin.x,
scrollView.frame.origin.y,
scrollView.frame.size.width,
scrollView.frame.size.height + 215 - 50); //resize
}
Namun, ini tidak secara otomatis "bergerak ke atas" atau memusatkan bidang teks yang lebih rendah di area yang terlihat, yang benar-benar saya inginkan.
sumber
Jawaban:
Anda hanya perlu
ScrollView
jika konten yang Anda miliki sekarang tidak muat di layar iPhone. (Jika Anda menambahkanScrollView
sebagai superview komponen hanya untuk membuatTextField
gulir ketika keyboard muncul, maka itu tidak diperlukan.)Cara standar untuk mencegah agar
TextField
s tidak tercakup oleh keyboard adalah menggerakkan tampilan ke atas / bawah setiap kali keyboard ditampilkan.Berikut ini beberapa contoh kode:
sumber
textFieldDidBeginEditing
bagian ini.Saya juga mengalami banyak masalah dengan
UIScrollView
penyusunan beberapaUITextFields
, di antaranya, satu atau lebih dari mereka akan dikaburkan oleh keyboard ketika mereka sedang diedit.Berikut adalah beberapa hal yang perlu dipertimbangkan jika Anda
UIScrollView
tidak menggulir dengan benar.1) Pastikan ukuran konten Anda lebih besar dari
UIScrollView
ukuran bingkai. Cara untuk memahamiUIScrollViews
adalahUIScrollView
seperti jendela tampilan pada konten yang didefinisikan dalam contentSize. Jadi ketikaUIScrollview
untuk menggulir di mana saja, contentSize harus lebih besar dariUIScrollView
. Selain itu, tidak ada gulir yang diperlukan karena semua yang didefinisikan dalam contentSize sudah terlihat. BTW, contentSize standar =CGSizeZero
.2) Sekarang setelah Anda memahami bahwa
UIScrollView
itu benar-benar jendela ke "konten" Anda, cara untuk memastikan bahwa keyboard tidak mengaburkanUIScrollView's
"jendela" penglihatan Anda adalah dengan mengubah ukuranUIScrollView
sehingga ketika keyboard ada, Anda memilikiUIScrollView
jendela berukuran hanyaUIScrollView
bingkai asli. ukuran. tinggi minus ketinggian keyboard. Ini akan memastikan bahwa jendela Anda hanya area kecil yang bisa dilihat.3) Inilah intinya : Ketika saya pertama kali menerapkan ini saya pikir saya harus mendapatkan
CGRect
dari bidang teks yang diedit dan memanggilUIScrollView's
metode scrollRecToVisible. Saya menerapkanUITextFieldDelegate
metodetextFieldDidBeginEditing
dengan panggilan kescrollRecToVisible
metode. Ini benar-benar bekerja dengan efek samping aneh yang bergulir akan mengambil yangUITextField
ke posisinya. Untuk waktu yang paling lama saya tidak tahu apa itu. Lalu saya berkomentartextFieldDidBeginEditing
metode Delegasi dan semuanya bekerja !! (???). Ternyata, saya percaya yangUIScrollView
sebenarnya secara implisit membawa yang saat ini dieditUITextField
ke jendela yang dapat dilihat secara implisit. Implementasi saya terhadapUITextFieldDelegate
metode dan panggilan selanjutnya kescrollRecToVisible
redundant dan merupakan penyebab efek samping yang aneh.Jadi, inilah langkah-langkah untuk menggulirkan Anda
UITextField
dengan benarUIScrollView
ke tempatnya saat keyboard muncul.viewDidLoad
viewDidUnload
contentSize
diatur dan lebih besar dariUIScrollView
pada AndaviewDidLoad
UIScrollView
ketika keyboard hadirUIScrollView
saat keyboard hilang.UITextField
adalah tab bahkan jika keyboard sudah ada untuk menghindari menyusut yangUIScrollView
ketika itu sudah menyusutSatu hal yang perlu diperhatikan adalah
UIKeyboardWillShowNotification
kehendak menyala bahkan saat keyboard sudah ada di layar saat Anda tab pada yang lainUITextField
. Saya menangani ini dengan menggunakan ivar untuk menghindari mengubah ukuranUIScrollView
ketika keyboard sudah ada di layar. Mengubah ukuran secara tidak sengajaUIScrollView
ketika keyboard sudah ada akan menjadi bencana!Semoga kode ini menghemat beberapa dari Anda sakit kepala.
sumber
UIKeyboardBoundsUserInfoKey
sudah usang. 2. keyboardSize ada di "koordinat layar", sehingga perhitungan viewFrame Anda akan gagal jika frame diputar atau diskalakan.CGSize keyboardSize = [[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size;
sebagai gantiUIKeyboardBoundsUserInfoKey
[[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size
seharusnya[[userInfo objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size
. Solusi hebat!Sebenarnya yang terbaik hanya menggunakan implementasi Apple, seperti yang disediakan dalam dokumen . Namun, kode yang mereka berikan salah. Ganti bagian yang ditemukan
keyboardWasShown:
tepat di bawah komentar sebagai berikut:Masalah dengan kode Apple adalah sebagai berikut: (1) Mereka selalu menghitung jika intinya ada dalam bingkai tampilan, tetapi ini adalah
ScrollView
, jadi mungkin sudah digulir dan Anda harus memperhitungkan offset itu:(2) Mereka menggeser kontenOffset oleh ketinggian keyboard, tetapi kami menginginkan yang sebaliknya (kami ingin menggeser
contentOffset
oleh ketinggian yang terlihat di layar, bukan apa yang tidak):sumber
UIKeyboardFrameEndUserInfoKey
daripadaUIKeyboardFrameBeginUserInfoKey
saat mendapatkan ukuran keyboard, karena ini akan mengambil hal-hal seperti perubahan keyboard khusus dan mengaktifkan / menonaktifkan teks prediktif.self.scrollView.contentOffset = self.currentSVoffset;
Di
textFieldDidBeginEditting
dan ditextFieldDidEndEditing
panggilan fungsi[self animateTextField:textField up:YES]
seperti:Saya harap kode ini akan membantu Anda.
Dalam Swift 2
SWIFT 3
sumber
[UIView animateWithDuration: animations:^{ }];
?Hanya menggunakan TextFields:
1a) Menggunakan
Interface Builder
: Pilih Semua TextFields => Edit => Embed In => ScrollView1b) Secara manual menanamkan TextFields di UIScrollView yang disebut scrollView
2) Atur
UITextFieldDelegate
3) Atur masing-masing
textField.delegate = self;
(atau buat koneksi diInterface Builder
)4) Salin / Tempel:
sumber
textField
sudah terlihat.CGPointMake(0, textField.frame.origin.y);
keCGPointMake(0, textField.frame.origin.y + scrollView.contentInset.top);
Untuk Solusi Universal , Inilah pendekatan saya untuk mengimplementasikan IQKeyboardManager .
Langkah 1: - Saya Ditambahkan pemberitahuan global
UITextField
,UITextView
danUIKeyboard
di kelas tunggal. Saya menyebutnya IQKeyboardManager .Langkah2: - Jika ditemukan
UIKeyboardWillShowNotification
,UITextFieldTextDidBeginEditingNotification
atauUITextViewTextDidBeginEditingNotification
pemberitahuan, saya mencoba untuk mendapatkantopMostViewController
contoh dariUIWindow.rootViewController
hierarki. Agar dapat menemukanUITextField
/UITextView
di atasnya,topMostViewController.view
bingkai harus disesuaikan.Langkah 3 : - Saya menghitung jarak bergerak yang diharapkan
topMostViewController.view
sehubungan dengan tanggapan pertamaUITextField
/UITextView
.Step4: - Saya bergerak
topMostViewController.view.frame
naik / turun sesuai dengan jarak bergerak yang diharapkan.Langkah 5: - Jika ditemukan
UIKeyboardWillHideNotification
,UITextFieldTextDidEndEditingNotification
atauUITextViewTextDidEndEditingNotification
notifikasi, saya kembali mencoba untuk mendapatkantopMostViewController
contoh dariUIWindow.rootViewController
hierarki.Langkah6: - Saya menghitung jarak terganggu
topMostViewController.view
yang perlu dikembalikan ke posisi semula.Step7: - Saya mengembalikan
topMostViewController.view.frame
turun sesuai dengan jarak yang terganggu.Langkah8: - Saya instantiated instance kelas IQKeyboardManager singleton pada aplikasi load, sehingga setiap
UITextField
/UITextView
dalam aplikasi akan menyesuaikan secara otomatis sesuai dengan jarak pergerakan yang diharapkan.Itu semua yang dilakukan IQKeyboardManager untuk Anda tanpa BANYAK KODE !! hanya perlu menarik dan melepas file sumber terkait ke proyek. IQKeyboardManager juga mendukung Orientasi Perangkat , Manajemen UIToolbar Otomatis , KeybkeyboardDistanceFromTextField dan lebih dari yang Anda pikirkan.
sumber
Saya telah membuat subclass universal, drop-in
UIScrollView
,UITableView
dan bahkanUICollectionView
yang menangani memindahkan semua bidang teks di dalamnya keluar dari keyboard.Ketika keyboard akan segera muncul, subclass akan menemukan subview yang akan diedit, dan menyesuaikan frame dan konten offset untuk memastikan tampilan terlihat, dengan animasi yang cocok dengan pop-up keyboard. Saat keyboard hilang, keyboard akan mengembalikan ukuran sebelumnya.
Seharusnya pada dasarnya bekerja dengan pengaturan apa pun, baik
UITableView
antarmuka berbasis, atau yang terdiri dari tampilan yang ditempatkan secara manual.Ini dia: solusi untuk memindahkan bidang teks dari keyboard
sumber
Ini akan melakukan segalanya untuk Anda, cukup taruh ini di kelas controller tampilan Anda dan implementasikan
UITextFieldDelegate
ke view controller Anda & setel delegasi textField keself
Menerapkan metode panggilan balik delegasi:
Untuk Swift 4, 4.2, 5: Ubah
untuk
Catatan terakhir tentang implementasi ini: Jika Anda mendorong pengontrol tampilan lain ke tumpukan saat keyboard ditampilkan, ini akan membuat kesalahan ketika tampilan dikembalikan kembali ke frame tengahnya tetapi offset keyboard tidak diatur ulang. Misalnya, keyboard Anda adalah responder pertama untuk nameField, tetapi kemudian Anda menekan tombol yang mendorong Help View Controller ke tumpukan Anda. Untuk memperbaiki kesalahan offset, pastikan untuk memanggil nameField.resignFirstResponder () sebelum meninggalkan pengontrol tampilan, memastikan bahwa metode delegasi textFieldDidEndEditing dipanggil juga. Saya melakukan ini dalam metode viewWillDisappear.
sumber
self.view.frame = CGRectOffset(self.view.frame, 0, movement)
jadi saya mengubah baris itu menjadiself.view.frame.offsetInPlace(dx: 0, dy: movement)
Sudah ada banyak jawaban, tetapi masih belum ada solusi di atas yang memiliki semua hal penentuan posisi mewah yang diperlukan untuk animasi "sempurna" bebas bug, kompatibel dengan belakang, dan bebas berkedip-kedip. (bug saat menjiwai bingkai / batas dan contentOffset bersama, orientasi antarmuka yang berbeda, keyboard perpecahan iPad, ...)
Biarkan saya berbagi solusi saya:
(dengan asumsi Anda telah mengatur
UIKeyboardWill(Show|Hide)Notification
)sumber
UIApplication.shared.sendAction(...)
. Inilah versi Swift 3 dari jawaban Anda (dikurangi porsi akan disembunyikan), dengansendAction
penerapan: gist.github.com/xaphod/7aab1302004f6e933593a11ad8f5a72dShiun berkata "Ternyata, saya percaya UIScrollView sebenarnya secara implisit membawa UITextField yang saat ini diedit ke dalam jendela yang dapat dilihat secara implisit" Ini tampaknya berlaku untuk iOS 3.1.3, tetapi tidak 3.2, 4.0, atau 4.1. Saya harus menambahkan scrollRectToVisible eksplisit untuk membuat UITextField terlihat di iOS> = 3.2.
sumber
[UITextField scrollTextFieldToVisibleIfNecessary]
metode pribadi yang kemudian memanggil[UIScrollView scrollRectToVisible]
saat[UITextField becomeFirstResponder]
dipanggil. Lihat github.com/leopatras/ios_textfields_on_scrollview . Jika kendala dan pengontrol tampilan diatur dengan benar, sebenarnya tidak perlu meneleponscrollRectToVisible
secara eksplisit (setidaknya sejak iOS 11).Satu hal yang perlu dipertimbangkan adalah apakah Anda pernah ingin menggunakan
UITextField
sendiri. Saya belum menemukan aplikasi iPhone yang dirancang dengan baik yang benar-benar digunakan diUITextFields
luarUITableViewCells
.Ini akan menjadi pekerjaan tambahan, tapi saya sarankan Anda menerapkan semua tampilan entri data tampilan tabel. Tambahkan
UITextView
keUITableViewCells
.sumber
UITableView
sayangnya satu-satunya cara untuk pergi. Notifikasi keyboard rapuh dan telah berubah dari waktu ke waktu. Contoh kode pada Stack Overflow: stackoverflow.com/a/32390936/218152Dokumen ini merinci solusi untuk masalah ini. Lihatlah kode sumber di bawah 'Memindahkan Konten yang Terletak Di Bawah Keyboard'. Cukup mudah.
EDIT: Melihat ada kesalahan wee dalam contoh. Anda mungkin ingin mendengarkan
UIKeyboardWillHideNotification
bukanUIKeyboardDidHideNotification
. Kalau tidak, tampilan gulir di belakang keyboard akan terpotong selama durasi animasi penutupan keyboard.sumber
Solusi termudah ditemukan
sumber
int movement = (up ? -movementDistance : movementDistance);
if (textField.frame.origin.y < self.view.frame.size.height - keyboard.height) { movementDistance = 0 }
Tolong jangan bahwakeyboard
variabel adalah CGRect dari keyboard yang muncul yang Anda dapatkan dengan melakukan:let keyboard = (notification.userInfo?[UIKeyboardFrameEndUserInfoKey]!.CGRectValue())!
Sedikit perbaikan yang berfungsi untuk banyak UITextFields
sumber
rect.origin.y=+currTextField.frame.origin.y
bekerja dengan baik, terima kasihKode RPDP berhasil memindahkan bidang teks dari keyboard. Tetapi ketika Anda menggulir ke atas setelah menggunakan dan mengabaikan keyboard, bagian atas telah digulir keluar dari tampilan. Ini berlaku untuk Simulator dan perangkat. Untuk membaca konten di bagian atas tampilan itu, seseorang harus memuat ulang tampilan.
Bukankah kode berikut ini seharusnya menurunkan tampilan?
sumber
Saya tidak yakin apakah menggerakkan tampilan ke atas adalah pendekatan yang benar, saya melakukannya dengan cara yang berbeda, mengubah ukuran UIScrollView. Saya menjelaskannya secara terperinci pada sebuah artikel kecil
sumber
Untuk mengembalikan ke kondisi tampilan asli, tambahkan:
sumber
Coba trik singkat ini.
sumber
Ada begitu banyak solusi, tetapi saya telah menghabiskan beberapa jam sebelum mulai bekerja. Jadi, saya meletakkan kode ini di sini (cukup tempel ke proyek, modifikasi apa pun tidak perlu):
PS: Saya harap kode membantu seseorang membuat efek yang diinginkan dengan cepat. (Xcode 4.5)
sumber
@ user271753
Untuk mengembalikan tampilan Anda ke yang asli, tambahkan:
sumber
Itu tidak memerlukan tampilan gulir untuk dapat memindahkan bingkai tampilan. Anda dapat mengubah bingkai
viewcontroller's
tampilan sehingga seluruh tampilan bergerak cukup tinggi untuk menempatkan bidang teks firstresponder di atas keyboard. Ketika saya mengalami masalah ini, saya membuat subkelasUIViewController
yang melakukan ini. Itu mengamati untuk keyboard akan muncul pemberitahuan dan menemukan subview responden pertama dan (jika perlu) itu menghidupkan tampilan utama ke atas cukup sehingga responden pertama di atas keyboard. Saat keyboard bersembunyi, ia menghidupkan kembali tampilan tempat itu.Untuk menggunakan subkelas ini, buat pengontrol tampilan khusus Anda menjadi subkelas GMKeyboardVC dan itu mewarisi fitur ini (pastikan Anda menerapkan
viewWillAppear
danviewWillDisappear
mereka harus memanggil super). Kelas ada di github .sumber
Cepat 4 .
Anda Dapat Dengan Mudah Bergerak Naik Turun
UITextField
AtauUIView
DenganUIKeyBoard
DenganAnimation
sumber
Inilah solusi retas yang saya buat untuk tata letak tertentu. Solusi ini mirip dengan solusi Matt Gallagher dalam hal ini menggulir bagian ke tampilan. Saya masih baru dalam pengembangan iPhone, dan saya tidak terbiasa dengan cara kerja tata letak. Demikian, retas ini.
Implementasi saya diperlukan untuk mendukung pengguliran saat mengklik di bidang, dan juga menggulir ketika pengguna memilih berikutnya pada keyboard.
Saya punya UIView dengan ketinggian 775. Kontrol pada dasarnya tersebar dalam kelompok 3 di ruang yang besar. Saya berakhir dengan tata letak IB berikut.
Ini dia hacknya
Saya mengatur ketinggian UIScrollView menjadi 500 unit lebih besar dari tata letak yang sebenarnya (1250). Saya kemudian membuat array dengan posisi absolut yang harus saya gulir, dan fungsi sederhana untuk mendapatkannya berdasarkan nomor Tag IB.
Sekarang yang perlu Anda lakukan adalah menggunakan dua baris kode berikut di textFieldDidBeginEditing dan textFieldShouldReturn (yang terakhir jika Anda membuat navigasi bidang berikutnya)
Sebuah contoh.
Metode ini tidak 'gulir kembali' seperti metode lainnya. Ini bukan persyaratan. Sekali lagi ini untuk UIView yang cukup 'tinggi', dan saya tidak punya waktu untuk mempelajari mesin tata letak internal.
sumber
Sesuai dokumen , pada iOS 3.0,
UITableViewController
kelas secara otomatis mengubah ukuran dan reposisi tampilan tabelnya ketika ada pengeditan in-line bidang teks. Saya pikir itu tidak cukup untuk menempatkan bidang teks di dalamUITableViewCell
seperti yang telah ditunjukkan beberapa orang.Dari dokumen :
sumber
Anda hanya perlu menyalin-tempel kode contoh di bawah ini dan mengubah bidang teks Anda atau tampilan apa pun yang ingin Anda naikkan.
Langkah 1
Langkah 2
Langkah-3
Referensi : baik, Harap hargai orang ini , yang berbagi snip kode cantik ini, solusi bersih.
Semoga ini bisa membantu seseorang yang bermuka masam di luar sana.
sumber
Telah mencari tutorial yang bagus untuk pemula tentang masalah ini, temukan tutorial terbaik di sini .
Pada
MIScrollView.h
contoh di bagian bawah tutorial pastikan untuk memberi spasiseperti yang kamu lihat.
sumber
Ketika
UITextField
sedang dalamUITableViewCell
bergulir harus diatur secara otomatis.Jika tidak, mungkin karena kode / pengaturan tampilan tabel yang salah.
Misalnya ketika saya memuat ulang meja panjang saya dengan satu
UITextField
di bagian bawah sebagai berikut,kemudian textfield saya di bagian bawah dikaburkan oleh keyboard yang muncul ketika saya mengklik di dalam textfield.
Untuk memperbaikinya saya harus melakukan ini -
sumber
viewWillAppear
tidak dipanggil. DanreloadData
tidak membuat baris tertutup menjadi terlihat.Gunakan pihak ketiga ini yang tidak perlu Anda tulis satu baris pun
https://github.com/hackiftekhar/IQKeyboardManager
unduh proyek dan seret dan lepas
IQKeyboardManager
di proyek Anda. Jika Anda menemukan masalah, bacaREADME
dokumen.Benar-benar menghapus sakit kepala untuk mengelola keyboard.
sumber
Catatan : jawaban ini mengasumsikan textField Anda dalam scrollView.
Saya lebih suka berurusan dengan ini menggunakan scrollContentInset dan scrollContentOffset daripada mengacaukan bingkai pandangan saya.
Pertama mari kita dengarkan notifikasi keyboard
Langkah selanjutnya adalah menjaga properti yang mewakili responden pertama saat ini (UITextfield / UITextVIew yang saat ini memiliki keyboard).
Kami menggunakan metode delegasi untuk mengatur properti ini. Jika Anda menggunakan komponen lain, Anda akan memerlukan sesuatu yang serupa.
Perhatikan bahwa untuk bidang teks kita atur di didBeginEditing dan untuk textView di shouldBeginEditing. Ini karena textViewDidBeginEditing dipanggil setelah UIKeyboardWillShowNotification karena beberapa alasan.
Akhirnya, inilah keajaibannya
sumber
Ini solusinya menggunakan Swift.
sumber