我正在嘗試在 Kotlin 中制作一個簡單的 Android 應用程式,用于顯示來自互聯網的一些影像的學校專案。影像顯示在 cardView 內,在具有網格布局的 recyclerView 上。
在每個 cardView 中,我從 picsum 中獲取隨機影像,并且我還有一個星形圖示,用于將影像標記為收藏。這項作業的目的是使用 sharedPreferences。所以我必須存盤哪個影像被設定為收藏(一次只能有一個),并存盤那個位置,每當我旋轉設備時,圖示保持可見。
我應該如何存盤它以及我應該在哪個函式中呼叫 sharedPreferences 資料來顯示圖示?
配接器.kt
package com.example.bottomnavigationapp.fragimages.ui
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.ImageView
import androidx.recyclerview.widget.RecyclerView
import com.example.bottomnavigationapp.R
import com.squareup.picasso.Picasso
class GridItemAdapter(
val cardImages: Array<String>,
private val listener: OnItemClickListener) :
RecyclerView.Adapter<GridItemAdapter.ViewHolder>() {
inner class ViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView),
View.OnClickListener{
val cardImage : ImageView = itemView.findViewById(R.id.cardImage)
val favImage : ImageView = itemView.findViewById(R.id.favImage)
init {
cardImage.setOnClickListener(this)
}
override fun onClick(v: View?) {
var position : Int = adapterPosition
val address = cardImages[position]
if (position != RecyclerView.NO_POSITION) {
listener.onItemClick(position, favImage, address)
}
}
}
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
val view =
LayoutInflater.from(parent.context).inflate(R.layout.grid_item_view, parent, false)
return ViewHolder(view)
}
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
Picasso.get().load(cardImages[position]).into(holder.cardImage)
}
override fun getItemCount(): Int {
return cardImages.size
}
interface OnItemClickListener {
fun onItemClick(position: Int, favImage: ImageView, address: String)
}
}
片段.kt
package com.example.bottomnavigationapp.fragimages.ui
import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.ImageView
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
import androidx.fragment.app.Fragment
import androidx.recyclerview.widget.GridLayoutManager
import com.example.bottomnavigationapp.R
import com.example.bottomnavigationapp.databinding.FragmentImagesBinding
class ImagesFragment : Fragment(), GridItemAdapter.OnItemClickListener {
private lateinit var binding: FragmentImagesBinding
var hasFavourite : Int = -1
override fun onCreateView(
inflater: LayoutInflater, container: ViewGroup?,
savedInstanceState: Bundle?
): View? {
binding = FragmentImagesBinding.inflate(inflater, container, false)
val cardImages : Array<String> = resources.getStringArray(R.array.cardImages)
val adapter = GridItemAdapter(cardImages, this)
val gridLayout = GridLayoutManager(context, 2)
binding.gridItems.layoutManager = gridLayout
binding.gridItems.adapter = adapter
return binding.root
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
(activity as AppCompatActivity?)!!.supportActionBar!!.title = "Images Fragment"
super.onViewCreated(view, savedInstanceState)
}
override fun onItemClick(position: Int, favImage: ImageView, address: String) {
if (hasFavourite < 0) {
Toast.makeText(context, "Address: $address", Toast.LENGTH_SHORT).show()
val favAddress = address
val favStatus = true
val sharedPreferences = requireActivity().applicationContext.getSharedPreferences("myPref", 0)
val editor = sharedPreferences.edit()
editor.apply {
putString("favAddress", address)
putBoolean("favStatus", favStatus)
}
favImage.visibility = View.VISIBLE
hasFavourite = position
Toast.makeText(context, "Item $position set to favourite", Toast.LENGTH_SHORT).show()
}
else if (hasFavourite == position) {
favImage.visibility = View.GONE
hasFavourite = -1
}
else {
Toast.makeText(context, "Favourite already set at position $hasFavourite", Toast.LENGTH_SHORT).show()
}
}
}
uj5u.com熱心網友回復:
這是因為您一直在嘗試設定偏好但沒有得到它們。創建名為“UserPreferences.kt”的單獨類并將以下代碼粘貼到其中:
class UserPreferences {
// Store all Sharedpreferences methods in here
fun getPositionPref(fragment: Fragment): Int {
return fragment.requireActivity().getSharedPreferences(
"myPref",
Context.MODE_PRIVATE
).getInt(
"positionPref",
-1
)
}
fun setPositionPref(fragment: Fragment, position: Int) {
val sharedPreferences =
fragment.requireActivity().getSharedPreferences(
"myPref",
Context.MODE_PRIVATE
)
val editor: SharedPreferences.Editor = sharedPreferences.edit()
editor.putInt(
"positionPref",
position
)
editor.apply()
}
}
來到您的代碼,讓我們進行一些調整:
class ImagesFragment : Fragment(), GridItemAdapter.OnItemClickListener {
private lateinit var binding: FragmentImagesBinding
//edited
private var hasFavourite : Int = -1
override fun onCreateView(
inflater: LayoutInflater, container: ViewGroup?,
savedInstanceState: Bundle?
): View? {
binding = FragmentImagesBinding.inflate(inflater, container, false)
hasFavourite = UserPreferences().getPositionPref(this)
// Now you get what's in sharedPreferences.
// If it's first time it will be -1 for default.
val cardImages : Array<String> =
resources.getStringArray(R.array.cardImages)
val adapter = GridItemAdapter(cardImages, this, hasFavourite)
// send hasFavourite to adapter too.
val gridLayout = GridLayoutManager(context, 2)
binding.gridItems.layoutManager = gridLayout
binding.gridItems.adapter = adapter
return binding.root
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
(activity as AppCompatActivity?)!!.supportActionBar!!.title = "Images Fragment"
super.onViewCreated(view, savedInstanceState)
}
override fun onItemClick(position: Int, favImage: ImageView, address: String) {
if (hasFavourite == -1) {
Toast.makeText(context, "Address: $address", Toast.LENGTH_SHORT).show()
UserPreferences().setPositionPref(this, position)
// Now we set it to position, for another time you wanna get
//putString("favAddress", address)
//putBoolean("favStatus", favStatus)
//For this two, you need to create it's own functions in
// UserPreferences class we created, you got the idea
favImage.visibility = View.VISIBLE
hasFavourite = UserPreferences().getPositionPref(this)
// We get the new value of hasFavourite from shared pref again.
Toast.makeText(context, "Item $position set to favourite", Toast.LENGTH_SHORT).show()
}
else if (hasFavourite == position) {
favImage.visibility = View.GONE
//edited
UserPreferences().setPositionPref(this, -1)
hasFavourite = UserPreferences().getPositionPref(this)
// We set it to default, there should be no item favorited
}
else {
Toast.makeText(context, "Favourite already set at position $hasFavourite", Toast.LENGTH_SHORT).show()
}
}
}
因此,假設您選擇了一個收藏夾并關閉應用程式并再次打開,它不會以收藏夾應用到配接器開始,直到您單擊其中一個專案來解決這個問題,我們將 hasFavourite 發送到配接器:
class GridItemAdapter(
val cardImages: Array<String>,
private val listener: OnItemClickListener,
private val hasFavourite: Int) :
RecyclerView.Adapter<GridItemAdapter.ViewHolder>() {
// and onBind we check and set:
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
Picasso.get().load(cardImages[position]).into(holder.cardImage)
if (hasFavourite == position) {
holder.favImage.visibility = View.VISIBLE
}
}
我認為這應該可以解決問題,沒有嘗試過,如果不起作用,請告訴我。
轉載請註明出處,本文鏈接:https://www.uj5u.com/gongcheng/530053.html
標籤:安卓科特林安卓片段android-recyclerview共享偏好
