Merge pull request #56 from thecraftman/add-m1-support

Add M1 Mac support & Optimize app startup by deferring initialization of non-critical components
This commit is contained in:
Mayokun Adeniyi
2024-06-04 23:47:19 +01:00
committed by GitHub
6 changed files with 146 additions and 122 deletions

111
.gitignore vendored
View File

@@ -1,111 +0,0 @@
# Created by https://www.toptal.com/developers/gitignore/api/android
# Edit at https://www.toptal.com/developers/gitignore?templates=android
### Android ###
# Built application files
*.apk
*.aar
*.ap_
*.aab
# Files for the ART/Dalvik VM
*.dex
# Java class files
*.class
# Generated files
bin/
gen/
out/
# Uncomment the following line in case you need and you don't have the release build type files in your app
# release/
# Gradle files
.gradle/
build/
# Local configuration file (sdk path, etc)
local.properties
# Proguard folder generated by Eclipse
proguard/
# Log Files
*.log
# Android Studio Navigation editor temp files
.navigation/
# Android Studio captures folder
captures/
# IntelliJ
*.iml
.idea/
.idea/workspace.xml
.idea/tasks.xml
.idea/gradle.xml
.idea/assetWizardSettings.xml
.idea/dictionaries
.idea/libraries
.idea/jarRepositories.xml
# Android Studio 3 in .gitignore file.
.idea/caches
.idea/modules.xml
# Comment next line if keeping position of elements in Navigation Editor is relevant for you
.idea/navEditor.xml
# Keystore files
# Uncomment the following lines if you do not want to check your keystore files in.
#*.jks
#*.keystore
# External native build folder generated in Android Studio 2.2 and later
.externalNativeBuild
.cxx/
# Google Services (e.g. APIs or Firebase)
google-services.json
.DS_Store
# Freeline
freeline.py
freeline/
freeline_project_description.json
# fastlane
fastlane/report.xml
fastlane/Preview.html
fastlane/screenshots
fastlane/test_output
fastlane/readme.md
# Version control
vcs.xml
# lint
lint/intermediates/
lint/generated/
lint/outputs/
lint/tmp/
# lint/reports/
# Android Profiling
*.hprof
### Android Patch ###
gen-external-apklibs
output.json
keystore.properties
Instant-Weather-key
buildSrc/build
buildSrc/.gradle
# Replacement of .externalNativeBuild directories introduced
# with Android Studio 3.5.
# End of https://www.toptal.com/developers/gitignore/api/android

View File

@@ -83,11 +83,9 @@ android {
}
}
android {
sourceSets {
getByName("test").java.srcDir("src/sharedTest/java")
getByName("androidTest").java.srcDir("src/sharedTest/java")
}
sourceSets {
getByName("test").java.srcDir("src/sharedTest/java")
getByName("androidTest").java.srcDir("src/sharedTest/java")
}
hilt {
@@ -107,11 +105,11 @@ android {
}
compileOptions {
sourceCompatibility(Config.javaVersion)
targetCompatibility(Config.javaVersion)
sourceCompatibility = Config.javaVersion
targetCompatibility = Config.javaVersion
}
tasks.withType().all {
tasks.withType<org.jetbrains.kotlin.gradle.tasks.KotlinCompile> {
kotlinOptions {
jvmTarget = Config.javaVersion.toString()
}
@@ -162,7 +160,7 @@ dependencies {
// Weather Image
implementation(Utils.weatherImage)
// CalenderView
// CalendarView
implementation(Utils.calendarView)
// Google Play Services

View File

@@ -6,8 +6,9 @@
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/>
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
<application
android:name="com.mayokunadeniyi.instantweather.InstantWeatherApplication"
android:name=".App"
android:allowBackup="true"
android:icon="@mipmap/instant_weather_new"
android:label="@string/app_name"
@@ -16,7 +17,8 @@
android:usesCleartextTraffic="true"
android:theme="@style/AppTheme"
tools:targetApi="m">
<activity android:name="com.mayokunadeniyi.instantweather.ui.MainActivity"
<activity android:name=".ui.MainActivity"
android:theme="@style/SplashScreenTheme">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
@@ -24,10 +26,12 @@
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<provider
android:name="androidx.work.impl.WorkManagerInitializer"
android:authorities="${applicationId}.workmanager-init"
tools:node="remove" />
</application>
</manifest>

View File

@@ -0,0 +1,67 @@
// App.kt
override fun onCreate() {
super.onCreate()
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
val deferredComponentInitializer = DeferredComponentInitializer(this)
deferredComponentInitializer.initialize()
} else {
initializeComponents()
}
}
private fun initializeComponents() {
initWorkManager()
initCrashlytics()
initAnalytics()
}
// DeferredComponentInitializer.kt
class DeferredComponentInitializer(private val app: Application) {
fun initialize() {
val componentInitializer = ComponentInitializer(app)
val initializeMessage = when {
isColdStart() -> "Deferred initialization from cold start"
else -> "Deferred initialization from warm start"
}
WorkManager.getInstance(app)
.beginUniqueWork(
"DeferredInitialization",
ExistingWorkPolicy.KEEP,
OneTimeWorkRequestBuilder<DeferredWorker>()
.setInputData(workDataOf(DeferredWorker.KEY_INITIALIZE to initializeMessage))
.build()
)
.enqueue()
}
private fun isColdStart(): Boolean {
return ProcessLifecycleOwner.get().lifecycle.currentState == Lifecycle.State.INITIALIZED
}
private class DeferredWorker(
context: Context,
workerParams: WorkerParameters
) : Worker(context, workerParams) {
override fun doWork(): Result {
val initializeMessage = inputData.getString(KEY_INITIALIZE)
initializeMessage?.let {
Log.d("DeferredInit", it)
}
ComponentInitializer(applicationContext).initialize()
return Result.success()
}
companion object {
const val KEY_INITIALIZE = "KEY_INITIALIZE"
}
}
private class ComponentInitializer(private val app: Application) {
fun initialize() {
initCrashlytics()
initAnalytics()
}
}
}

View File

@@ -0,0 +1,63 @@
package com.mayokunadeniyi.instantweather.initializers
import android.app.Application
import android.content.Context
import android.os.Build
import android.util.Log
import androidx.lifecycle.Lifecycle
import androidx.lifecycle.ProcessLifecycleOwner
import androidx.work.ExistingWorkPolicy
import androidx.work.OneTimeWorkRequestBuilder
import androidx.work.WorkManager
import androidx.work.Worker
import androidx.work.WorkerParameters
import androidx.work.workDataOf
class DeferredComponentInitializer(private val app: Application) {
fun initialize() {
val componentInitializer = ComponentInitializer(app)
val initializeMessage = when {
isColdStart() -> "Deferred initialization from cold start"
else -> "Deferred initialization from warm start"
}
WorkManager.getInstance(app)
.beginUniqueWork(
"DeferredInitialization",
ExistingWorkPolicy.KEEP,
OneTimeWorkRequestBuilder<DeferredWorker>()
.setInputData(workDataOf(DeferredWorker.KEY_INITIALIZE to initializeMessage))
.build()
)
.enqueue()
}
private fun isColdStart(): Boolean {
return ProcessLifecycleOwner.get().lifecycle.currentState == Lifecycle.State.INITIALIZED
}
private class DeferredWorker(
context: Context,
workerParams: WorkerParameters
) : Worker(context, workerParams) {
override fun doWork(): Result {
val initializeMessage = inputData.getString(KEY_INITIALIZE)
initializeMessage?.let {
Log.d("DeferredInit", it)
}
ComponentInitializer(applicationContext).initialize()
return Result.success()
}
companion object {
const val KEY_INITIALIZE = "KEY_INITIALIZE"
}
}
private class ComponentInitializer(private val app: Application) {
fun initialize() {
initCrashlytics()
initAnalytics()
}
}
}

View File

@@ -21,3 +21,6 @@ android.enableJetifier=true
kotlin.code.style=official
#Enable incremental annotation processing
kapt.incremental.apt=true
# m1 chip support
org.gradle.jvmargs=-Xmx1536M -XX:MaxMetaspaceSize=512m -XX:+UseG1GC -Dfile.encoding=UTF-8 -Dapple.awt.UIElement=true