Kotlin RecyclerView onItemClick

问题描述

我尝试使用 RecyclerView 实现项目点击大约 2 天。我尝试做所有关于这个主题的建议 stackoverflow。我已经没有任何想法要做什么了。所以我想问你。

这是我的代码:

    class CustomAdapter(var data: List<DataSource>,val clickListener: OnWordItemClickListener):
RecyclerView.Adapter<CustomAdapter.ViewHolder>() {

    class ViewHolder(view: View) : RecyclerView.ViewHolder(view)
    {
        val tv_front: TextView = view.findViewById(R.id.tv_front) as TextView
        val tv_back: TextView = view.findViewById(R.id.tv_back) as TextView
        // Define the click listener
        fun initialize(dataSource: DataSource,action: OnWordItemClickListener)
        {
            tv_front.text = dataSource._front
            tv_back.text = dataSource._back

            itemView.setOnClickListener {
                action.onItemClick(dataSource,adapterPosition)
            }
        }
    }

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

        return ViewHolder(view)
    }

    override fun onBindViewHolder(holder: ViewHolder,position: Int) {
        /*val currentItem = data[position]
        holder.tv_front.text = currentItem._front
        holder.tv_back.text = currentItem._back*/

        holder.initialize(data[position],clickListener)
    }

    override fun getItemCount(): Int = data.size
}

interface OnWordItemClickListener
{
    fun onItemClick(dataSource: DataSource,position: Int)
}

以及来自 MainActivity 的代码:

    class MainActivity : AppCompatActivity(),OnWordItemClickListener {

    val PERMISSION_REQUEST_CODE: Int = 123
    private lateinit var linearLayoutManager: LinearLayoutManager
    lateinit var rv_allWords: RecyclerView
    lateinit var adapter: CustomAdapter
    lateinit var databaseHandler: DatabaseHandler
    lateinit var dataSource: DataSource

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        permissions()

        rv_allWords = findViewById(R.id.rv_allWords) as RecyclerView
        linearLayoutManager = LinearLayoutManager(this)
        rv_allWords.layoutManager = linearLayoutManager

        databaseHandler = DatabaseHandler(this)
        val exampleList = databaseHandler.read_from()
        adapter = CustomAdapter(exampleList,this)
        rv_allWords.adapter = adapter
        adapter.notifyDataSetChanged()
    }

    fun permissions()
    {
        //var permissionStatus = ContextCompat.checkSelfPermission(this,Manifest.permission.WRITE_EXTERNAL_STORAGE)

        if (ContextCompat.checkSelfPermission(this,Manifest.permission.WRITE_EXTERNAL_STORAGE) +
                ContextCompat.checkSelfPermission(this,Manifest.permission.READ_EXTERNAL_STORAGE)
                == PackageManager.PERMISSION_GRANTED)
        {
            // permission granted
        } else {
            ActivityCompat.requestPermissions(this,arrayOf(Manifest.permission.WRITE_EXTERNAL_STORAGE,Manifest.permission.READ_EXTERNAL_STORAGE),PERMISSION_REQUEST_CODE)
        }
    }

    override fun onRequestPermissionsResult(requestCode: Int,permissions: Array<out String>,grantResults: IntArray) {
        super.onRequestPermissionsResult(requestCode,permissions,grantResults)
        when(requestCode)
        {
            PERMISSION_REQUEST_CODE ->
            {
                if ((grantResults.isNotEmpty()) && grantResults[0] == PackageManager.PERMISSION_GRANTED && grantResults[1] == PackageManager.PERMISSION_GRANTED)
                {
                    // permissions is granted. Continue the action or workflow
                    Toast.makeText(this,"Permissions granted",Toast.LENGTH_SHORT).show()
                } else {
                    // Explain to the user that the feature is unavailable because
                    // the features requires a permission the the user has denied
                    val alertDialog: AlertDialog? = this?.let {
                        val builder = AlertDialog.Builder(it)
                        builder.apply {
                            setPositiveButton(R.string.OK,DialogInterface.OnClickListener { dialog,id ->
                                finish()
                                System.exit(0)
                            })
                            setMessage("The app needs to save some data to external storage.")
                        }
                        builder.show()
                    }
                }
                return
            }
            // Add other 'when' line to check for other
            // permissions this app might request
            else ->
            {
                // Ignore all other requests
            }
        }
    }
    fun generateTestList(size: Int): List<DataSource> {
        val list = ArrayList<DataSource>()

        for (i in 0 until size)
        {
            val item = DataSource(i,"Item $i","$i")
            list += item
        }
        return list
    }

    override fun onCreateOptionsMenu(menu: Menu?): Boolean {
        menuInflater.inflate(R.menu.menu,menu)

        return super.onCreateOptionsMenu(menu)
    }

    override fun onOptionsItemSelected(item: MenuItem): Boolean {
        var id = item.itemId

        if(id == R.id.menu_refresh)
        {

        }
        return super.onOptionsItemSelected(item)
    }

    override fun onResume() {
        super.onResume()
        databaseHandler.read_from()
    }

    override fun onItemClick(dataSource: DataSource,position: Int) {
        Toast.makeText(this,dataSource._back,Toast.LENGTH_SHORT).show()
        Log.i("onItemClick",dataSource._back)
    }
}

当我在设备或模拟器上运行应用程序时,什么也没有发生。那是当我尝试单击 RecyclerView 中的任何项目时,我的消息没有显示并且应用程序运行没有错误。对不起我的英语不好。 我还能做什么?

解决方法

  1. itemView 在哪里定义?我可能错了,但您应该在 itemView 方法中将 view 更改为 initialize()

  2. 尝试使用 View.OnClickListener 类实现 ViewHolder

     class ViewHolder(val view: View) : RecyclerView.ViewHolder(view),View.OnClickListener {
     //(...)
         fun initialize(dataSource: DataSource,action: OnWordItemClickListener)
             {
                 tv_front.text = dataSource._front
                 tv_back.text = dataSource._back
    
                 view.setOnClickListener{action.onItemClick(dataSource,adapterPosition)}            
    
     }
    

更新: 因此,在调查了其余代码后,我在 xml 中发现了两个用于 ViewHolder 布局的 LinearLayouts。我删除了“父级”并开始工作。 这是更改后的 row_item.xml。

<?xml version="1.0" encoding="utf-8"?>

    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:gravity="center_horizontal"
        android:orientation="horizontal"
        android:clickable="true"
        android:focusable="true"
        android:background="?attr/selectableItemBackground">

        <TextView
            android:id="@+id/tv_front"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:padding="3dp"
            android:text="Front"
            android:textSize="32sp"
            android:gravity="left"
            android:layout_weight="1" />

        <TextView
            android:id="@+id/tv_back"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:padding="3dp"
            android:text="Back"
            android:textSize="32sp"
            android:gravity="right"
            android:layout_weight="1" />

    </LinearLayout>

相关问答

依赖报错 idea导入项目后依赖报错,解决方案:https://blog....
错误1:代码生成器依赖和mybatis依赖冲突 启动项目时报错如下...
错误1:gradle项目控制台输出为乱码 # 解决方案:https://bl...
错误还原:在查询的过程中,传入的workType为0时,该条件不起...
报错如下,gcc版本太低 ^ server.c:5346:31: 错误:‘struct...