Bagaimana saya bisa mengkonfigurasi secara terprogram (dan dengan metode apa) UILabel yang tingginya tergantung pada teksnya? Saya sudah mencoba mengaturnya menggunakan kombinasi Storyboard dan kode, tetapi tidak berhasil. Semua orang merekomendasikan sizeToFit
saat mengatur lineBreakMode
dan numberOfLines
. Namun, tidak peduli jika saya menempatkan kode yang di viewDidLoad:
, viewDidAppear:
, atau viewDidLayoutSubviews
saya tidak bisa mendapatkannya untuk bekerja. Entah saya membuat kotak terlalu kecil untuk teks yang panjang dan tidak tumbuh, atau saya membuatnya terlalu besar dan tidak menyusut.
ios
ios6
uilabel
autolayout
circuitlego
sumber
sumber
label.sizeToFit()
Xcode / viewController, batasannya sudah cukup. tidak membuat label di Playground . Sejauh ini satu-satunya cara saya menemukannya untuk bekerja di Playground adalah dengan melakukanlabel.sizeToFit()
Jawaban:
Harap dicatat bahwa dalam kebanyakan kasus , solusi Matt berfungsi seperti yang diharapkan. Tetapi jika itu tidak berhasil untuk Anda, silakan baca lebih lanjut.
Untuk membuat label Anda mengubah ukuran ketinggian secara otomatis, Anda perlu melakukan hal berikut:
Sebagai contoh:
Menggunakan Interface Builder
Siapkan empat kendala. Batasan ketinggian adalah wajib.
Lalu pergi ke inspektur atribut label dan atur jumlah baris ke 0.
Pergi ke inspektur ukuran label dan tingkatkan ContentHuggingPriority vertikal dan ContentCompressionResistancePriority vertikal.
Pilih dan edit batasan ketinggian.
Dan mengurangi prioritas batasan ketinggian.
Nikmati. :)
sumber
preferredMaxLayoutWidth
atau sematkan lebar label (atau sisi kanan dan kirinya). Itu saja! Kemudian secara otomatis akan tumbuh dan menyusut secara vertikal agar sesuai dengan isinya.Di iOS 6, menggunakan autolayout, jika sisi (atau lebar) UILabel disematkan, ia akan secara otomatis tumbuh dan menyusut secara vertikal agar sesuai dengan isinya, tanpa kode sama sekali dan tanpa mengacaukan ketahanan kompresi atau apa pun. Ini sangat sederhana.
Dalam kasus yang lebih kompleks, cukup atur labelnya
preferredMaxLayoutWidth
.Either way, hal yang benar terjadi secara otomatis.
sumber
label.sizeToFit()
Meskipun pertanyaan menyatakan secara pemrograman, setelah mengalami masalah yang sama, dan lebih suka bekerja di Interface Builder, saya pikir mungkin berguna untuk menambahkan jawaban yang ada dengan solusi Interface Builder.
Hal pertama yang harus dilupakan
sizeToFit
. Tata Letak Otomatis akan menangani ini atas nama Anda berdasarkan pada ukuran konten intrinsik.Masalahnya adalah, bagaimana cara mendapatkan label agar sesuai dengan kontennya dengan Tata Letak Otomatis? Khususnya - karena pertanyaan menyebutkannya - tinggi. Perhatikan bahwa prinsip yang sama berlaku untuk lebar.
Jadi mari kita mulai dengan contoh UILabel yang memiliki tinggi diatur ke tinggi 41px:
Seperti yang dapat Anda lihat di layar ambil di atas,
"This is my text"
memiliki bantalan di atas dan di bawah. Itu adalah padding di antara ketinggian UILabel, dan isinya, teks.Jika kami menjalankan aplikasi di simulator, tentu saja, kami melihat hal yang sama:
Sekarang, mari kita pilih label UIL di Interface Builder, dan lihat pengaturan default di inspektur Ukuran:
Perhatikan kendala yang disorot di atas. Itulah Prioritas Memeluk Konten . Seperti yang dijelaskan Erica Sadun dalam iOS Auto Layout Demystified , ini adalah:
Bagi kami, dengan UILabel, konten intinya adalah teks.
Di sini kita sampai pada inti dari skenario dasar ini. Kami telah memberi dua batasan pada label teks kami. Mereka saling bertentangan. Seseorang mengatakan "tingginya harus sama dengan tinggi 41 piksel" . Yang lain mengatakan "memeluk tampilan untuk konten itu sehingga kami tidak memiliki bantalan tambahan" . Dalam kasus kami, peluk tampilan ke teks itu sehingga kami tidak memiliki bantalan tambahan.
Sekarang, dengan Tata Letak Otomatis, dengan dua instruksi berbeda yang mengatakan melakukan hal yang berbeda, runtime harus memilih satu atau yang lain. Tidak bisa melakukan keduanya. UILabel tidak boleh memiliki tinggi 41 piksel, dan tidak memiliki bantalan.
Cara ini diselesaikan, adalah dengan menentukan prioritas. Satu instruksi harus memiliki prioritas yang lebih tinggi daripada instruksi lainnya. Jika kedua instruksi mengatakan hal yang berbeda, dan memiliki prioritas yang sama, pengecualian akan terjadi.
Jadi mari kita mencobanya. Batasan tinggi badan saya memiliki prioritas 1000 , yang diperlukan . Tinggi konten memeluk adalah 250 , yang lemah . Apa yang terjadi jika kita mengurangi prioritas batasan ketinggian menjadi 249 ?
Sekarang kita bisa melihat keajaiban mulai terjadi. Mari kita coba di sim:
Luar biasa! Pelukan konten tercapai. Hanya karena prioritas tinggi 249 kurang dari prioritas konten yang dipeluk 250 . Pada dasarnya, saya katakan "ketinggian yang saya tentukan di sini kurang penting daripada apa yang saya tentukan untuk memeluk konten" . Jadi, konten yang dipeluk menang.
Intinya, mendapatkan label agar sesuai dengan teks dapat sesederhana menetapkan batasan tinggi - atau lebar, dan memperbaiki pengaturan yang diprioritaskan terkait dengan kendala prioritas memeluk konten sumbu.
Akan meninggalkan melakukan yang setara dengan lebar sebagai latihan untuk pembaca!
sumber
Tercatat dalam ukuran iOS7 iOSToFit tidak bekerja juga - mungkin solusinya dapat membantu Anda juga
sumber
layoutIfNeeded
ketika Anda membutuhkannyasetNeedsUpdateConstraints
. Tetapi situasinya mungkin sedikit berbeda.Opsi lain untuk memastikanMaxLayoutWidth label yang disukai tetap sinkron dengan lebar label:
sumber
Saya merasa harus berkontribusi karena butuh beberapa saat untuk menemukan solusi yang tepat:
Pada dasarnya, yang terjadi adalah Anda memberi tahu UILabel bahwa meskipun memiliki batasan ketinggian yang tetap, itu dapat membuat mematahkan batasan untuk menjadikan dirinya lebih kecil untuk memeluk konten (jika Anda memiliki satu baris misalnya), tetapi tidak dapat mematahkan batasan untuk membuatnya lebih besar.
sumber
Dalam kasus saya, saya membuat subkelas UIView yang berisi UILabel (dengan panjang yang tidak diketahui). Di iOS7 kodenya mudah: atur batasannya, jangan khawatir tentang konten yang dipeluk atau resistensi kompresi, dan semuanya berfungsi seperti yang diharapkan.
Namun di iOS6, UILabel selalu terpotong menjadi satu baris. Tidak ada jawaban di atas yang berfungsi untuk saya. Pengaturan pelukan konten dan resistensi kompresi diabaikan. Satu-satunya solusi yang mencegah kliping adalah dengan memasukkanMaxLayoutWidth yang disukai pada label. Tapi saya tidak tahu harus mengatur lebar yang disukai, karena ukuran tampilan induknya tidak diketahui (memang, itu akan ditentukan oleh konten).
Saya akhirnya menemukan solusinya di sini . Karena saya sedang mengerjakan tampilan kustom, saya bisa menambahkan metode berikut untuk mengatur lebar tata letak yang disukai setelah kendala dihitung sekali, dan kemudian menghitung ulang mereka:
sumber
saya tambahkan
UILabel
pemrograman dan dalam kasus saya itu sudah cukup:sumber
Saya telah menyelesaikan dengan xCode6 menempatkan "Lebar yang Diinginkan" ke Otomatis dan pin atas label, memimpin dan mengikuti
sumber
sumber
Saya mengalami masalah ini juga dengan subkelas UIView yang berisi UILabel sebagai salah satu jika elemen internalnya. Bahkan dengan pembayaran otomatis dan mencoba semua solusi yang disarankan, label tidak akan memperketat ketinggiannya ke teks. Dalam kasus saya, saya hanya ingin label menjadi satu baris.
Bagaimanapun, apa yang berhasil bagi saya adalah menambahkan batasan ketinggian yang diperlukan untuk UILabel dan mengaturnya secara manual ke ketinggian yang benar ketika intrinsicContentSize dipanggil. Jika Anda tidak memiliki UILabel yang terkandung dalam UIView lain, Anda dapat mencoba subclassing UILabel dan memberikan implementasi yang serupa dengan terlebih dahulu menetapkan batasan ketinggian dan kemudian mengembalikan
[super instrinsicContentSize]; bukannya [self.containerview intrinsiceContentSize]; seperti yang saya lakukan di bawah ini yang khusus untuk subkelas UIView saya.
Sekarang berfungsi dengan baik di iOS 7 dan iOS 8.
sumber
intrinsicContentSize
. Runtime harus dapat menghitung ini berdasarkan batasan pengaturan Anda dengan benar.Solusi yang berhasil untuk saya; Jika UILabel Anda memiliki lebar tetap, ubah kendala dari
constant =
menjadiconstant <=
di file antarmuka Andasumber
Dalam kasus saya ketika menggunakan label dalam UITableViewCell, label at akan mengubah ukuran tetapi tingginya akan menyerbu ketinggian sel tabel. Inilah yang bekerja untuk saya. Saya lakukan sesuai dengan Max MacLeod, dan kemudian memastikan tinggi sel diatur ke UITableViewAutomaticDimension.
Anda dapat menambahkan ini di init Anda atau awakeFromNib,
Di storyboard, pilih sel, buka inspektur Ukuran, dan pastikan tinggi baris diatur ke "Default" dengan mencentang kotak centang 'Kustom'.
Ada masalah di 8.0 yang juga mengharuskannya diatur dalam kode.
sumber