Parcelize 사용하기

id 'kotlin-parcelize'


@Parcelize
data class Book(
    @SerializedName("itemId")val id:Long,
    @SerializedName("title")val title:String,
    @SerializedName("description")val description:String,
    @SerializedName("coverSmallUrl")val coverSmallUrl:String
) : Parcelable


디테일 화면 생성, 스크롤뷰 사용

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <ScrollView
        android:id="@+id/scrollView"
        android:layout_width="0dp"
        android:layout_height="0dp"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent">

        <androidx.constraintlayout.widget.ConstraintLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content">

            <TextView
                android:id="@+id/titleTextView"
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                android:layout_marginEnd="16dp"
                android:textColor="@color/black"
                android:textSize="24sp"
                android:gravity="center"
                app:layout_constraintEnd_toEndOf="parent"
                app:layout_constraintStart_toStartOf="parent"
                app:layout_constraintTop_toTopOf="parent" />

            <ImageView
                android:id="@+id/coverImageView"
                android:layout_width="300dp"
                android:layout_height="300dp"
                app:layout_constraintTop_toBottomOf="@id/titleTextView"
                app:layout_constraintStart_toStartOf="parent"
                app:layout_constraintEnd_toEndOf="parent"
                android:layout_marginTop="16dp"/>

            <TextView
                android:id="@+id/descriptionTextView"
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                android:textSize="16sp"
                app:layout_constraintTop_toBottomOf="@id/coverImageView"
                app:layout_constraintStart_toStartOf="parent"
                android:layout_margin="16dp"
                app:layout_constraintEnd_toEndOf="parent"
                android:textColor="@color/black"/>

            <EditText
                android:id="@+id/reviewEditText"
                android:layout_width="0dp"
                android:layout_height="300dp"
                app:layout_constraintTop_toBottomOf="@id/descriptionTextView"
                android:layout_margin="16dp"
                app:layout_constraintStart_toStartOf="parent"
                app:layout_constraintEnd_toEndOf="parent"/>

            <Button
                android:id="@+id/saveButton"
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                app:layout_constraintTop_toBottomOf="@id/reviewEditText"
                app:layout_constraintStart_toStartOf="parent"
                android:text="save"
                android:layout_margin="16dp"
                app:layout_constraintEnd_toEndOf="parent"/>


        </androidx.constraintlayout.widget.ConstraintLayout>
    </ScrollView>

</androidx.constraintlayout.widget.ConstraintLayout>


북 어뎁터에 인터페이스 추가


    // 추가 된 인터페이스
    interface OnItemClickedListener{
        fun onItemClicked(bookModel:Book)
    }

    var onItemClickedListener:OnItemClickedListener? = null

    inner class BookItemViewHolder(private val binding: ItemBookBinding) :RecyclerView.ViewHolder(binding.root) {
        fun bind(bookModel:Book){
            binding.titleTextView.text = bookModel.title
            binding.descriptionTextView.text = bookModel.description

            Glide
                .with(binding.titleTextView.context)
                .load(bookModel.coverSmallUrl)
                .into(binding.coverImageView)

            binding.root.setOnClickListener {
                onItemClickedListener?.onItemClicked(bookModel)
            }
        }
    }


클릭리스너 넘겨주기

    // 메인 엑티비티에서 어뎁터 구현할 때 리스너 객체 만들기
    adapter.onItemClickedListener = object :BookAdapter.OnItemClickedListener{
        override fun onItemClicked(bookModel: Book) {
            val intent = Intent(applicationContext, DetailActivity::class.java)

            // 위에서 직렬화 한 오브젝트를 넘겨주기
            intent.putExtra("bookModel", bookModel)
            startActivity(intent)
        }
    }


Review Model(Entity), ReviewDao 인터페이스 생성, 데이터베이스에 DAO 추가

// Review.kotlin
@Entity
data class Review(
    @PrimaryKey val id:Int?,
    @ColumnInfo(name = "review") val review:String?
)


// ReviewDao.kt
@Dao
interface ReviewDao {

    @Query("select * from review where id ==:id")
    fun getOneReview(id:Int): Review?

    // 대체 삽입
    @Insert(onConflict = OnConflictStrategy.REPLACE)
    fun saveReview(review:Review)
}


// AppDatabase.kt
@Database(entities = [History::class, Review::class], version =2)
abstract class AppDatabase:RoomDatabase() {
    abstract fun historyDao() : HistoryDao
    abstract fun reviewDao() : ReviewDao
}



Detail 엑티비티 생성

// DetailActicity.kt
class DetailActivity : AppCompatActivity() {

    lateinit var binding:ActivityDetailBinding
    lateinit var db:AppDatabase

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

        initDB()
        initLayout()
    }

    // 디비 생성
    private fun initDB() {
        db = Room.databaseBuilder(
            applicationContext,
            AppDatabase::class.java,
            "BookSearchDB"
        ).build()
    }

    // 레이아웃 초기화
    private fun initLayout() {
        val model = intent.getParcelableExtra<Book>("bookModel")
        binding.titleTextView.text = model?.title
        binding.descriptionTextView.text = model?.description

        Glide
            .with(this)
            .load(model?.coverSmallUrl)
            .into(binding.coverImageView)

        binding.saveButton.setOnClickListener {
            Thread{
                db.reviewDao().saveReview(Review(model?.id?.toInt() ?: 0, binding.reviewEditText.text.toString()))
            }.start()
        }

        Thread{
            val review = db.reviewDao().getOneReview(model?.id?.toInt() ?: 0)
            runOnUiThread{
                binding.reviewEditText.setText(review?.review.toString() ?: "")
            }
        }.start()
    }
}