Android Academy · บทเรียน

เหตุการณ์คลิกใน RecyclerView

จัดการการคลิกและการกดค้างที่รายการใน RecyclerView ส่งตัวรับฟังการคลิกไปยังอะแดปเตอร์ และนำทางไปยังหน้ารายละเอียดเมื่อแตะรายการ

บทเรียน 3 จาก 611 ขั้นตอน

เหตุการณ์คลิกใน RecyclerView เป็นบทเรียน Android Academy ฟรีบน CoddyKit นี่คือบทเรียนที่ 3 จากทั้งหมด 6 บทเรียน คุณสามารถอ่านบทเรียนทั้งหมดด้านล่างฟรี — จากนั้นลองปฏิบัติด้วยตัวคุณเองในเบราว์เซอร์พร้อมตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7 บทเรียนนี้เป็นส่วนหนึ่งของเส้นทางการเรียน Android Academy และความก้าวหน้าของคุณจะซิงค์ข้ามเว็บและแอป CoddyKit คอร์ส Android Academy มีบทเรียนทั้งหมด 6 บทเรียน

การทำให้สมาชิกในรายการแตะได้

RecyclerView ไม่มีตัวรับฟังการคลิกในตัวเหมือนที่ ListView เคยมี คุณต้องเพิ่มตัวรับฟังการคลิกภายใน Adapter

รูปแบบที่แนะนำคือ ส่งแลมบ์ดา (ฟังก์ชันเรียกกลับ) ไปยังตัวสร้างของ Adapter เมื่อแตะสมาชิก Adapter จะเรียกแลมบ์ดาพร้อมสมาชิกที่เลือก แล้ว Activity จะจัดการขั้นตอนถัดไป

Adapter พร้อมการเรียกกลับเมื่อคลิก

เพิ่มพารามิเตอร์แลมบ์ดา onItemClick ให้กับ Adapter:

class FruitAdapter(
    private val fruits: List<Fruit>,
    private val onItemClick: (Fruit) -> Unit
) : RecyclerView.Adapter<FruitAdapter.ViewHolder>() {

    class ViewHolder(view: View) : RecyclerView.ViewHolder(view) {
        val tvName: TextView = view.findViewById(R.id.tvName)
        val tvCalories: TextView = view.findViewById(R.id.tvCalories)
    }

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
        val view = LayoutInflater.from(parent.context)
            .inflate(R.layout.item_fruit, parent, false)
        return ViewHolder(view)
    }

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        val fruit = fruits[position]
        holder.tvName.text = fruit.name
        holder.tvCalories.text = "${fruit.calories} kcal"
        // Set click listener on the whole item
        holder.itemView.setOnClickListener {
            onItemClick(fruit)
        }
    }

    override fun getItemCount() = fruits.size
}

การจัดการการคลิกใน Activity

ใน Activity ให้ส่งแลมบ์ดาที่นำทางไปยังหน้าจอรายละเอียด:

val adapter = FruitAdapter(fruits) { fruit ->
    // Called when user taps a fruit
    val intent = Intent(this, FruitDetailActivity::class.java)
    intent.putExtra("FRUIT_NAME", fruit.name)
    intent.putExtra("FRUIT_CALORIES", fruit.calories)
    startActivity(intent)
}

binding.recyclerView.apply {
    this.adapter = adapter
    layoutManager = LinearLayoutManager(this@MainActivity)
}

การรับข้อมูลในหน้าจอรายละเอียด

อ่านข้อมูลเพิ่มเติมใน Activity รายละเอียด:

class FruitDetailActivity : AppCompatActivity() {

    private lateinit var binding: ActivityFruitDetailBinding

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        binding = ActivityFruitDetailBinding.inflate(layoutInflater)
        setContentView(binding.root)

        val name = intent.getStringExtra("FRUIT_NAME") ?: "Unknown"
        val calories = intent.getIntExtra("FRUIT_CALORIES", 0)

        binding.tvDetailName.text = name
        binding.tvDetailCalories.text = "$calories kcal"
    }
}

DiffUtil สำหรับการอัปเดตอย่างมีประสิทธิภาพ

เมื่อข้อมูลรายการเปลี่ยนแปลง อย่าเรียก notifyDataSetChanged() เพราะจะวาดทุกอย่างใหม่ ให้ใช้ DiffUtil แทน:

  • คำนวณความแตกต่างขั้นต่ำระหว่างรายการเก่าและใหม่
  • ทำภาพเคลื่อนไหวเฉพาะสมาชิกที่เปลี่ยนแปลง
  • ประสิทธิภาพและประสบการณ์ผู้ใช้ดีขึ้น

วิธีสมัยใหม่คือใช้ ListAdapter ซึ่งใช้ DiffUtil โดยอัตโนมัติ

ListAdapter พร้อม DiffUtil

สืบทอดจาก ListAdapter เพื่ออัปเดตรายการโดยอัตโนมัติพร้อมภาพเคลื่อนไหว:

class FruitAdapter(
    private val onItemClick: (Fruit) -> Unit
) : ListAdapter<Fruit, FruitAdapter.ViewHolder>(DIFF_CALLBACK) {

    companion object {
        val DIFF_CALLBACK = object : DiffUtil.ItemCallback<Fruit>() {
            override fun areItemsTheSame(old: Fruit, new: Fruit) =
                old.name == new.name
            override fun areContentsTheSame(old: Fruit, new: Fruit) =
                old == new  // data class equals()
        }
    }

    // ... ViewHolder and onCreateViewHolder same as before ...

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        val fruit = getItem(position)  // use getItem(), not fruits[position]
        holder.tvName.text = fruit.name
        holder.itemView.setOnClickListener { onItemClick(fruit) }
    }
}

การส่งรายการใหม่

เมื่อใช้ ListAdapter ให้อัปเดตรายการด้วยการเรียก submitList() โดย DiffUtil จะจัดการภาพเคลื่อนไหวให้อัตโนมัติ:

// In Activity:
val adapter = FruitAdapter { fruit ->
    // handle click
}
binding.recyclerView.adapter = adapter

// Initial data
adapter.submitList(fruits)

// Later, update with new data (e.g. after filtering):
val filtered = fruits.filter { it.calories < 100 }
adapter.submitList(filtered)  // DiffUtil animates the change

การกดค้างและเมนูตามบริบท

คุณยังสามารถตอบสนองต่อการกดค้างได้ด้วยการตั้งค่า setOnLongClickListener ใน onBindViewHolder:

  • คืนค่า true จากตัวรับฟังเพื่อใช้เหตุการณ์นั้น
  • ใช้เพื่อแสดงกล่องโต้ตอบสำหรับลบหรือแก้ไข
  • หรือใช้การปัดเพื่อลบด้วย ItemTouchHelper

การเพิ่มตัวตกแต่งสมาชิก

เพิ่มเส้นแบ่งระหว่างสมาชิกในรายการด้วย DividerItemDecoration:

binding.recyclerView.apply {
    adapter = fruitAdapter
    layoutManager = LinearLayoutManager(this@MainActivity)
    addItemDecoration(
        DividerItemDecoration(
            this@MainActivity,
            DividerItemDecoration.VERTICAL
        )
    )
}

ตรวจสอบความเข้าใจ

วิธีที่แนะนำในการจัดการการคลิกสมาชิกใน RecyclerView Adapter คืออะไร

สรุป: การคลิกใน RecyclerView

ขณะนี้คุณสามารถสร้างรายการแบบโต้ตอบได้:

  • ส่งฟังก์ชันเรียกกลับแบบแลมบ์ดาไปยังตัวสร้างของ Adapter
  • ใน onBindViewHolder ให้เรียก holder.itemView.setOnClickListener
  • นำทางไปยังหน้าจอรายละเอียดโดยส่งข้อมูลเพิ่มเติมผ่าน Intent
  • ใช้ ListAdapter + DiffUtil เพื่ออัปเดตอย่างราบรื่นพร้อมภาพเคลื่อนไหว
  • เรียก submitList() เพื่ออัปเดตข้อมูลที่แสดง

ถัดไป: เก็บข้อมูลไว้ในเครื่องอย่างถาวรด้วย SharedPreferences

เริ่มต้นได้ฟรี

เรียนรู้ Kotlin ด้วย AI tutor — ฟรี

เขียนและเรียกใช้โค้ดจริงในเบราว์เซอร์ของคุณ รับความช่วยเหลือทันทีจาก AI tutor 24/7 และเรียนรู้ต่อจากที่คุณหยุดบนเว็บหรือในแอป

คอร์ส
36
บทเรียน
152

คำถามที่พบบ่อย

บทเรียน “เหตุการณ์คลิกใน RecyclerView” ฟรีหรือไม่

ใช่ — ข้อความเต็มของ “เหตุการณ์คลิกใน RecyclerView” ฟรีให้อ่านที่นี่บนเว็บ เพื่อปฏิบัติแบบโต้ตอบ (ตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7) และปลดล็อคส่วนที่เหลือของคอร์ส Android Academy ให้อัปเกรดเป็น CoddyKit PRO คอร์ส Android Academy มีบทเรียนทั้งหมด 6 บทเรียน

คุณจะเรียนรู้อะไรในบทเรียน “เหตุการณ์คลิกใน RecyclerView”

จัดการการคลิกและการกดค้างที่รายการใน RecyclerView ส่งตัวรับฟังการคลิกไปยังอะแดปเตอร์ และนำทางไปยังหน้ารายละเอียดเมื่อแตะรายการ คุณปฏิบัติ Android Academy ด้วยโค้ดที่ใช้งานได้จริงที่คุณเรียกใช้โดยตรงในเบราว์เซอร์ และติวเตอร์ AI ตลอด 24/7 ตอบคำถามของคุณขณะที่คุณไปผ่านบทเรียน

คุณต้องมีประสบการณ์ก่อนที่จะเริ่มเรียน Android Academy หรือไม่

ไม่จำเป็นต้องมีประสบการณ์มาก่อน Android Academy บน CoddyKit ออกแบบมาสำหรับผู้เริ่มต้นไปจนถึงผู้เรียนขั้นสูง คุณสามารถเริ่มต้นที่นี่หรือเริ่มจากตัวแรกและเรียนด้วยความเร็วของคุณเอง นี่คือบทเรียนที่ 3 จากทั้งหมด 6 บทเรียน

บทเรียน “เหตุการณ์คลิกใน RecyclerView” ใช้เวลานานแค่ไหน

บทเรียน CoddyKit ส่วนใหญ่ใช้เวลาประมาณ 5–10 นาที แต่ละบทเรียนจึงสั้นและเป็นแบบโต้ตอบ คุณสามารถก้าวหน้าอย่างต่อเนื่องและกลับมาเรียนต่อจากตรงที่เพิ่งหยุดบนเว็บและแอปได้เลย

ฉันเขียนและรันโค้ดในบทเรียน Android Academy นี้ได้ไหม

ได้ บทเรียน Android Academy ทุกบทมีตัวแก้ไขโค้ดในตัว คุณจึงเขียนและรันโค้ดจริงได้เลยในเบราว์เซอร์ และได้รับข้อเสนอแนะจาก AI ในทันที — ไม่ต้องติดตั้งในเครื่องของคุณ

บทเรียนทั้งหมดในหลักสูตรนี้

  1. คอลเลกชัน Kotlin
  2. พื้นฐาน RecyclerView
  3. เหตุการณ์คลิกใน RecyclerView
  4. SharedPreferences
  5. ค่ากำหนดของ DataStore
  6. อะแดปเตอร์และ DiffUtil
← กลับไปที่ Android Academy