Skip to content

Commit e1b5abe

Browse files
refactor(dialogs): Use CardView for Top and Bottom Sheets
This commit refactors the `FontBottomSheetDialogLocked` and introduces a new `FontTopSheetDialogLocked` to use `MaterialCardView` as the main sheet container. This approach provides a more reliable way to achieve rounded corners compared to the previous `FrameLayout` with a `GradientDrawable` background. Key changes: - `FontBottomSheetDialogLocked`: - Replaced `FrameLayout` with `MaterialCardView` for the sheet. - Removed the logic for creating rounded corners with `GradientDrawable`. - Removed dependency on `BottomSheetBehavior` and its associated logic, as dragging is disabled. - `FontTopSheetDialogLocked`: - Added a new `FontTopSheetDialogLocked` class for dialogs appearing from the top. - Implemented using `MaterialCardView` for consistent appearance with the bottom sheet. - Both dialogs now have a consistent slide-in animation.
1 parent 31386c0 commit e1b5abe

File tree

2 files changed

+158
-95
lines changed

2 files changed

+158
-95
lines changed

app/src/main/java/com/github/creativecodecat/components/views/FontBottomSheetDialogLocked.kt

Lines changed: 28 additions & 95 deletions
Original file line numberDiff line numberDiff line change
@@ -2,51 +2,29 @@ package com.github.creativecodecat.components.views
22

33
import android.content.Context
44
import android.graphics.Typeface
5-
import android.graphics.drawable.GradientDrawable
65
import android.view.Gravity
76
import android.view.View
87
import android.view.ViewGroup
98
import android.view.WindowManager
109
import android.widget.FrameLayout
1110
import android.widget.TextView
1211
import androidx.appcompat.app.AppCompatDialog
12+
import androidx.cardview.widget.CardView
1313
import androidx.coordinatorlayout.widget.CoordinatorLayout
1414
import androidx.core.content.ContextCompat
1515
import com.github.droidworksstudio.common.isGestureNavigationEnabled
1616
import com.github.droidworksstudio.mlauncher.R
1717
import com.github.droidworksstudio.mlauncher.helper.CustomFontView
1818
import com.github.droidworksstudio.mlauncher.helper.FontManager
19-
import com.google.android.material.bottomsheet.BottomSheetBehavior
20-
import com.google.android.material.R as MaterialR
19+
import com.google.android.material.card.MaterialCardView
2120

2221
/**
23-
* BottomSheetDialog that:
24-
* - Disables swipe-to-dismiss
25-
* - Keeps tap outside, back button, and programmatic `.hide()` working
22+
* BottomSheetDialog using CardView for reliable rounded bottom corners.
2623
*/
27-
2824
class FontBottomSheetDialogLocked(context: Context) : AppCompatDialog(context), CustomFontView {
2925

30-
private var coordinator: CoordinatorLayout = CoordinatorLayout(context).apply {
31-
layoutParams = ViewGroup.LayoutParams(
32-
ViewGroup.LayoutParams.MATCH_PARENT,
33-
ViewGroup.LayoutParams.MATCH_PARENT
34-
)
35-
}
36-
37-
private var sheet: FrameLayout = FrameLayout(context).apply {
38-
id = MaterialR.id.design_bottom_sheet
39-
layoutParams = CoordinatorLayout.LayoutParams(
40-
ViewGroup.LayoutParams.MATCH_PARENT,
41-
ViewGroup.LayoutParams.WRAP_CONTENT
42-
).apply {
43-
gravity = Gravity.BOTTOM
44-
}
45-
46-
elevation = 16 * context.resources.displayMetrics.density
47-
}
48-
49-
private var behavior: BottomSheetBehavior<FrameLayout>
26+
private val coordinator: CoordinatorLayout
27+
private val sheet: CardView
5028
private var cancelableFlag = true
5129

5230
override fun setCancelable(flag: Boolean) {
@@ -55,7 +33,7 @@ class FontBottomSheetDialogLocked(context: Context) : AppCompatDialog(context),
5533
}
5634

5735
init {
58-
// Coordinator
36+
// Coordinator layout
5937
coordinator = CoordinatorLayout(context).apply {
6038
layoutParams = ViewGroup.LayoutParams(
6139
ViewGroup.LayoutParams.MATCH_PARENT,
@@ -64,51 +42,22 @@ class FontBottomSheetDialogLocked(context: Context) : AppCompatDialog(context),
6442
setOnClickListener { if (cancelableFlag) dismiss() }
6543
}
6644

45+
// Sheet wrapped in CardView
46+
sheet = MaterialCardView(context).apply {
47+
layoutParams = CoordinatorLayout.LayoutParams(
48+
ViewGroup.LayoutParams.MATCH_PARENT,
49+
ViewGroup.LayoutParams.WRAP_CONTENT
50+
).apply { gravity = Gravity.BOTTOM }
6751

68-
// Bottom sheet layout params with behavior attached
69-
val lp = CoordinatorLayout.LayoutParams(
70-
ViewGroup.LayoutParams.MATCH_PARENT,
71-
ViewGroup.LayoutParams.WRAP_CONTENT
72-
).apply {
73-
gravity = Gravity.BOTTOM
74-
width = ViewGroup.LayoutParams.MATCH_PARENT
75-
behavior = BottomSheetBehavior<FrameLayout>()
76-
// optional: no margins
77-
setMargins(0, 0, 0, 0)
52+
cardElevation = 16 * context.resources.displayMetrics.density
53+
setCardBackgroundColor(ContextCompat.getColor(context, R.color.colorPrimaryBackground))
7854
}
7955

80-
// Sheet
81-
sheet = FrameLayout(context).apply {
82-
id = MaterialR.id.design_bottom_sheet
83-
layoutParams = lp
84-
// background drawable (with rounded top corners)
85-
background = GradientDrawable().apply {
86-
shape = GradientDrawable.RECTANGLE
87-
val radiusPx = 16 * context.resources.displayMetrics.density
88-
cornerRadii = floatArrayOf(
89-
radiusPx, radiusPx, // top-left
90-
radiusPx, radiusPx, // top-right
91-
0f, 0f, // bottom-right
92-
0f, 0f // bottom-left
93-
)
94-
setColor(ContextCompat.getColor(context, R.color.colorPrimaryBackground))
95-
}
96-
elevation = 16 * context.resources.displayMetrics.density
97-
}
9856

99-
100-
// Add sheet to coordinator
10157
coordinator.addView(sheet)
10258
super.setContentView(coordinator)
10359

104-
// Get behavior safely
105-
behavior = BottomSheetBehavior.from(sheet).apply {
106-
isDraggable = false
107-
skipCollapsed = true
108-
state = BottomSheetBehavior.STATE_EXPANDED
109-
}
110-
111-
// Window dim
60+
// Window setup
11261
window?.apply {
11362
setBackgroundDrawableResource(android.R.color.transparent)
11463
setLayout(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT)
@@ -119,11 +68,10 @@ class FontBottomSheetDialogLocked(context: Context) : AppCompatDialog(context),
11968
}
12069
}
12170

122-
// Font manager
71+
// Register font manager
12372
FontManager.register(this)
12473
}
12574

126-
12775
override fun setContentView(view: View) {
12876
sheet.removeAllViews()
12977
sheet.addView(
@@ -137,41 +85,28 @@ class FontBottomSheetDialogLocked(context: Context) : AppCompatDialog(context),
13785
override fun onStart() {
13886
super.onStart()
13987

140-
behavior.state = BottomSheetBehavior.STATE_EXPANDED
141-
142-
// Force full width
143-
sheet.layoutParams = (sheet.layoutParams as CoordinatorLayout.LayoutParams).apply {
144-
width = ViewGroup.LayoutParams.MATCH_PARENT
145-
gravity = Gravity.BOTTOM
146-
}
147-
sheet.requestLayout()
148-
149-
// Apply font
88+
// Apply font recursively
15089
window?.decorView?.let { rootView ->
15190
FontManager.getTypeface(context)?.let { typeface ->
15291
applyFontRecursively(rootView, typeface)
15392
}
15493
}
15594

156-
val paddingBottom = when (isGestureNavigationEnabled(context)) {
95+
// Add padding for gesture/status bar
96+
val bottomMargin = when (isGestureNavigationEnabled(context)) {
15797
true -> context.resources.getDimensionPixelSize(R.dimen.bottom_margin_gesture_nav)
15898
false -> context.resources.getDimensionPixelSize(R.dimen.bottom_margin_3_button_nav)
15999
}
160100

161-
sheet.setPadding(
162-
sheet.paddingLeft,
163-
sheet.paddingTop,
164-
sheet.paddingRight,
165-
paddingBottom
166-
)
167-
168-
// Determine side margins
101+
// Apply side margins
169102
val sideMargin = context.resources.getDimensionPixelSize(R.dimen.bottom_sheet_side_margin)
170-
171-
// Update LayoutParams for the sheet
172103
val lp = sheet.layoutParams as CoordinatorLayout.LayoutParams
173-
lp.setMargins(sideMargin, lp.topMargin, sideMargin, lp.bottomMargin)
104+
lp.setMargins(sideMargin, lp.topMargin, sideMargin, bottomMargin)
174105
sheet.layoutParams = lp
106+
107+
// Slide down from top
108+
sheet.translationY = -sheet.height.toFloat()
109+
sheet.animate().translationY(0f).setDuration(250).start()
175110
}
176111

177112
override fun applyFont(typeface: Typeface?) {
@@ -184,11 +119,9 @@ class FontBottomSheetDialogLocked(context: Context) : AppCompatDialog(context),
184119
if (typeface == null) return
185120
when (view) {
186121
is TextView -> view.typeface = typeface
187-
is ViewGroup -> {
188-
for (i in 0 until view.childCount) {
189-
applyFontRecursively(view.getChildAt(i), typeface)
190-
}
122+
is ViewGroup -> (0 until view.childCount).forEach {
123+
applyFontRecursively(view.getChildAt(it), typeface)
191124
}
192125
}
193126
}
194-
}
127+
}
Lines changed: 130 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,130 @@
1+
package com.github.creativecodecat.components.views
2+
3+
import android.content.Context
4+
import android.graphics.Typeface
5+
import android.view.Gravity
6+
import android.view.View
7+
import android.view.ViewGroup
8+
import android.view.WindowManager
9+
import android.widget.FrameLayout
10+
import android.widget.TextView
11+
import androidx.appcompat.app.AppCompatDialog
12+
import androidx.cardview.widget.CardView
13+
import androidx.coordinatorlayout.widget.CoordinatorLayout
14+
import androidx.core.content.ContextCompat
15+
import com.github.droidworksstudio.mlauncher.R
16+
import com.github.droidworksstudio.mlauncher.helper.CustomFontView
17+
import com.github.droidworksstudio.mlauncher.helper.FontManager
18+
import com.google.android.material.card.MaterialCardView
19+
20+
/**
21+
* TopSheetDialog using CardView for reliable rounded bottom corners.
22+
*/
23+
class FontTopSheetDialogLocked(context: Context) : AppCompatDialog(context), CustomFontView {
24+
25+
private val coordinator: CoordinatorLayout
26+
private val sheet: CardView
27+
private var cancelableFlag = true
28+
29+
override fun setCancelable(flag: Boolean) {
30+
super.setCancelable(flag)
31+
cancelableFlag = flag
32+
}
33+
34+
init {
35+
// Coordinator layout
36+
coordinator = CoordinatorLayout(context).apply {
37+
layoutParams = ViewGroup.LayoutParams(
38+
ViewGroup.LayoutParams.MATCH_PARENT,
39+
ViewGroup.LayoutParams.MATCH_PARENT
40+
)
41+
setOnClickListener { if (cancelableFlag) dismiss() }
42+
}
43+
44+
// Sheet wrapped in CardView
45+
sheet = MaterialCardView(context).apply {
46+
layoutParams = CoordinatorLayout.LayoutParams(
47+
ViewGroup.LayoutParams.MATCH_PARENT,
48+
ViewGroup.LayoutParams.WRAP_CONTENT
49+
).apply { gravity = Gravity.TOP }
50+
51+
cardElevation = 16 * context.resources.displayMetrics.density
52+
setCardBackgroundColor(ContextCompat.getColor(context, R.color.colorPrimaryBackground))
53+
}
54+
55+
56+
coordinator.addView(sheet)
57+
super.setContentView(coordinator)
58+
59+
// Window setup
60+
window?.apply {
61+
setBackgroundDrawableResource(android.R.color.transparent)
62+
setLayout(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT)
63+
setGravity(Gravity.TOP)
64+
attributes = attributes.apply {
65+
dimAmount = 0.5f
66+
flags = flags or WindowManager.LayoutParams.FLAG_DIM_BEHIND
67+
}
68+
}
69+
70+
// Register font manager
71+
FontManager.register(this)
72+
}
73+
74+
override fun setContentView(view: View) {
75+
sheet.removeAllViews()
76+
sheet.addView(
77+
view, FrameLayout.LayoutParams(
78+
ViewGroup.LayoutParams.MATCH_PARENT,
79+
ViewGroup.LayoutParams.WRAP_CONTENT
80+
)
81+
)
82+
}
83+
84+
override fun onStart() {
85+
super.onStart()
86+
87+
// Apply font recursively
88+
window?.decorView?.let { rootView ->
89+
FontManager.getTypeface(context)?.let { typeface ->
90+
applyFontRecursively(rootView, typeface)
91+
}
92+
}
93+
94+
// Add padding for gesture/status bar
95+
val paddingBottom = context.resources.getDimensionPixelSize(R.dimen.bottom_sheet_side_margin)
96+
97+
sheet.setContentPadding(
98+
sheet.paddingLeft,
99+
sheet.paddingTop,
100+
sheet.paddingRight,
101+
paddingBottom
102+
)
103+
104+
// Apply side margins
105+
val sideMargin = context.resources.getDimensionPixelSize(R.dimen.bottom_sheet_side_margin)
106+
val lp = sheet.layoutParams as CoordinatorLayout.LayoutParams
107+
lp.setMargins(sideMargin, lp.topMargin, sideMargin, lp.bottomMargin)
108+
sheet.layoutParams = lp
109+
110+
// Slide down from top
111+
sheet.translationY = -sheet.height.toFloat()
112+
sheet.animate().translationY(0f).setDuration(250).start()
113+
}
114+
115+
override fun applyFont(typeface: Typeface?) {
116+
window?.decorView?.let { rootView ->
117+
applyFontRecursively(rootView, typeface)
118+
}
119+
}
120+
121+
private fun applyFontRecursively(view: View, typeface: Typeface?) {
122+
if (typeface == null) return
123+
when (view) {
124+
is TextView -> view.typeface = typeface
125+
is ViewGroup -> (0 until view.childCount).forEach {
126+
applyFontRecursively(view.getChildAt(it), typeface)
127+
}
128+
}
129+
}
130+
}

0 commit comments

Comments
 (0)