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
Trong lớp học lập trình này, bạn sẽ tìm hiểu cách thêm tiêu đề kéo dài theo chiều rộng của danh sách hiển thị trong RecyclerView
. Bạn tạo ứng dụng theo dõi giấc ngủ từ các lớp học lập trình trước đó.
Kiến thức bạn cần có
- Cách 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.
- Cách di chuyển giữa các mảnh và cách 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 DAO và xác định các thực thể. - Cách sử dụng coroutine để tương tác với 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ụcAdapter
,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
. - Cách ghi lại và xử lý các lượt nhấp vào mục trong
RecyclerView.
Kiến thức bạn sẽ học được
- Cách sử dụng nhiều
ViewHolder
vớiRecyclerView
để thêm mục có bố cục khác. Cụ thể là cách sử dụngViewHolder
thứ hai để thêm tiêu đề phía trên các mục hiển thị trongRecyclerView
.
Bạn sẽ thực hiện
- Xây dựng dựa trên ứ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 tiêu đề kéo dài theo chiều rộng của màn hình phía trên các đêm ngủ được hiển thị trong
RecyclerView
.
Ứng dụng theo dõi giấc ngủ mà bạn bắt đầu có 3 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ị ở giữa, cho thấy một điểm xếp hạng chất lượng giấc ngủ. Màn hình thứ ba là chế độ xem chi tiết sẽ mở ra khi người dùng nhấn vào một mục trong lưới.
Ứ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 một tiêu đề vào lưới của các mục hiển thị. Màn hình chính cuối cùng sẽ như sau:
Lớp học mã này hướng dẫn nguyên tắc chung về việc đưa các mục sử dụng bố cục khác nhau vào RecyclerView
. Một ví dụ phổ biến là có tiêu đề trong danh sách hoặc lưới của bạn. Danh sách có thể có một tiêu đề để mô tả nội dung mục. Một danh sách cũng có thể có nhiều tiêu đề để nhóm và tách các mục trong một danh sách.
RecyclerView
không biết gì về dữ liệu của bạn hoặc loại bố cục của từng mục. LayoutManager
sắp xếp các mục trên màn hình, nhưng bộ chuyển đổi điều chỉnh dữ liệu sẽ hiển thị và chuyển các lớp lưu giữ chế độ xem đến RecyclerView
. Vì vậy, bạn sẽ thêm mã để tạo tiêu đề trong bộ chuyển đổi.
Hai cách thêm tiêu đề
Trong RecyclerView
, mỗi mục trong danh sách tương ứng với một số chỉ mục bắt đầu từ 0. Ví dụ:
[Dữ liệu thực tế] –> [Lượt xem bộ chuyển đổi]
[0: Sleepnight] -> [0: SleepNight]
[1: SleepNight] -> [1: SleepNight]
[2: Sleepnight] -> [2: SleepNight]
Một cách để thêm tiêu đề vào danh sách là sửa đổi bộ chuyển đổi để sử dụng ViewHolder
khác bằng cách kiểm tra chỉ mục nơi tiêu đề cần hiển thị. Adapter
sẽ chịu trách nhiệm theo dõi tiêu đề. Ví dụ: để hiển thị tiêu đề ở đầu bảng, bạn cần phải trả về ViewHolder
khác cho tiêu đề trong khi bố trí mục không được lập chỉ mục. Sau đó, tất cả các mục khác sẽ được liên kết với phần bù tiêu đề, như minh họa bên dưới.
[Dữ liệu thực tế] –> [Lượt xem bộ chuyển đổi]
[0: Tiêu đề]
[0: SleepNight] -> [1: Sleepnight]
[1: SleepNight] -> [2: SleepNight]
[2: SleepNight] -> [3: SleepNight.{/1}
Một cách khác để thêm tiêu đề là sửa đổi tập dữ liệu sao lưu cho lưới dữ liệu của bạn. Vì tất cả dữ liệu cần được hiển thị đều được lưu trữ trong danh sách, bạn có thể sửa đổi danh sách để bao gồm các mục đại diện cho một tiêu đề. Điều này hơi đơn giản hơn một chút, nhưng bạn phải suy nghĩ về cách bạn thiết kế đối tượng để có thể kết hợp nhiều loại mục vào một danh sách duy nhất. Khi được triển khai theo cách này, bộ chuyển đổi sẽ hiển thị các mục được chuyển đến. Vì vậy, mục ở vị trí 0 là tiêu đề và mục ở vị trí 1 là một SleepNight
, ánh xạ trực tiếp đến nội dung trên màn hình.
[Dữ liệu thực tế] –> [Lượt xem bộ chuyển đổi]
[0: Tiêu đề] -> [0: Tiêu đề]
[1: SleepNight] -> [1: SleepNight]
[2: Sleepnight] -> [2: SleepNight]
[3: SleepNight] -> [3: SleepNight]
Mỗi phương pháp đều có lợi ích và hạn chế. Việc thay đổi tập dữ liệu không ảnh hưởng nhiều đến phần còn lại của mã bộ chuyển đổi và bạn có thể thêm logic tiêu đề bằng cách thao tác danh sách dữ liệu. Ngược lại, bằng cách sử dụng một ViewHolder
khác bằng cách kiểm tra chỉ mục cho các tiêu đề, bạn có thể linh hoạt hơn khi bố cục tiêu đề. Bộ chuyển đổi cũng cho phép bộ chuyển đổi xử lý cách điều chỉnh dữ liệu cho phù hợp với chế độ xem mà không cần sửa đổi dữ liệu sao lưu.
Trong lớp học lập trình này, bạn cập nhật RecyclerView
để hiển thị tiêu đề ở đầu danh sách. Trong trường hợp này, ứng dụng sẽ dùng một ViewHolder
cho tiêu đề khác với mục dữ liệu. Ứng dụng sẽ kiểm tra chỉ mục của danh sách để xác định ViewHolder
nên sử dụng.
Bước 1: Tạo một lớp DataItem
Để trừu tượng hóa loại mục và cho phép bộ chuyển đổi chỉ xử lý "items", bạn có thể tạo một lớp lưu giữ dữ liệu đại diện cho một SleepNight
hoặc một Header
. Tập dữ liệu của bạn sẽ là một danh sách các mục chứa dữ liệu.
Bạn có thể tải ứng dụng dành cho người mới bắt đầu từ GitHub hoặc tiếp tục sử dụng ứng dụng SleepTracker mà bạn đã xây dựng trong lớp học lập trình trước đó.
- Tải mã RecyclerViewHeaders-Starter xuống từ GitHub. Thư mục RecyclerViewHeaders-Starter chứa phiên bản dành cho người mới bắt đầu của ứng dụng SleepTracker trong lớp học lập trình này. Bạn cũng có thể tiếp tục dùng ứng dụng đã hoàn tất trong lớp học lập trình trước đó nếu muốn.
- Mở SleepnightAdapter.kt.
- Bên dưới lớp
SleepNightListener
, ở cấp cao nhất, hãy xác định lớpsealed
có tên làDataItem
đại diện cho một mục dữ liệu.
Lớpsealed
xác định một loại đã đóng, nghĩa là tất cả các lớp con củaDataItem
phải được xác định trong tệp này. Kết quả là trình biên dịch biết số lớp con. Phần khác của mã không thể xác định một loạiDataItem
mới có thể làm hỏng bộ chuyển đổi.
sealed class DataItem {
}
- Bên trong phần nội dung của lớp
DataItem
, hãy xác định hai lớp đại diện cho các loại mục dữ liệu. Đầu tiên làSleepNightItem
, là một trình bao bọc xung quanhSleepNight
, vì vậy, giá trị này chỉ có một giá trị có tên làsleepNight
. Để lớp này thuộc lớp bị đóng, hãy yêu cầu mở rộngDataItem
.
data class SleepNightItem(val sleepNight: SleepNight): DataItem()
- Lớp thứ hai là
Header
, để đại diện cho tiêu đề. Vì một tiêu đề không có dữ liệu thực tế nên bạn có thể khai báo tiêu đề đó làobject
. Điều đó có nghĩa là sẽ chỉ có một phiên bản củaHeader
. Xin nhắc lại, yêu cầu mở rộngDataItem
.
object Header: DataItem()
- Bên trong
DataItem
, ở cấp lớp, hãy xác định thuộc tínhabstract
Long
có tênid
. Khi bộ chuyển đổi dùngDiffUtil
để xác định xem một mặt hàng có thay đổi hay không vàDiffItemCallback
cần biết mã của từng mặt hàng. Bạn sẽ thấy lỗi doSleepNightItem
vàHeader
cần ghi đè thuộc tính trừu tượngid
.
abstract val id: Long
- Trong
SleepNightItem
, hãy ghi đèid
để trả vềnightId
.
override val id = sleepNight.nightId
- Trong
Header
, hãy ghi đèid
để trả vềLong.MIN_VALUE
, đây là một số rất nhỏ (tức là -2 lũy thừa 63). Vì vậy, điều này sẽ không bao giờ xung đột với bất kỳnightId
nào đang tồn tại.
override val id = Long.MIN_VALUE
- Mã hoàn tất của bạn sẽ trông như thế này và ứng dụng của bạn phải xây dựng mà không có lỗi.
sealed class DataItem {
abstract val id: Long
data class SleepNightItem(val sleepNight: SleepNight): DataItem() {
override val id = sleepNight.nightId
}
object Header: DataItem() {
override val id = Long.MIN_VALUE
}
}
Bước 2: Tạo ViewHolder cho Tiêu đề
- Tạo bố cục cho tiêu đề trong tệp tài nguyên bố cục mới có tên header.xml hiển thị
TextView
. Không có gì thú vị trong mã này, vì vậy, đây là mã.
<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/text"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textAppearance="?android:attr/textAppearanceLarge"
android:text="Sleep Results"
android:padding="8dp" />
- Trích xuất
"Sleep Results"
thành một tài nguyên chuỗi và gọi nó làheader_text
.
<string name="header_text">Sleep Results</string>
- Trong tệp SleepNightAdapter.kt, bên trong
SleepNightAdapter
, phía trên lớpViewHolder
, hãy tạo một lớpTextViewHolder
mới. Lớp này tăng cường bố cục textview.xml và trả về một thực thểTextViewHolder
. Vì bạn đã làm việc này trước đây, nên đây là mã và bạn sẽ phải nhậpView
vàR
:
class TextViewHolder(view: View): RecyclerView.ViewHolder(view) {
companion object {
fun from(parent: ViewGroup): TextViewHolder {
val layoutInflater = LayoutInflater.from(parent.context)
val view = layoutInflater.inflate(R.layout.header, parent, false)
return TextViewHolder(view)
}
}
}
Bước 3: Cập nhật SleepNightAdapter
Tiếp theo, bạn cần cập nhật nội dung khai báo của SleepNightAdapter
. Thay vì chỉ hỗ trợ một loại ViewHolder
, bạn cần sử dụng được bất kỳ loại chế độ xem nào.
Xác định loại mục
- Trong
SleepNightAdapter.kt
, ở cấp cao nhất, dưới câu lệnhimport
và trênSleepNightAdapter
, hãy xác định hai hằng số cho loại chế độ xem.RecyclerView
sẽ cần phân biệt loại chế độ xem của từng mục để có thể chỉ định chính xác giá trị cho chế độ xem.
private val ITEM_VIEW_TYPE_HEADER = 0
private val ITEM_VIEW_TYPE_ITEM = 1
- Bên trong
SleepNightAdapter
, hãy tạo một hàm để ghi đègetItemViewType()
để trả về tiêu đề hoặc hằng số mục chính xác, tùy thuộc vào loại mục hiện tại.
override fun getItemViewType(position: Int): Int {
return when (getItem(position)) {
is DataItem.Header -> ITEM_VIEW_TYPE_HEADER
is DataItem.SleepNightItem -> ITEM_VIEW_TYPE_ITEM
}
}
Cập nhật định nghĩa SleepnightAdapter
- Trong định nghĩa của
SleepNightAdapter
, hãy cập nhật đối số đầu tiên choListAdapter
từSleepNight
thànhDataItem
. - Trong định nghĩa của
SleepNightAdapter
, hãy thay đổi đối số chung thứ hai choListAdapter
từSleepNightAdapter.ViewHolder
thànhRecyclerView.ViewHolder
. Bạn sẽ thấy một số lỗi về các nội dung cập nhật cần thiết và tiêu đề của lớp sẽ có dạng như dưới đây.
class SleepNightAdapter(val clickListener: SleepNightListener):
ListAdapter<DataItem, RecyclerView.ViewHolder>(SleepNightDiffCallback()) {
Cập nhật onCreateViewHolder()
- Thay đổi chữ ký của
onCreateViewHolder()
để trả vềRecyclerView.ViewHolder
.
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): RecyclerView.ViewHolder
- Mở rộng phương thức triển khai phương thức
onCreateViewHolder()
để thử nghiệm và trả về trình giữ chế độ xem thích hợp cho từng loại mục. Phương thức cập nhật của bạn sẽ trông giống như mã bên dưới.
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): RecyclerView.ViewHolder {
return when (viewType) {
ITEM_VIEW_TYPE_HEADER -> TextViewHolder.from(parent)
ITEM_VIEW_TYPE_ITEM -> ViewHolder.from(parent)
else -> throw ClassCastException("Unknown viewType ${viewType}")
}
}
Cập nhật onBindViewHolder()
- Thay đổi loại thông số của
onBindViewHolder()
từViewHolder
thànhRecyclerView.ViewHolder
.
override fun onBindViewHolder(holder: RecyclerView.ViewHolder, position: Int)
- Thêm một điều kiện để chỉ chỉ định dữ liệu cho chủ sở hữu chế độ xem nếu chủ sở hữu là
ViewHolder
.
when (holder) {
is ViewHolder -> {...}
- Truyền loại đối tượng do
getItem()
trả về choDataItem.SleepNightItem
. HàmonBindViewHolder()
đã hoàn thành của bạn phải có dạng như thế này.
override fun onBindViewHolder(holder: RecyclerView.ViewHolder, position: Int) {
when (holder) {
is ViewHolder -> {
val nightItem = getItem(position) as DataItem.SleepNightItem
holder.bind(nightItem.sleepNight, clickListener)
}
}
}
Cập nhật các lệnh gọi lại diffUtil
- Thay đổi các phương thức trong
SleepNightDiffCallback
để sử dụng lớpDataItem
mới thay vìSleepNight
. Chặn cảnh báo lỗi như trong mã bên dưới.
class SleepNightDiffCallback : DiffUtil.ItemCallback<DataItem>() {
override fun areItemsTheSame(oldItem: DataItem, newItem: DataItem): Boolean {
return oldItem.id == newItem.id
}
@SuppressLint("DiffUtilEquals")
override fun areContentsTheSame(oldItem: DataItem, newItem: DataItem): Boolean {
return oldItem == newItem
}
}
Thêm và gửi tiêu đề
- Bên trong
SleepNightAdapter
, bên dướionCreateViewHolder()
, hãy xác định hàmaddHeaderAndSubmitList()
như bên dưới. Hàm này lấy danh sáchSleepNight
. Thay vì dùngsubmitList()
doListAdapter
cung cấp, để gửi danh sách của bạn, bạn phải dùng hàm này để thêm tiêu đề rồi gửi danh sách.
fun addHeaderAndSubmitList(list: List<SleepNight>?) {}
- Bên trong
addHeaderAndSubmitList()
, nếu danh sách được chuyển lànull
, hãy chỉ trả về tiêu đề, nếu không, hãy đính kèm tiêu đề vào đầu danh sách, sau đó gửi danh sách.
val items = when (list) {
null -> listOf(DataItem.Header)
else -> listOf(DataItem.Header) + list.map { DataItem.SleepNightItem(it) }
}
submitList(items)
- Mở SleepTrackerFragment.kt rồi thay đổi lệnh gọi thành
submitList()
thànhaddHeaderAndSubmitList()
.
- Chạy ứng dụng của bạn và quan sát cách tiêu đề hiển thị dưới dạng mục đầu tiên trong danh sách các mục ngủ.
Có hai vấn đề cần được khắc phục cho ứng dụng này. Một điều có thể hiển thị và một nội dung thì không.
- Tiêu đề sẽ hiển thị ở góc trên cùng bên trái và không dễ phân biệt.
- Thao tác này không ảnh hưởng nhiều đến danh sách ngắn có một tiêu đề, nhưng bạn không nên thao tác với danh sách trong
addHeaderAndSubmitList()
trên chuỗi giao diện người dùng. Hãy tưởng tượng danh sách với hàng trăm mục, nhiều tiêu đề và logic để quyết định vị trí cần chèn mục. Tác vụ này thuộc về một coroutine.
Thay đổi addHeaderAndSubmitList()
để sử dụng coroutine:
- Ở cấp cao nhất trong lớp
SleepNightAdapter
, hãy xác định mộtCoroutineScope
bằngDispatchers.Default
.
private val adapterScope = CoroutineScope(Dispatchers.Default)
- Trong
addHeaderAndSubmitList()
, hãy chạy coroutine trongadapterScope
để thao tác với danh sách. Sau đó, chuyển sang ngữ cảnhDispatchers.Main
để gửi danh sách như trong mã bên dưới.
fun addHeaderAndSubmitList(list: List<SleepNight>?) {
adapterScope.launch {
val items = when (list) {
null -> listOf(DataItem.Header)
else -> listOf(DataItem.Header) + list.map { DataItem.SleepNightItem(it) }
}
withContext(Dispatchers.Main) {
submitList(items)
}
}
}
- Mã của bạn phải tạo và chạy và bạn sẽ không thấy bất kỳ sự khác biệt nào.
Hiện tại, tiêu đề có cùng chiều rộng với các mục khác trên lưới, chiếm một chiều ngang và dọc. Toàn bộ lưới vừa với 3 mục có chiều rộng một khoảng theo chiều ngang, vì vậy, tiêu đề phải sử dụng 3 khoảng ngang.
Để sửa chiều rộng tiêu đề, bạn cần phải cho GridLayoutManager
biết thời điểm cần mở rộng dữ liệu trên tất cả các cột. Bạn có thể thực hiện việc này bằng cách thiết lập SpanSizeLookup
trên GridLayoutManager
. Đây là một đối tượng cấu hình mà GridLayoutManager
sử dụng để xác định số lượng khoảng thời gian để dùng cho từng mục trong danh sách.
- Mở SleepTrackerFragment.kt.
- Tìm mã mà bạn xác định
manager
, ở cuốionCreateView()
.
val manager = GridLayoutManager(activity, 3)
- Bên dưới
manager
, hãy xác địnhmanager.spanSizeLookup
(như minh họa). Bạn cần tạoobject
vìsetSpanSizeLookup
không lấy hàm lambda. Để tạoobject
trong Kotlin, hãy nhậpobject : classname
, trong trường hợp này làGridLayoutManager.SpanSizeLookup
.
manager.spanSizeLookup = object : GridLayoutManager.SpanSizeLookup() {
}
- Bạn có thể gặp lỗi với trình biên dịch để gọi hàm dựng. Nếu bạn làm như vậy, hãy mở trình đơn ý định bằng
Option+Enter
(Mac) hoặcAlt+Enter
(Windows) để áp dụng lệnh gọi hàm dựng.
- Sau đó, bạn sẽ gặp lỗi trên
object
cho biết bạn cần phải ghi đè các phương thức. Đặt con trỏ trênobject
, nhấnOption+Enter
(Mac) hoặcAlt+Enter
(Windows) để mở trình đơn ý định, sau đó ghi đè phương thứcgetSpanSize()
.
- Trong phần nội dung của
getSpanSize()
, hãy trả về kích thước khoảng bên phải cho mỗi vị trí. Vị trí 0 có kích thước khoảng là 3 và các vị trí khác có kích thước khoảng là 1. Mã hoàn tất sẽ có dạng như mã bên dưới:
manager.spanSizeLookup = object : GridLayoutManager.SpanSizeLookup() {
override fun getSpanSize(position: Int) = when (position) {
0 -> 3
else -> 1
}
}
- Để cải thiện giao diện tiêu đề của bạn, hãy mở header.xml và thêm mã này vào tệp bố cục header.xml.
android:textColor="@color/white_text_color"
android:layout_marginStart="16dp"
android:layout_marginTop="16dp"
android:layout_marginEnd="16dp"
android:background="@color/colorAccent"
- Chạy ứng dụng của bạn. Ứng dụng phải giống như ảnh chụp màn hình dưới đây.
Xin chúc mừng! Bạn đã hoàn tất.
Dự án Android Studio: RecyclerViewHeaders
- Tiêu đề thường là một mục kéo dài chiều rộng của một danh sách và có vai trò là tiêu đề hoặc dấu phân tách. Một danh sách có thể có một tiêu đề để mô tả nội dung mục hoặc nhiều tiêu đề để nhóm các mục và tách các mục khỏi nhau.
RecyclerView
có thể sử dụng nhiều chủ sở hữu chế độ xem để đáp ứng nhóm các mục không đồng nhất; ví dụ: tiêu đề và mục danh sách.- Một cách để thêm tiêu đề là sửa đổi bộ chuyển đổi để sử dụng
ViewHolder
khác bằng cách kiểm tra các chỉ mục mà tiêu đề cần hiển thị.Adapter
chịu trách nhiệm theo dõi tiêu đề. - Một cách khác để thêm tiêu đề là sửa đổi tập dữ liệu sao lưu (danh sách) cho lưới dữ liệu của bạn, đó là những gì bạn đã làm trong lớp học lập trình này.
Sau đây là các bước chính để thêm tiêu đề:
- Trừu tượng dữ liệu trong danh sách của bạn bằng cách tạo
DataItem
có thể chứa tiêu đề hoặc dữ liệu. - Tạo một chế độ xem có bố cục cho tiêu đề trong bộ chuyển đổi.
- Cập nhật bộ chuyển đổi và phương thức để sử dụng bất kỳ loại
RecyclerView.ViewHolder
nào. - Trong
onCreateViewHolder()
, hãy trả về đúng loại giá trị xem cho mục dữ liệu. - Hãy cập nhật
SleepNightDiffCallback
để làm việc với lớpDataItem
. - Tạo một hàm
addHeaderAndSubmitList()
sử dụng coroutine để thêm tiêu đề vào tập dữ liệu rồi gọisubmitList()
. - Triển khai
GridLayoutManager.SpanSizeLookup()
để chỉ làm cho tiêu đề rộng ba nhịp.
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
Câu nào sau đây đúng về ViewHolder
?
▢ Một bộ chuyển đổi có thể sử dụng nhiều lớp ViewHolder
để lưu giữ tiêu đề và nhiều loại dữ liệu.
▢ Bạn có thể có duy nhất một trình xem chế độ xem cho dữ liệu và một máy chủ xem cho tiêu đề.
▢ RecyclerView
có hỗ trợ nhiều loại tiêu đề, nhưng dữ liệu phải thống nhất.
▢ Khi thêm tiêu đề, bạn sẽ phân lớp con RecyclerView
để chèn tiêu đề vào đúng vị trí.
Câu hỏi 2
Khi nào bạn nên sử dụng coroutine với RecyclerView
? Chọn tất cả câu đúng.
▢ Không bao giờ. RecyclerView
là một phần tử giao diện người dùng và không được sử dụng coroutine.
▢ Sử dụng coroutine cho các tác vụ chạy trong thời gian dài có thể làm chậm giao diện người dùng.
▢ Các thao tác với danh sách có thể mất nhiều thời gian và bạn luôn phải thực hiện các thao tác đó bằng coroutine.
▢ Sử dụng coroutine với các hàm tạm ngưng để tránh chặn chuỗi chính.
Câu hỏi 3
Bạn KHÔNG phải làm những việc nào sau đây khi sử dụng nhiều ViewHolder
?
▢ Trong ViewHolder
, hãy cung cấp nhiều tệp bố cục để tăng cường nếu cần.
▢ Trong onCreateViewHolder()
, hãy trả về đúng loại chủ sở hữu chế độ xem cho mục dữ liệu.
▢ Trong onBindViewHolder()
, chỉ liên kết dữ liệu nếu chủ sở hữu chế độ xem là loại chủ sở hữu chế độ xem chính xác cho mục dữ liệu.
▢ Giới thiệu chung về chữ ký của lớp bộ chuyển đổi để chấp nhận bất kỳ RecyclerView.ViewHolder
nào.
Bắt đầu bài học tiếp theo:
Để biết đường liên kết đến các lớp học lập trình khác trong khóa học này, hãy xem trang đích của các lớp học lập trình cơ bản về Android Kotlin.