Skip to content

Commit 9c67591

Browse files
authored
Added Dark Mode (#406)
* Added Dark mode * updated readme and updated version
1 parent 4500bfd commit 9c67591

10 files changed

Lines changed: 152 additions & 11 deletions

File tree

README.md

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -307,6 +307,36 @@ This library uses material components, so should use Theme.MaterialComponents or
307307

308308
> `colorControlActivated` is used to colorize Street title, if not set, it uses colorAccent by default
309309
310+
##### Dark Theme (Day/Night) support ✅
311+
312+
Leku supports Android Day/Night resources and can automatically adapt to Dark Mode, **as long as the picker activity is using a DayNight theme**.
313+
314+
**Recommended (easiest):** apply `leku_Theme` to `LocationPickerActivity` in your app manifest:
315+
316+
```xml
317+
<activity
318+
android:name="com.adevinta.leku.LocationPickerActivity"
319+
android:label="@string/leku_title_activity_location_picker"
320+
android:theme="@style/leku_Theme"
321+
android:windowSoftInputMode="adjustPan"
322+
android:parentActivityName=".MainActivity">
323+
<intent-filter>
324+
<action android:name="android.intent.action.SEARCH" />
325+
</intent-filter>
326+
<meta-data
327+
android:name="android.app.searchable"
328+
android:resource="@xml/leku_searchable" />
329+
<meta-data
330+
android:name="android.support.PARENT_ACTIVITY"
331+
android:value=".MainActivity" />
332+
</activity>
333+
```
334+
335+
If your app already uses a DayNight theme (AppCompat or MaterialComponents), you can also rely on your app theme instead of `leku_Theme`.
336+
337+
> Note: the picker UI will follow the **system** or **app** night mode.
338+
> The Google Map tiles themselves can be styled independently via `.withMapStyle(...)` (see below).
339+
310340
##### New activity images and button color customization
311341

312342
If you need to change theme colors for new activity map, you can do it with the below keys:
@@ -327,6 +357,23 @@ To customize map, use:
327357

328358
> Theme creator here: https://mapstyle.withgoogle.com/
329359
360+
**Tip for Dark Mode maps:** you can provide a different style JSON for night mode, e.g.:
361+
362+
```kotlin
363+
val builder = LocationPickerActivity.Builder(context)
364+
.withLocation(41.4036299, 2.1743558)
365+
366+
if ((context.resources.configuration.uiMode and android.content.res.Configuration.UI_MODE_NIGHT_MASK)
367+
== android.content.res.Configuration.UI_MODE_NIGHT_YES
368+
) {
369+
builder.withMapStyle(R.raw.map_style_night)
370+
} else {
371+
builder.withMapStyle(R.raw.map_style_retro)
372+
}
373+
374+
val intent = builder.build()
375+
```
376+
330377
##### Layout
331378

332379
It's possible to hide or show some of the information shown after selecting a location.

app/src/main/java/com/adevinta/mappicker/MainActivity.kt

Lines changed: 62 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import androidx.activity.compose.setContent
1313
import androidx.activity.result.ActivityResult
1414
import androidx.activity.result.contract.ActivityResultContracts
1515
import androidx.appcompat.app.AppCompatActivity
16+
import androidx.appcompat.app.AppCompatDelegate
1617
import androidx.compose.foundation.Image
1718
import androidx.compose.foundation.layout.Arrangement
1819
import androidx.compose.foundation.layout.Box
@@ -153,9 +154,32 @@ class MainActivity : AppCompatActivity() {
153154
}
154155
}
155156

157+
/**
158+
* Toggles between Light and Dark mode for the sample app.
159+
*/
160+
private fun toggleNightMode(context: Context) {
161+
val currentNightMode =
162+
context.resources.configuration.uiMode and android.content.res.Configuration.UI_MODE_NIGHT_MASK
163+
164+
val newMode =
165+
when (currentNightMode) {
166+
android.content.res.Configuration.UI_MODE_NIGHT_YES -> AppCompatDelegate.MODE_NIGHT_NO
167+
else -> AppCompatDelegate.MODE_NIGHT_YES
168+
}
169+
170+
AppCompatDelegate.setDefaultNightMode(newMode)
171+
}
172+
173+
private fun isNightMode(context: Context): Boolean {
174+
val currentNightMode =
175+
context.resources.configuration.uiMode and android.content.res.Configuration.UI_MODE_NIGHT_MASK
176+
return currentNightMode == android.content.res.Configuration.UI_MODE_NIGHT_YES
177+
}
178+
156179
private fun onLaunchMapPickerClicked(context: Context) {
157180
val activity = context as MainActivity
158-
val locationPickerIntent =
181+
182+
val builder =
159183
LocationPickerActivity
160184
.Builder(activity)
161185
.withLocation(DEMO_LATITUDE, DEMO_LONGITUDE)
@@ -175,8 +199,15 @@ private fun onLaunchMapPickerClicked(context: Context) {
175199
// .withVoiceSearchHidden()
176200
.withUnnamedRoadHidden()
177201
.withSolidBottomColor()
178-
// .withSearchBarHidden()
179-
.build()
202+
// .withSearchBarHidden()
203+
204+
// Optional: use a dark Google Maps style when night mode is enabled
205+
// (requires you to add app/src/main/res/raw/map_style_night.json)
206+
if (isNightMode(context)) {
207+
builder.withMapStyle(R.raw.map_style_night)
208+
}
209+
210+
val locationPickerIntent = builder.build()
180211

181212
// this is optional if you want to return RESULT_OK if you don't set the
182213
// latitude/longitude and click back button
@@ -231,12 +262,19 @@ private fun onMapPoisClicked(context: Context) {
231262

232263
private fun onMapWithStylesClicked(context: Context) {
233264
val activity = context as MainActivity
234-
val locationPickerIntent =
265+
266+
val builder =
235267
LocationPickerActivity
236268
.Builder(activity)
237269
.withLocation(DEMO_LATITUDE, DEMO_LONGITUDE)
238-
.withMapStyle(R.raw.map_style_retro)
239-
.build()
270+
271+
if (isNightMode(context)) {
272+
builder.withMapStyle(R.raw.map_style_night)
273+
} else {
274+
builder.withMapStyle(R.raw.map_style_retro)
275+
}
276+
277+
val locationPickerIntent = builder.build()
240278
activity.mapPoisActivityResultLauncher.launch(locationPickerIntent)
241279
}
242280

@@ -260,6 +298,24 @@ fun MainView() {
260298
painter = painterResource(id = R.mipmap.leku_img_logo),
261299
contentDescription = null,
262300
)
301+
302+
Button(
303+
colors =
304+
ButtonDefaults.buttonColors(
305+
backgroundColor = buttonColor,
306+
contentColor = Color.White,
307+
),
308+
onClick = { toggleNightMode(context) },
309+
) {
310+
Text(
311+
"Toggle Dark / Light",
312+
Modifier
313+
.padding(8.dp)
314+
.fillMaxWidth(),
315+
textAlign = TextAlign.Center,
316+
)
317+
}
318+
263319
Button(
264320
colors =
265321
ButtonDefaults.buttonColors(
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
[
2+
{ "elementType": "geometry", "stylers": [{ "color": "#1d2c4d" }] },
3+
{ "elementType": "labels.text.fill", "stylers": [{ "color": "#8ec3b9" }] },
4+
{ "elementType": "labels.text.stroke", "stylers": [{ "color": "#1a3646" }] },
5+
{ "featureType": "road", "elementType": "geometry", "stylers": [{ "color": "#304a7d" }] },
6+
{ "featureType": "water", "elementType": "geometry", "stylers": [{ "color": "#0e1626" }] }
7+
]

app/src/main/res/values/styles.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
<resources>
22

33
<style name="AppTheme"
4-
parent="Theme.MaterialComponents.Light.NoActionBar">
4+
parent="leku_Theme">
55
<item name="colorPrimary">#009688</item>
66
<item name="colorPrimaryDark">#00695C</item>
77
<item name="colorAccent">#2979FF</item>

gradle.properties

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ org.gradle.jvmargs=-Xmx2048m
22
org.gradle.configureondemand=false
33
android.useAndroidX=true
44
libGroup=com.adevinta.android
5-
libVersion=13.0.0
5+
libVersion=13.1.0
66

77
android.buildFeatures.buildConfig=true
88
android.nonTransitiveRClass=false

gradle/libs.versions.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ animation = "1.9.3"
55
espressoVersion = "3.7.0"
66
fragmentKtx = "1.8.9"
77
googleMapsServices = "2.2.0"
8-
gradle = "8.13.0"
8+
gradle = "8.13.2"
99
gradleNexusStagingPlugin = "0.30.0"
1010
kotlinVersion = "2.2.20"
1111
kotlinxCoroutinesGuava = "1.10.2"

leku/src/main/AndroidManifest.xml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
android:name="com.adevinta.leku.LocationPickerActivity"
1515
android:label="@string/leku_title_activity_location_picker"
1616
android:windowSoftInputMode="adjustPan"
17+
android:theme="@style/leku_Theme"
1718
android:parentActivityName=".MainActivity">
1819
<intent-filter>
1920
<action android:name="android.intent.action.SEARCH" />

leku/src/main/res/drawable/leku_bottom_screen_gradient_background.xml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
<?xml version="1.0" encoding="utf-8"?>
22
<shape xmlns:android="http://schemas.android.com/apk/res/android">
33
<gradient
4-
android:startColor="#FFFFFFFF"
5-
android:endColor="#00FFFFFF"
4+
android:startColor="@color/leku_white"
5+
android:endColor="@android:color/transparent"
66
android:angle="270"
77
android:dither="true"
88
/>
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
<?xml version="1.0" encoding="utf-8"?>
2+
<resources>
3+
<color name="leku_white">#FF1E1E1E</color>
4+
<color name="leku_white_alpha">#F21E1E1E</color>
5+
<color name="leku_soft_grey">#FF2A2A2A</color>
6+
<color name="leku_mid_grey">#FF9AA0A6</color>
7+
<color name="leku_strong_grey">#FFE8EAED</color>
8+
<color name="leku_search_background">#0000</color>
9+
<color name="leku_blackish">#FFE8EAED</color>
10+
<color name="leku_black_20_transparent">#33FFFFFF</color>
11+
12+
<color name="leku_ic_close">@null</color>
13+
<color name="leku_ic_gps">@null</color>
14+
<color name="leku_ic_satellite">@null</color>
15+
<color name="leku_ic_maps">@null</color>
16+
<color name="leku_location_accept_button_bg">@null</color>
17+
</resources>
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
<?xml version="1.0" encoding="utf-8"?>
2+
<resources>
3+
4+
<!--
5+
Apply this theme to LocationPickerActivity in your app's AndroidManifest.xml:
6+
android:theme="@style/leku_Theme"
7+
It inherits from a DayNight parent so it will automatically follow the system/app night mode.
8+
-->
9+
<style name="leku_Theme" parent="Theme.MaterialComponents.DayNight.NoActionBar">
10+
<!-- Keep colors coming from the host app/theme (primary, secondary, etc.) -->
11+
</style>
12+
13+
</resources>

0 commit comments

Comments
 (0)