Saya telah mencari-cari solusi untuk masalah ini, dan satu-satunya jawaban yang dapat saya temukan adalah " jangan masukkan ListView ke dalam ScrollView ". Saya belum melihat penjelasan nyata mengapa . Satu-satunya alasan yang dapat saya temukan adalah bahwa Google tidak berpikir Anda harus melakukan itu. Ya saya lakukan, jadi saya lakukan.
Jadi pertanyaannya adalah, bagaimana Anda bisa menempatkan ListView ke dalam sebuah ScrollView tanpa runtuh ke ketinggian minimum?
ListView
.ListView
dapat memiliki beberapa gaya baris, ditambah baris yang tidak dapat dipilih.Jawaban:
Menggunakan
ListView
untuk membuatnya tidak gulir sangat mahal dan bertentangan dengan seluruh tujuanListView
. Anda TIDAK boleh melakukan ini. Cukup gunakanLinearLayout
saja.sumber
How can I put a ListView into a ScrollView without it collapsing?
... Anda bisa mengatakan bahwa Anda seharusnya tidak melakukannya, tetapi juga memberikan jawaban tentang bagaimana melakukannya, itu jawaban yang bagus. Anda tahu bahwa ListView memiliki beberapa fitur keren lain selain pengguliran, fitur yang tidak dimiliki LinearLayout.Inilah solusi saya. Saya cukup baru di platform Android, dan saya yakin ini agak meretas, terutama di bagian tentang memanggil pengukuran langsung, dan mengatur
LayoutParams.height
properti secara langsung, tetapi berfungsi.Yang harus Anda lakukan adalah menelepon
Utility.setListViewHeightBasedOnChildren(yourListView)
dan akan diubah ukurannya untuk mengakomodasi ketinggian barang-barangnya.sumber
LinearLayout
tidak memiliki semua sifat bawaan dari aListView
- ia tidak memiliki pembagi, tampilan header / footer, pemilih daftar yang cocok dengan warna tema UI ponsel, dll. Jujur, tidak ada alasan mengapa Anda tidak dapat menggulir wadah bagian dalam sampai mencapai ujung dan kemudian berhenti mencegat acara sentuh sehingga wadah luar bergulir. Setiap browser desktop melakukan ini saat Anda menggunakan roda gulir Anda. Android sendiri dapat menangani penggulungan bersarang jika Anda menavigasi melalui trackball, jadi mengapa tidak melalui sentuhan?listItem.measure(0,0)
akan melempar NPE jika listItem adalah instance ViewGroup. Saya menambahkan yang berikut sebelumnyalistItem.measure
:if (listItem instanceof ViewGroup) listItem.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT));
int totalHeight = listView.getPaddingTop() + listView.getPaddingBottom();
ListView
dapat berisi item dengan tinggi variabel. Panggilan untukgetMeasuredHeight()
hanya mengembalikan tinggi minimum yang ditargetkan sebagai lawan dari tinggi aktual. Saya mencoba menggunakangetHeight()
sebagai gantinya, tetapi ini mengembalikan 0. Apakah ada yang punya wawasan tentang cara mendekati ini?Ini pasti akan bekerja ............
Anda harus hanya mengganti Anda
<ScrollView ></ScrollView>
dalam tata letak file XML dengan iniCustom ScrollView
seperti<com.tmd.utils.VerticalScrollview > </com.tmd.utils.VerticalScrollview >
sumber
Insted menempatkan
ListView
di dalamScrollView
, kita dapat menggunakanListView
sebagaiScrollView
. Hal-hal yang harus diListView
dapat dimasukkan ke dalamListView
. Layout lain di atas dan bawahListView
dapat dimasukkan dengan menambahkan layout ke header dan footerListView
. Jadi keseluruhannyaListView
akan memberi Anda pengalaman menggulir.sumber
Ada banyak situasi di mana masuk akal untuk memiliki ListView di ScrollView.
Berikut kode berdasarkan saran DougW ... bekerja dalam sebuah fragmen, membutuhkan lebih sedikit memori.
panggil setListViewHeightBasedOnChildren (listview) pada setiap tampilan daftar yang disematkan.
sumber
ListView sebenarnya sudah mampu mengukur dirinya cukup tinggi untuk menampilkan semua item, tetapi tidak melakukan ini ketika Anda cukup menentukan wrap_content (MeasureSpec.UNSPECIFIED). Ini akan melakukan ini ketika diberi ketinggian dengan MeasureSpec.AT_MOST. Dengan pengetahuan ini, Anda dapat membuat subclass yang sangat sederhana untuk menyelesaikan masalah ini yang bekerja jauh lebih baik daripada solusi yang diposting di atas. Anda harus tetap menggunakan wrap_content dengan subclass ini.
Memanipulasi heightMeasureSpec menjadi AT_MOST dengan ukuran yang sangat besar (Integer.MAX_VALUE >> 4) menyebabkan ListView mengukur semua anak-anaknya hingga ketinggian (sangat besar) yang diberikan dan mengatur tingginya.
Ini berfungsi lebih baik daripada solusi lain karena beberapa alasan:
Pada sisi negatifnya, Anda bisa berpendapat bahwa melakukan ini bergantung pada perilaku tidak berdokumen di SDK yang dapat berubah. Di sisi lain, Anda bisa berpendapat bahwa ini adalah bagaimana wrap_content harus benar-benar berfungsi dengan ListView dan bahwa perilaku wrap_content saat ini baru saja rusak.
Jika Anda khawatir bahwa perilaku tersebut dapat berubah di masa mendatang, Anda cukup menyalin fungsi onMeasure dan fungsi terkait dari ListView.java dan ke dalam subkelas Anda sendiri, lalu buat jalur AT_MOST melalui onMeasure yang dijalankan untuk UNSPECIFIED juga.
Omong-omong, saya percaya bahwa ini adalah pendekatan yang benar-benar valid ketika Anda bekerja dengan sejumlah kecil item daftar. Mungkin tidak efisien jika dibandingkan dengan LinearLayout, tetapi ketika jumlah item kecil, menggunakan LinearLayout adalah optimasi yang tidak perlu dan karenanya kompleksitas yang tidak perlu.
sumber
Ada pengaturan bawaan untuk itu. Di ScrollView:
Di jawa
Romain Guy menjelaskannya secara mendalam di sini: http://www.curious-creature.org/2010/08/15/scrollviews-handy-trick/
sumber
Anda Membuat Custom ListView yang bukan dapat digulir
Di File Sumber Daya Tata Letak Anda
Dalam Java File
Buat objek customListview Anda, bukan ListView seperti: NonScrollListView non_scroll_list = (NonScrollListView) findViewById (R.id.lv_nonscroll_list);
sumber
Kami tidak dapat menggunakan dua pengguliran secara simulteniuosly. Kami akan mendapatkan total panjang ListView dan memperluas listview dengan tinggi total. Kemudian kami dapat menambahkan ListView di ScrollView secara langsung atau menggunakan LinearLayout karena ScrollView memiliki satu anak secara langsung. salin metode setListViewHeightBasedOnChildren (lv) dalam kode Anda dan perluas listview maka Anda bisa menggunakan listview di dalam scrollview. \ tata letak file xml
Metode onCreate di kelas aktivitas:
sumber
Ini adalah kombinasi dari jawaban oleh DougW, Good Guy Greg, dan Paul. Saya menemukan itu semua diperlukan ketika mencoba menggunakan ini dengan adaptor listview khusus dan item daftar non-standar jika tidak, listview merusak aplikasi (juga macet dengan jawaban oleh Nex):
sumber
Anda tidak boleh meletakkan ListView di ScrollView karena ListView sudah merupakan ScrollView. Jadi itu akan seperti meletakkan ScrollView di ScrollView.
Apa yang ingin Anda capai?
sumber
Saya mengkonversi @ DougW
Utility
menjadi C # (digunakan di Xamarin). Berikut ini berfungsi dengan baik untuk item ketinggian tetap dalam daftar, dan sebagian besar akan baik-baik saja, atau setidaknya awal yang baik, jika hanya beberapa item yang sedikit lebih besar dari item standar.Terima kasih @DougW, ini membuat saya keluar dari tempat yang sempit ketika saya harus bekerja dengan OtherPeople'sCode. :-)
sumber
setListViewHeightBasedOnChildren()
metode ini? Karena itu tidak berfungsi sepanjang waktu untuk saya.Ini adalah satu-satunya hal yang berhasil untuk saya:
pada Lollipop dan seterusnya, Anda dapat menggunakan
Ini mengaktifkan atau menonaktifkan pengguliran bersarang untuk tampilan ini jika Anda memerlukan kompatibilitas mundur dengan versi OS yang lebih lama Anda harus menggunakan RecyclerView.
sumber
Sebelumnya itu tidak mungkin. Tetapi dengan dirilisnya pustaka Appcompat baru dan pustaka Desain, ini dapat dicapai.
Anda hanya perlu menggunakan NestedScrollView https://developer.android.com/reference/android/support/v4/widget/NestedScrollView.html
Saya tidak tahu ini akan bekerja dengan Listview atau tidak tetapi berfungsi dengan RecyclerView.
Cuplikan Kode:
sumber
hei saya punya masalah serupa. Saya ingin menampilkan tampilan daftar yang tidak menggulir dan saya menemukan bahwa memanipulasi parameter berfungsi tetapi tidak efisien dan akan berperilaku berbeda pada perangkat yang berbeda .. sebagai hasilnya, ini adalah bagian dari kode jadwal saya yang sebenarnya melakukan ini dengan sangat efisien .
Catatan: jika Anda menggunakan ini,
notifyDataSetChanged();
tidak akan berfungsi sebagaimana dimaksud karena tampilan tidak akan digambar ulang. Lakukan ini jika Anda perlu bekerjasumber
Ada dua masalah saat menggunakan ListView di dalam ScrollView.
1- ListView harus sepenuhnya diperluas hingga ketinggian anak-anaknya. ListView ini menyelesaikan ini:
Tinggi pembagi harus 0, gunakan bantalan dalam baris sebagai gantinya.
2- ListView mengkonsumsi acara sentuh sehingga ScrollView tidak dapat digulir seperti biasa. ScrollView ini menyelesaikan masalah ini:
Ini adalah cara terbaik yang saya temukan untuk melakukan trik!
sumber
Solusi yang saya gunakan adalah, untuk menambahkan semua Konten ScrollView (apa yang harus di atas dan di bawah listView) sebagai headerView dan footerView di ListView.
Jadi berfungsi seperti itu, juga konversi diatur ulang bagaimana seharusnya.
sumber
terima kasih untuk kode Vinay di sini adalah kode saya ketika Anda tidak dapat memiliki tampilan daftar di dalam scrollview namun Anda memerlukan sesuatu seperti itu
relativeLayout tetap berada di dalam ScrollView sehingga semuanya menjadi scrollable :)
sumber
Berikut ini adalah modifikasi kecil pada @djunod 's jawaban yang saya butuhkan untuk membuatnya bekerja dengan sempurna:
sumber
coba ini, ini bekerja untuk saya, saya lupa di mana saya menemukannya, di suatu tempat di stack overflow, saya di sini bukan untuk menjelaskan mengapa itu tidak berhasil, tapi ini jawabannya :).
EDIT !, Saya akhirnya menemukan di mana saya mendapatkan kode. di sini! : ListView di dalam ScrollView tidak menggulir di Android
sumber
Meskipun metode setListViewHeightBasedOnChildren () yang disarankan bekerja di sebagian besar kasus, dalam beberapa kasus, khususnya dengan banyak item, saya perhatikan bahwa elemen terakhir tidak ditampilkan. Jadi saya memutuskan untuk meniru versi sederhana dari perilaku ListView untuk menggunakan kembali kode Adaptor, ini dia alternatif ListView:
sumber
Semua jawaban ini salah !!! Jika Anda mencoba untuk menempatkan tampilan daftar dalam tampilan gulir, Anda harus memikirkan kembali desain Anda. Anda mencoba untuk meletakkan ScrollView di dalam ScrollView. Mengganggu daftar akan merusak kinerja daftar. Itu dirancang untuk menjadi seperti ini oleh Android.
Jika Anda benar-benar ingin daftar berada dalam gulir yang sama dengan elemen lainnya, yang harus Anda lakukan adalah menambahkan item lain ke bagian atas daftar menggunakan pernyataan sakelar sederhana di adaptor Anda:
Adaptor daftar dapat menangani semuanya karena hanya membuat apa yang terlihat.
sumber
Seluruh masalah ini hanya akan hilang jika LinearLayout memiliki metode setAdapter, karena saat itu ketika Anda memberi tahu seseorang untuk menggunakannya, alternatifnya adalah sepele.
Jika Anda benar-benar menginginkan scroll ListView di dalam tampilan scroll lain, ini tidak akan membantu, tetapi jika tidak, ini setidaknya akan memberi Anda ide.
Anda perlu membuat adaptor khusus untuk menggabungkan semua konten yang ingin Anda gulir dan mengatur adaptor ListView itu.
Saya tidak memiliki kode sampel yang berguna, tetapi jika Anda menginginkan sesuatu seperti.
Maka Anda perlu membuat adaptor yang mewakili semua konten itu. ListView / Adapters cukup pintar untuk menangani berbagai jenis juga, tetapi Anda harus menulis sendiri adaptor.
Android UI API tidak setua apa pun yang ada di luar sana, sehingga tidak memiliki kualitas yang sama dengan platform lainnya. Juga, ketika melakukan sesuatu di android Anda harus berada dalam pola pikir android (unix) di mana Anda berharap untuk melakukan apa pun yang Anda mungkin harus merakit fungsi bagian-bagian yang lebih kecil dan menulis banyak kode Anda sendiri untuk mendapatkannya kerja.
sumber
Ketika kita menempatkan
ListView
di dalamScrollView
dua masalah muncul. Salah satunya adalahScrollView
mengukur anak-anaknya dalam mode UNSPECIFIED, jadiListView
atur sendiri tingginya untuk mengakomodasi hanya satu item (saya tidak tahu mengapa), yang lainScrollView
mencegat acara sentuh sehinggaListView
tidak menggulir.Tetapi kita dapat menempatkan
ListView
di dalamScrollView
dengan beberapa solusi. Posting ini , oleh saya, menjelaskan solusinya. Dengan solusi ini, kami juga dapat mempertahankanListView
fitur daur ulang.sumber
Alih-alih menempatkan tampilan daftar di dalam Scrollview, taruh sisa konten antara tampilan daftar dan pembukaan Scrollview sebagai tampilan terpisah dan mengatur tampilan itu sebagai header dari tampilan daftar. Jadi akhirnya Anda hanya akan berakhir dengan tampilan daftar yang mengambil alih Scroll.
sumber
Perpustakaan ini adalah solusi termudah dan tercepat untuk masalah ini.
sumber
Ini adalah versi kode saya yang menghitung tinggi total tampilan daftar. Yang ini bekerja untuk saya:
sumber