Android Kotlin Fundamentals 07.4: Tương tác với các mục trong RecyclerView

Lớp học lập trình này nằm trong khóa học về Khái niệm cơ bản về Android Kotlin. Bạn sẽ nhận được nhiều giá trị nhất từ khóa học này nếu bạn làm việc qua các lớp học lập trình theo trình tự. Tất cả các lớp học lập trình trong khóa học đều có trên trang đích của các lớp học lập trình cơ bản về Android Kotlin.

Giới thiệu

Hầu hết các ứng dụng sử dụng danh sách và lưới để hiển thị các mục đều cho phép người dùng tương tác với các mục đó. Thao tác nhấn vào một mục trong danh sách và xem thông tin chi tiết của mục đó là trường hợp sử dụng rất phổ biến đối với kiểu tương tác này. Để đạt được điều này, bạn có thể thêm trình xử lý lượt nhấp nhằm phản hồi hành động nhấn của người dùng vào các mục bằng cách hiển thị chế độ xem chi tiết.

Trong lớp học lập trình này, bạn thêm hoạt động tương tác với RecyclerView của mình, dựa trên phiên bản mở rộng của ứng dụng theo dõi giấc ngủ trong chuỗi lớp học lập trình trước đó.

Kiến thức bạn cần có

  • Xây dựng giao diện người dùng cơ bản bằng cách sử dụng hoạt động, mảnh và chế độ xem.
  • Di chuyển giữa các mảnh và sử dụng safeArgs để chuyển dữ liệu giữa các mảnh.
  • Xem các mô hình, xem thông tin về nhà máy, phép biến đổi, LiveData và các đối tượng tiếp nhận dữ liệu của các mô hình đó.
  • Cách tạo cơ sở dữ liệu Room, tạo đối tượng truy cập dữ liệu (DAO) và xác định các đối tượng.
  • Cách sử dụng coroutine cho cơ sở dữ liệu và các tác vụ chạy trong thời gian dài khác.
  • Cách triển khai RecyclerView cơ bản bằng bố cục Adapter, ViewHolder và mục.
  • Cách triển khai liên kết dữ liệu cho RecyclerView.
  • Cách tạo và sử dụng bộ chuyển đổi liên kết để chuyển đổi dữ liệu.
  • Cách sử dụng GridLayoutManager.

Kiến thức bạn sẽ học được

  • Cách làm cho các mục trong RecyclerView có thể nhấp được. Triển khai trình nghe lượt nhấp để chuyển đến chế độ xem chi tiết khi một mục được nhấp vào.

Bạn sẽ thực hiện

  • Xây dựng dựa trên phiên bản mở rộng của ứng dụng TrackMySleepChất lượng từ lớp học lập trình trước đó trong loạt bài này.
  • Thêm một trình xử lý lượt nhấp vào danh sách của bạn và bắt đầu lắng nghe sự tương tác của người dùng. Khi một mục trong danh sách được nhấn, mục đó sẽ kích hoạt thao tác di chuyển đến một mảnh có thông tin chi tiết về mục đã nhấp. Mã dành cho người mới bắt đầu cung cấp mã cho mảnh chi tiết cũng như mã điều hướng.

Ứng dụng theo dõi giấc ngủ khởi động có hai màn hình, được biểu thị bằng các mảnh, như minh họa trong hình bên dưới.

Màn hình đầu tiên (hiển thị ở bên trái) có các nút để bắt đầu và dừng theo dõi. Màn hình hiển thị một số dữ liệu giấc ngủ của người dùng. Nút Xóa xóa vĩnh viễn tất cả dữ liệu mà ứng dụng đã thu thập cho người dùng. Màn hình thứ hai hiển thị ở bên phải, cho biết mức chọn điểm xếp hạng chất lượng giấc ngủ.

Ứng dụng này dùng một cấu trúc đơn giản có bộ điều khiển giao diện người dùng, mô hình chế độ xem, LiveData và cơ sở dữ liệu Room để duy trì dữ liệu về giấc ngủ.

Trong lớp học lập trình này, bạn thêm khả năng phản hồi khi người dùng nhấn vào một mục trong lưới, thao tác này sẽ hiển thị màn hình chi tiết như màn hình bên dưới. Mã cho màn hình này (mảnh, mô hình chế độ xem và thành phần điều hướng) được cung cấp cùng với ứng dụng khởi động và bạn sẽ triển khai cơ chế xử lý lượt nhấp.

Bước 1: Tải ứng dụng dành cho người mới bắt đầu

  1. Tải mã RecyclerViewClickHandler-Starter xuống từ GitHub và mở dự án trong Android Studio.
  2. Tạo và chạy ứng dụng theo dõi giấc ngủ dành cho người mới bắt đầu.

[Không bắt buộc] Cập nhật ứng dụng nếu bạn muốn dùng ứng dụng từ lớp học lập trình trước đây

Nếu bạn sẽ làm việc từ ứng dụng khởi động được cung cấp trong GitHub cho lớp học lập trình này, hãy chuyển sang bước tiếp theo.

Nếu bạn muốn tiếp tục sử dụng ứng dụng theo dõi giấc ngủ của riêng mình mà bạn đã tạo trong lớp học lập trình trước đó, hãy làm theo hướng dẫn bên dưới để cập nhật ứng dụng hiện có để ứng dụng có mã cho đoạn màn hình chi tiết.

  1. Ngay cả khi bạn đang tiếp tục với ứng dụng hiện có, hãy lấy mã RecyclerViewClickHandler-Starter từ GitHub để bạn có thể sao chép tệp.
  2. Sao chép tất cả các tệp trong gói sleepdetail.
  3. Trong thư mục layout, hãy sao chép tệp fragment_sleep_detail.xml.
  4. Sao chép nội dung cập nhật của navigation.xml. Thao tác này sẽ thêm thao tác cho sleep_detail_fragment.
  5. Trong gói database, trong SleepDatabaseDao, hãy thêm phương thức getNightWithId() mới:
/**
 * Selects and returns the night with given nightId.
*/
@Query("SELECT * from daily_sleep_quality_table WHERE nightId = :key")
fun getNightWithId(key: Long): LiveData<SleepNight>
  1. Trong res/values/strings, hãy thêm tài nguyên chuỗi sau:
<string name="close">Close</string>
  1. Dọn dẹp và tạo lại ứng dụng của bạn để cập nhật liên kết dữ liệu.

Bước 2: Kiểm tra mã của màn hình thông tin chi tiết về giấc ngủ

Trong lớp học lập trình này, bạn triển khai một trình xử lý lượt nhấp dẫn đến một mảnh hiển thị thông tin chi tiết về đêm ngủ được nhấp. Mã dành cho người mới bắt đầu đã chứa mảnh và sơ đồ điều hướng cho SleepDetailFragment này, vì mã đó khá dài, đồng thời các mảnh và thành phần điều hướng không thuộc lớp học lập trình này. Hãy làm quen với mã sau:

  1. Trong ứng dụng, hãy tìm gói sleepdetail. Gói này chứa mảnh, chế độ xem và nhà máy mô hình chế độ xem cho mảnh hiển thị thông tin chi tiết về một giấc ngủ.

  2. Trong gói sleepdetail, hãy mở và kiểm tra mã của SleepDetailViewModel. Mô hình chế độ xem này lấy khóa cho SleepNight và DAO trong hàm dựng.

    Nội dung của lớp sẽ có mã để lấy SleepNight cho phím đã cho và biến navigateToSleepTracker để điều khiển cách di chuyển trở lại SleepTrackerFragment khi nhấn nút Đóng.

    Hàm getNightWithId() trả về LiveData<SleepNight> và được xác định trong SleepDatabaseDao (trong gói database).

  3. Trong gói sleepdetail, hãy mở và kiểm tra mã của SleepDetailFragment. Khi xem thiết lập cho liên kết dữ liệu, mô hình chế độ xem và đối tượng tiếp nhận dữ liệu cho hoạt động điều hướng.

  4. Trong gói sleepdetail, hãy mở và kiểm tra mã của SleepDetailViewModelFactory.

  5. Trong thư mục bố cục, hãy kiểm tra fragment_sleep_detail.xml. Hãy chú ý biến sleepDetailViewModel được xác định trong thẻ <data> để dữ liệu hiển thị trong từng chế độ xem từ mô hình chế độ xem.

    Bố cục chứa ConstraintLayout chứa chất lượng giấc ngủ, TextView cho điểm xếp hạng chất lượng, TextView cho thời lượng giấc ngủ và Button để đóng mảnh chi tiết.

  6. Mở tệp navigation.xml. Đối với sleep_tracker_fragment, hãy chú ý đến thao tác mới của sleep_detail_fragment.

    Thao tác mới action_sleep_tracker_fragment_to_sleepDetailFragment, là thao tác từ đoạn theo dõi giấc ngủ đến màn hình thông tin chi tiết.

Trong nhiệm vụ này, bạn cập nhật RecyclerView để phản hồi hành động nhấn của người dùng bằng cách hiển thị màn hình thông tin chi tiết cho mục đã nhấn.

Nhận lượt nhấp và xử lý các lượt nhấp này là một nhiệm vụ gồm hai phần: Trước tiên, bạn cần nghe và nhận lượt nhấp cũng như xác định mục nào đã được nhấp. Sau đó, bạn cần phản hồi lượt nhấp bằng một hành động.

Vậy, đâu là nơi tốt nhất để thêm trình xử lý lượt nhấp cho ứng dụng này?

  • SleepTrackerFragment lưu trữ nhiều chế độ xem, và vì vậy, việc nghe đọc các sự kiện nhấp chuột ở cấp độ mảnh sẽ không cho bạn biết mục nào được nhấp vào. Tính năng này sẽ không cho bạn biết đó là một mục được nhấp vào hay một trong các thành phần trên giao diện người dùng khác.
  • Khi nghe ở cấp RecyclerView, thật khó để tìm ra chính xác mục nào trong danh sách mà người dùng đã nhấp vào.
  • Đối với ViewHolder, đối tượng nhận thông tin về một mục được nhấp vào là phù hợp nhất vì đối tượng này biểu thị một mục trong danh sách.

Mặc dù ViewHolder là nơi lý tưởng để theo dõi số lượt nhấp, nhưng thường không phải là nơi thích hợp để xử lý các lượt nhấp đó. Vậy, đâu là cách tốt nhất để xử lý các lượt nhấp?

  • Adapter hiển thị các mục dữ liệu trong các chế độ xem để bạn có thể xử lý các lượt nhấp trong bộ chuyển đổi. Tuy nhiên, nhiệm vụ của trình chuyển đổi là điều chỉnh dữ liệu để hiển thị chứ không phải xử lý logic của ứng dụng.
  • Bạn thường nên xử lý các lượt nhấp trong ViewModel, vì ViewModel có quyền truy cập vào dữ liệu và logic để xác định những gì cần xảy ra để phản hồi lượt nhấp.

Bước 1: Tạo một trình xử lý lượt nhấp và kích hoạt trình xử lý này từ bố cục mục

  1. Trong thư mục sleeptracker, hãy mở SleepNightAdapter.kt.
  2. Ở cuối tệp, ở cấp cao nhất, hãy tạo một lớp trình nghe mới, SleepNightListener.
class SleepNightListener() {
    
}
  1. Bên trong lớp SleepNightListener, hãy thêm một hàm onClick(). Khi người dùng nhấp vào chế độ xem hiển thị một mục trong danh sách, chế độ xem đó sẽ gọi hàm onClick() này. (Bạn sẽ đặt thuộc tính android:onClick của chế độ xem sau thành hàm này.)
class SleepNightListener() {
    fun onClick() = 
}
  1. Thêm đối số hàm night thuộc loại SleepNight vào onClick(). Chế độ xem biết mục đang hiển thị và thông tin đó cần được chuyển sang để xử lý lượt nhấp.
class SleepNightListener() {
    fun onClick(night: SleepNight) = 
}
  1. Để xác định chức năng của onClick(), hãy cung cấp lệnh gọi lại clickListener trong hàm dựng của SleepNightListener và chỉ định lệnh gọi lại đó cho onClick().

    Việc dùng hàm lambda xử lý lượt nhấp có tên clickListener sẽ giúp bạn theo dõi tên này khi nó được chuyển qua lại giữa các lớp. Lệnh gọi lại clickListener chỉ cần có night.nightId để truy cập vào dữ liệu từ cơ sở dữ liệu. Lớp SleepNightListener đã hoàn thành của bạn phải giống như mã bên dưới.
class SleepNightListener(val clickListener: (sleepId: Long) -> Unit) {
   fun onClick(night: SleepNight) = clickListener(night.nightId)
}
  1. Mở tệp list_item_sleep_night.xml.
  2. Bên trong khối data, hãy thêm một biến mới để cung cấp lớp SleepNightListener thông qua tính năng liên kết dữ liệu. Đặt name mới của <variable> thành clickListener. Đặt type thành tên đủ điều kiện của lớp com.example.android.trackmysleepquality.sleeptracker.SleepNightListener, như minh họa bên dưới. Giờ đây, bạn có thể truy cập vào hàm onClick() trong SleepNightListener từ bố cục này.
<variable
            name="clickListener"
            type="com.example.android.trackmysleepquality.sleeptracker.SleepNightListener" />
  1. Để theo dõi số lượt nhấp vào bất kỳ phần nào của mục danh sách này, hãy thêm thuộc tính android:onClick vào ConstraintLayout.

    Đặt thuộc tính thành clickListener:onClick(sleep) bằng cách sử dụng hàm lambda liên kết dữ liệu, như minh họa dưới đây:
android:onClick="@{() -> clickListener.onClick(sleep)}"

Bước 2: Chuyển trình xử lý lượt nhấp vào phần giữ chỗ xem và đối tượng liên kết

  1. Mở SleepNightAdapter.kt.
  2. Sửa đổi hàm dựng của lớp SleepNightAdapter để nhận val clickListener: SleepNightListener. Khi liên kết ViewHolder, bộ chuyển đổi cần cung cấp trình nghe lượt nhấp này.
class SleepNightAdapter(val clickListener: SleepNightListener):
       ListAdapter<SleepNight, SleepNightAdapter.ViewHolder>(SleepNightDiffCallback()) {
  1. Trong onBindViewHolder(), hãy cập nhật lệnh gọi thành holder.bind() để chuyển trình nghe lượt nhấp sang ViewHolder. Bạn sẽ gặp lỗi với trình biên dịch vì bạn đã thêm một thông số vào lệnh gọi hàm.
holder.bind(getItem(position)!!, clickListener)
  1. Thêm thông số clickListener vào bind(). Để thực hiện việc này, hãy đặt con trỏ vào lỗi và nhấn Alt+Enter (Windows) hoặc Option+Enter (Mac) trên lỗi đó, như minh họa trong ảnh chụp màn hình bên dưới.

  1. Bên trong lớp ViewHolder, bên trong hàm bind(), hãy chỉ định trình xử lý lượt nhấp cho đối tượng binding. Bạn thấy lỗi vì bạn cần cập nhật đối tượng liên kết.
binding.clickListener = clickListener
  1. Để cập nhật liên kết dữ liệu, hãy Dọn sạchTạo lại dự án của bạn. (Bạn cũng có thể cần phải vô hiệu hóa bộ nhớ đệm.) Vì vậy, bạn đã lấy một trình xử lý lượt nhấp từ hàm dựng chuyển đổi và chuyển trình xử lý đó đến chủ thể chế độ xem và chuyển đến đối tượng liên kết.

Bước 3: Hiển thị thông báo nhanh khi nhấn vào một mục

Bây giờ bạn đã có mã để nắm bắt lượt nhấp, nhưng bạn chưa triển khai điều sẽ xảy ra khi một mục trong danh sách được nhấn vào. Phản hồi đơn giản nhất là hiển thị thông báo nhanh cho biết nightId khi một mục được nhấp vào. Việc này giúp xác minh rằng khi một mục trong danh sách được nhấp vào, nightId chính xác sẽ được chụp và chuyển đi.

  1. Mở SleepTrackerFragment.kt.
  2. Trong onCreateView(), hãy tìm biến adapter. Bạn có thể thấy lỗi hiển thị lỗi vì hiện sẽ có thông số trình nghe lượt nhấp.
  3. Xác định trình xử lý lượt nhấp bằng cách chuyển hàm lambda vào SleepNightAdapter. Hàm lambda đơn giản này chỉ hiển thị một thông báo ngắn hiển thị nightId, như minh họa bên dưới. Bạn sẽ phải nhập Toast. Dưới đây là định nghĩa đầy đủ.
val adapter = SleepNightAdapter(SleepNightListener { nightId ->
   Toast.makeText(context, "${nightId}", Toast.LENGTH_LONG).show()
})
  1. Chạy ứng dụng, nhấn vào các mục và xác minh rằng các mục này hiển thị thông báo nhanh với đúng nightId. Vì các mục có giá trị nightId tăng và ứng dụng sẽ hiển thị đêm gần đây nhất trước tiên, nên mục có nightId thấp nhất sẽ nằm ở cuối danh sách.

Trong tác vụ này, bạn thay đổi hành vi khi một mục trong RecyclerView được nhấp để thay vì hiển thị thông báo ngắn, ứng dụng sẽ chuyển đến một mảnh chi tiết hiển thị thêm thông tin về đêm đã nhấp.

Bước 1: Di chuyển khi nhấp chuột

Trong bước này, thay vì chỉ hiển thị thông báo nhanh, bạn thay đổi hàm lambda lượt nhấp trong onCreateView() của SleepTrackerFragment để chuyển nightId đến SleepTrackerViewModel và kích hoạt thao tác di chuyển đến SleepDetailFragment.

Xác định chức năng của trình xử lý lượt nhấp:

  1. Mở SleepTrackerViewModel.kt.
  2. Bên trong SleepTrackerViewModel, về phía cuối, hãy xác định onSleepNightClicked()hàm xử lý lượt nhấp.
fun onSleepNightClicked(id: Long) {

}
  1. Bên trong onSleepNightClicked(), hãy kích hoạt tính năng chỉ đường bằng cách đặt _navigateToSleepDetail ở chế độ chuyển qua id trong đêm ngủ được nhấp.
fun onSleepNightClicked(id: Long) {
   _navigateToSleepDetail.value = id
}
  1. Triển khai _navigateToSleepDetail. Như bạn đã làm trước đó, hãy xác định private MutableLiveData cho trạng thái điều hướng. Và một bảng tính công khai val để sử dụng.
private val _navigateToSleepDetail = MutableLiveData<Long>()
val navigateToSleepDetail
   get() = _navigateToSleepDetail
  1. Xác định phương thức gọi sau khi ứng dụng điều hướng xong. Gọi giá trị là onSleepDetailNavigated() và đặt giá trị thành null.
fun onSleepDetailNavigated() {
    _navigateToSleepDetail.value = null
}

Thêm mã để gọi trình xử lý lượt nhấp:

  1. Mở SleepTrackerFragment.kt rồi cuộn xuống mã tạo bộ chuyển đổi và xác định SleepNightListener để hiển thị thông báo nhanh.
val adapter = SleepNightAdapter(SleepNightListener { nightId ->
   Toast.makeText(context, "${nightId}", Toast.LENGTH_LONG).show()
})
  1. Thêm mã sau vào bên dưới thông báo nhanh để gọi trình xử lý lượt nhấp, onSleepNighClicked(), trong sleepTrackerViewModel khi nhấn vào một mục. Chuyển vào nightId để mô hình chế độ xem biết đêm nào cần ngủ. Việc này khiến bạn gặp lỗi, vì bạn chưa xác định onSleepNightClicked(). Bạn có thể giữ lại, bình luận hoặc xóa thông báo nhanh như bạn muốn.
sleepTrackerViewModel.onSleepNightClicked(nightId)

Thêm mã để quan sát các lần nhấp:

  1. Mở SleepTrackerFragment.kt.
  2. Trong onCreateView(), ngay phía trên phần khai báo manager, hãy thêm mã để quan sát navigateToSleepDetail LiveData mới. Khi navigateToSleepDetail thay đổi, hãy chuyển đến SleepDetailFragment, chuyển vào night, sau đó gọi onSleepDetailNavigated(). Vì bạn đã thực hiện việc này trước đó trong lớp học lập trình trước, nên mã sau đây:
sleepTrackerViewModel.navigateToSleepDetail.observe(this, Observer { night ->
            night?.let {
              this.findNavController().navigate(
                        SleepTrackerFragmentDirections
                                .actionSleepTrackerFragmentToSleepDetailFragment(night))
               sleepTrackerViewModel.onSleepDetailNavigated()
            }
        })
  1. Chạy mã của bạn, nhấp vào một mục và ... ứng dụng đó gặp sự cố.

Xử lý các giá trị rỗng trong bộ chuyển đổi liên kết:

  1. Chạy lại ứng dụng ở chế độ gỡ lỗi. Nhấn vào một mục và lọc các nhật ký để hiển thị lỗi. Báo cáo này sẽ hiển thị dấu vết ngăn xếp, chẳng hạn như nội dung bên dưới.
Caused by: java.lang.IllegalArgumentException: Parameter specified as non-null is null: method kotlin.jvm.internal.Intrinsics.checkParameterIsNotNull, parameter item

Rất tiếc, dấu vết ngăn xếp không cho biết rõ lỗi này được kích hoạt ở đâu. Một ưu điểm của việc liên kết dữ liệu là có thể gây khó khăn cho việc gỡ lỗi mã. Ứng dụng gặp sự cố khi bạn nhấp vào một mục và mã mới duy nhất dùng để xử lý lượt nhấp đó.

Tuy nhiên, hóa ra rằng với cơ chế xử lý lượt nhấp mới này, giờ đây, các bộ chuyển đổi liên kết có thể được gọi bằng giá trị null cho item. Cụ thể là khi ứng dụng khởi động, LiveData sẽ bắt đầu bằng null, vì vậy, bạn cần thêm giá trị null kiểm tra vào mỗi bộ chuyển đổi.

  1. Trong BindingUtils.kt, đối với mỗi bộ chuyển đổi liên kết, hãy thay đổi loại của đối số item thành có thể có giá trị null và bao quanh phần nội dung bằng item?.let{...}. Ví dụ: bộ chuyển đổi của bạn cho sleepQualityString sẽ có dạng như sau. Tương tự, cũng thay đổi bộ chuyển đổi khác.
@BindingAdapter("sleepQualityString")
fun TextView.setSleepQualityString(item: SleepNight?) {
   item?.let {
       text = convertNumericQualityToString(item.sleepQuality, context.resources)
   }
}
  1. Chạy ứng dụng của bạn. Nhấn vào một mục và chế độ xem chi tiết sẽ mở ra.

Dự án Android Studio: RecyclerViewClickHandler.

Để giúp các mục trong RecyclerView phản hồi các lượt nhấp, hãy đính kèm trình xử lý lượt nhấp để liệt kê các mục trong ViewHolder và xử lý các lượt nhấp trong ViewModel.

Để mục trong RecyclerView phản hồi các lượt nhấp, bạn cần làm như sau:

  • Tạo một lớp trình xử lý nhận hàm lambda và chỉ định lớp đó cho hàm onClick().
class SleepNightListener(val clickListener: (sleepId: Long) -> Unit) {
   fun onClick(night: SleepNight) = clickListener(night.nightId)
}
  • Đặt trình xử lý lượt nhấp trên chế độ xem.
android:onClick="@{() -> clickListener.onClick(sleep)}"
  • Chuyển trình xử lý lượt nhấp vào hàm dựng bộ chuyển đổi, vào trình xem chế độ xem, rồi thêm nó vào đối tượng liên kết.
class SleepNightAdapter(val clickListener: SleepNightListener):
       ListAdapter<DataItem, RecyclerView.ViewHolder>(SleepNightDiffCallback()
holder.bind(getItem(position)!!, clickListener)
binding.clickListener = clickListener
  • Trong mảnh hiển thị chế độ xem tuần hoàn, nơi bạn tạo bộ chuyển đổi, hãy xác định trình xử lý lượt nhấp bằng cách chuyển hàm lambda cho bộ chuyển đổi.
val adapter = SleepNightAdapter(SleepNightListener { nightId ->
      sleepTrackerViewModel.onSleepNightClicked(nightId)
})
  • Triển khai trình xử lý lượt nhấp trong mô hình chế độ xem. Đối với các lượt nhấp vào mục trong danh sách, thao tác này thường kích hoạt thao tác di chuyển đến một đoạn chi tiết.

Khóa học từ Udacity:

Tài liệu dành cho nhà phát triển Android:

Phần này liệt kê các bài tập về nhà có thể được giao cho học viên đang làm việc qua lớp học lập trình này trong khóa học do người hướng dẫn tổ chức. Người hướng dẫn có thể làm những việc sau:

  • Giao bài tập về nhà nếu được yêu cầu.
  • Trao đổi với học viên cách nộp bài tập về nhà.
  • Chấm điểm bài tập về nhà.

Người hướng dẫn có thể sử dụng những đề xuất này ít hay nhiều tùy ý. Do đó, họ có thể thoải mái giao bất kỳ bài tập về nhà nào khác mà họ cảm thấy phù hợp.

Nếu bạn đang tự mình làm việc qua lớp học lập trình này, hãy thoải mái sử dụng các bài tập về nhà này để kiểm tra kiến thức của bạn.

Trả lời những câu hỏi này

Câu hỏi 1

Giả sử ứng dụng của bạn chứa RecyclerView hiển thị các mặt hàng trong danh sách mua sắm. Ứng dụng của bạn cũng xác định một lớp danh sách nhấp chuột:

class ShoppingListItemListener(val clickListener: (itemId: Long) -> Unit) {
    fun onClick(cartItem: CartItem) = clickListener(cartItem.itemId)
}

Làm cách nào để ShoppingListItemListener có thể liên kết dữ liệu? Hãy chọn một vấn đề.

▢ Trong tệp bố cục chứa RecyclerView hiển thị danh sách mua sắm, hãy thêm biến <data> cho ShoppingListItemListener.

▢ Trong tệp bố cục xác định bố cục của một hàng trong danh sách mua sắm, hãy thêm biến <data> cho ShoppingListItemListener.

▢Trong lớp ShoppingListItemListener, hãy thêm một hàm để bật liên kết dữ liệu:

fun onBinding (cartItem: CartItem) {dataBindingEnable(true)}

▢Trong lớp ShoppingListItemListener, bên trong hàm onClick(), hãy thêm một lệnh gọi để bật liên kết dữ liệu:

fun onClick(cartItem: CartItem) = { 
    clickListener(cartItem.itemId)
    dataBindingEnable(true)
}

Câu hỏi 2

Bạn thêm thuộc tính android:onClick ở đâu để các mục trong RecyclerView phản hồi với lượt nhấp? Hãy chọn mọi câu phù hợp.

▢ Trong tệp bố cục hiển thị RecyclerView, hãy thêm tệp đó vào <androidx.recyclerview.widget.RecyclerView>

▢ Thêm nội dung này vào tệp bố cục cho một mục trong hàng. Nếu bạn muốn toàn bộ mục có thể nhấp vào được, hãy thêm mục đó vào chế độ xem gốc chứa các mục trong hàng.

▢ Thêm nội dung này vào tệp bố cục cho một mục trong hàng. Nếu bạn muốn nhấp được một TextView trong mục, hãy thêm vào <TextView>.

▢ Luôn thêm tệp bố cục cho MainActivity.

Bắt đầu bài học tiếp theo: 7.5: Tiêu đề trong RecyclerView