0️⃣ CustomDialog!
사실 Dialog를 띄워 화면에 알림을 주는 일은 이제는 도저히 뺄 수 없는 필수 기능이다. 할 줄 안다고 생각했는데도 막상 다시 하니 또 버벅거리며 한참을 헤매서 세세하게 기록해보려고 한다.
1️⃣ dialog.xml
<?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"
android:background="@color/black_a50"
android:gravity="center"
android:paddingHorizontal="20dp">
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="192dp"
android:background="@drawable/shape_dialog"
android:paddingHorizontal="20dp"
android:paddingVertical="14dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent">
<TextView
android:id="@+id/tv_dialog_title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center"
android:text="@string/dialog_default"
android:textColor="@color/white"
android:textSize="16sp"
android:textStyle="bold"
app:layout_constraintBottom_toTopOf="@+id/wrapper_buttons"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<LinearLayout
android:id="@+id/wrapper_buttons"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent">
<androidx.appcompat.widget.AppCompatButton
android:id="@+id/btn_dialog_cancel"
style="@style/detail_btn"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginEnd="4dp"
android:layout_weight="1"
android:backgroundTint="@color/transparent"
android:gravity="center"
android:text="@string/dialog_cancel"
android:textColor="@color/blue_grey"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent" />
<androidx.appcompat.widget.AppCompatButton
android:id="@+id/btn_dialog_confirm"
style="@style/detail_btn"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginStart="4dp"
android:layout_weight="1"
android:gravity="center"
android:text="@string/dialog_confirm"
android:textAllCaps="false"
app:layout_constraintBottom_toBottomOf="@+id/btn_dialog_cancel"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@+id/btn_dialog_cancel"
app:layout_constraintTop_toTopOf="@+id/btn_dialog_cancel" />
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
핵심 포인트는 가장 최상단 부모 태그의 width, height값을 match_parent로 주는 것이다.
2️⃣ DialogFragment
class TwoButtonDialogFragment(
private val title: String,
private val onClickConfirm: () -> Unit
) : DialogFragment() {
private var _binding: DialogTwobuttonBinding? = null
val binding get() = _binding!!
override fun onCreateView(
inflater: LayoutInflater, container: ViewGroup?,
savedInstanceState: Bundle?
): View {
_binding = DialogTwobuttonBinding.inflate(inflater, container, false)
return binding.root
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
initView()
}
private fun initView() = with(binding) {
tvDialogTitle.text = title
btnDialogCancel.setOnClickListener {
dismiss()
}
btnDialogConfirm.setOnClickListener {
onClickConfirm()
dismiss()
}
}
override fun onResume() {
super.onResume()
// full Screen code
dialog?.window?.setLayout(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT)
dialog?.window?.setBackgroundDrawable(ColorDrawable(Color.TRANSPARENT))
dialog?.window?.clearFlags(WindowManager.LayoutParams.FLAG_DIM_BEHIND)
}
}
해당 Fragment를 재사용하기 위해 생성자로 title과 setOnClickListner를 받아와서 사용했다.
또한 onResume() 코드를 전체 복사해서 붙여넣자! 그렇지 않으면 아래 스크린샷처럼 옹졸한 Dialog가 나온다... (옹졸 그자체)
3️⃣ Dialog 띄우는 함수
btn.setOnClickListener {
val dialog = TwoButtonDialogFragment(
getString(R.string.timer_dialog_finish)
) {
// timer 종료하기
}
// 알림창이 띄워져있는 동안 배경 클릭 막기
dialog.isCancelable = false
dialog.show(getParentFragmentManager(), "ConfirmDialog")
}
이렇게 setOnClickListener에서 dialog를 선언해주고, 생성자로 받기로 한 props들을 모두 보내준 뒤, show해주면 된다.
그럼 이렇게 완벽한 Dialog가 등장한다.
막상 정리해놓고 보니 별 거 없는데 또 저 옹졸하게 나오는 dialog 때문에 40분 넘게 삽질했다...!
더 열심히 공부해보는 것으로...
'Android' 카테고리의 다른 글
Android에서 Firebase Google Login 구현하기 (0) | 2024.08.31 |
---|---|
Hilt로 Context 사용하기 (feat. OkHttpClient cache) (0) | 2024.08.29 |
Android의 4대 구성요소 알아보기 (0) | 2024.08.14 |
Android에서 Fragment와 TabLayout, 그리고 RecyclerView 적용하기 (0) | 2024.08.05 |
Android에서 Lottie Animation 적용하기 (0) | 2024.07.04 |