Kotlin RecyclerView onItemClick
Kotlin RecyclerView onItemClick
我尝试使用 RecyclerView 实现项目点击大约 2 天。我尝试做关于这个主题的所有建议的 Whosebug。我已经不知道该怎么做了。所以想问问你
这是我的代码:
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 中的任何项目时,我的消息不会显示并且应用程序 运行s 没有错误。对不起我的英语不好。
我还能做什么?
itemView
在哪里定义的?我可能是错的,但你应该在 initialize()
方法中将 itemView
更改为 view
。
尝试用 ViewHolder
class 实现 View.OnClickListener
。
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。我删除了 'parent one' 并开始工作。
这里是修改后的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>
我尝试使用 RecyclerView 实现项目点击大约 2 天。我尝试做关于这个主题的所有建议的 Whosebug。我已经不知道该怎么做了。所以想问问你
这是我的代码:
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 中的任何项目时,我的消息不会显示并且应用程序 运行s 没有错误。对不起我的英语不好。 我还能做什么?
itemView
在哪里定义的?我可能是错的,但你应该在initialize()
方法中将itemView
更改为view
。尝试用
ViewHolder
class 实现View.OnClickListener
。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。我删除了 'parent one' 并开始工作。 这里是修改后的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>