Skip and docs
30
pedi-foods/Android/app/src/main/AndroidManifest.xml
Normal file
@@ -0,0 +1,30 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!-- This AndroidManifest.xml template was generated by Skip -->
|
||||
<manifest xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools">
|
||||
<!-- example permissions for using device location -->
|
||||
<!-- <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/> -->
|
||||
<!-- <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/> -->
|
||||
|
||||
<!-- permissions needed for using the internet or an embedded WebKit browser -->
|
||||
<uses-permission android:name="android.permission.INTERNET" />
|
||||
<!-- <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> -->
|
||||
|
||||
<application
|
||||
android:label="${PRODUCT_NAME}"
|
||||
android:name=".AndroidAppMain"
|
||||
android:supportsRtl="true"
|
||||
android:allowBackup="true"
|
||||
android:icon="@mipmap/ic_launcher">
|
||||
<activity
|
||||
android:name=".MainActivity"
|
||||
android:exported="true"
|
||||
android:configChanges="orientation|screenSize|screenLayout|keyboardHidden|mnc|colorMode|density|fontScale|fontWeightAdjustment|keyboard|layoutDirection|locale|mcc|navigation|smallestScreenSize|touchscreen|uiMode"
|
||||
android:theme="@style/Theme.AppCompat.DayNight.NoActionBar"
|
||||
android:windowSoftInputMode="adjustResize">
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.MAIN" />
|
||||
<category android:name="android.intent.category.LAUNCHER" />
|
||||
</intent-filter>
|
||||
</activity>
|
||||
</application>
|
||||
</manifest>
|
||||
167
pedi-foods/Android/app/src/main/kotlin/Main.kt
Normal file
@@ -0,0 +1,167 @@
|
||||
package pedi.foods
|
||||
|
||||
import skip.lib.*
|
||||
import skip.model.*
|
||||
import skip.foundation.*
|
||||
import skip.ui.*
|
||||
|
||||
import android.Manifest
|
||||
import android.app.Application
|
||||
import android.graphics.Color as AndroidColor
|
||||
import androidx.activity.compose.setContent
|
||||
import androidx.activity.enableEdgeToEdge
|
||||
import androidx.activity.SystemBarStyle
|
||||
import androidx.activity.ComponentActivity
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import androidx.compose.foundation.isSystemInDarkTheme
|
||||
import androidx.compose.foundation.layout.fillMaxSize
|
||||
import androidx.compose.foundation.layout.Box
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.DisposableEffect
|
||||
import androidx.compose.runtime.SideEffect
|
||||
import androidx.compose.runtime.saveable.rememberSaveableStateHolder
|
||||
import androidx.compose.ui.Alignment
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.graphics.luminance
|
||||
import androidx.compose.ui.platform.LocalContext
|
||||
import androidx.compose.material3.MaterialTheme
|
||||
import androidx.core.app.ActivityCompat
|
||||
|
||||
internal val logger: SkipLogger = SkipLogger(subsystem = "pedi.foods", category = "PediFoods")
|
||||
|
||||
private typealias AppRootView = PediFoodsRootView
|
||||
private typealias AppDelegate = PediFoodsAppDelegate
|
||||
|
||||
/// AndroidAppMain is the `android.app.Application` entry point, and must match `application android:name` in the AndroidMainfest.xml file.
|
||||
open class AndroidAppMain: Application {
|
||||
constructor() {
|
||||
}
|
||||
|
||||
override fun onCreate() {
|
||||
super.onCreate()
|
||||
logger.info("starting app")
|
||||
ProcessInfo.launch(applicationContext)
|
||||
AppDelegate.shared.onInit()
|
||||
}
|
||||
|
||||
companion object {
|
||||
}
|
||||
}
|
||||
|
||||
/// AndroidAppMain is initial `androidx.appcompat.app.AppCompatActivity`, and must match `activity android:name` in the AndroidMainfest.xml file.
|
||||
open class MainActivity: AppCompatActivity {
|
||||
constructor() {
|
||||
}
|
||||
|
||||
override fun onCreate(savedInstanceState: android.os.Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
logger.info("starting activity")
|
||||
UIApplication.launch(this)
|
||||
enableEdgeToEdge()
|
||||
|
||||
setContent {
|
||||
val saveableStateHolder = rememberSaveableStateHolder()
|
||||
saveableStateHolder.SaveableStateProvider(true) {
|
||||
PresentationRootView(ComposeContext())
|
||||
SideEffect { saveableStateHolder.removeState(true) }
|
||||
}
|
||||
}
|
||||
|
||||
AppDelegate.shared.onLaunch()
|
||||
|
||||
// Example of requesting permissions on startup.
|
||||
// These must match the permissions in the AndroidManifest.xml file.
|
||||
//let permissions = listOf(
|
||||
// Manifest.permission.ACCESS_COARSE_LOCATION,
|
||||
// Manifest.permission.ACCESS_FINE_LOCATION
|
||||
// Manifest.permission.CAMERA,
|
||||
// Manifest.permission.WRITE_EXTERNAL_STORAGE,
|
||||
//)
|
||||
//let requestTag = 1
|
||||
//ActivityCompat.requestPermissions(self, permissions.toTypedArray(), requestTag)
|
||||
}
|
||||
|
||||
override fun onStart() {
|
||||
logger.info("onStart")
|
||||
super.onStart()
|
||||
}
|
||||
|
||||
override fun onResume() {
|
||||
super.onResume()
|
||||
AppDelegate.shared.onResume()
|
||||
}
|
||||
|
||||
override fun onPause() {
|
||||
super.onPause()
|
||||
AppDelegate.shared.onPause()
|
||||
}
|
||||
|
||||
override fun onStop() {
|
||||
super.onStop()
|
||||
AppDelegate.shared.onStop()
|
||||
}
|
||||
|
||||
override fun onDestroy() {
|
||||
super.onDestroy()
|
||||
AppDelegate.shared.onDestroy()
|
||||
}
|
||||
|
||||
override fun onLowMemory() {
|
||||
super.onLowMemory()
|
||||
AppDelegate.shared.onLowMemory()
|
||||
}
|
||||
|
||||
override fun onRestart() {
|
||||
logger.info("onRestart")
|
||||
super.onRestart()
|
||||
}
|
||||
|
||||
override fun onSaveInstanceState(outState: android.os.Bundle): Unit = super.onSaveInstanceState(outState)
|
||||
|
||||
override fun onRestoreInstanceState(bundle: android.os.Bundle) {
|
||||
// Usually you restore your state in onCreate(). It is possible to restore it in onRestoreInstanceState() as well, but not very common. (onRestoreInstanceState() is called after onStart(), whereas onCreate() is called before onStart().
|
||||
logger.info("onRestoreInstanceState")
|
||||
super.onRestoreInstanceState(bundle)
|
||||
}
|
||||
|
||||
override fun onRequestPermissionsResult(requestCode: Int, permissions: kotlin.Array<String>, grantResults: IntArray) {
|
||||
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
|
||||
logger.info("onRequestPermissionsResult: ${requestCode}")
|
||||
}
|
||||
|
||||
companion object {
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
internal fun SyncSystemBarsWithTheme() {
|
||||
val dark = MaterialTheme.colorScheme.background.luminance() < 0.5f
|
||||
|
||||
val transparent = AndroidColor.TRANSPARENT
|
||||
val style = if (dark) {
|
||||
SystemBarStyle.dark(transparent)
|
||||
} else {
|
||||
SystemBarStyle.light(transparent, transparent)
|
||||
}
|
||||
|
||||
val activity = LocalContext.current as? ComponentActivity
|
||||
DisposableEffect(style) {
|
||||
activity?.enableEdgeToEdge(
|
||||
statusBarStyle = style,
|
||||
navigationBarStyle = style
|
||||
)
|
||||
onDispose { }
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
internal fun PresentationRootView(context: ComposeContext) {
|
||||
val colorScheme = if (isSystemInDarkTheme()) ColorScheme.dark else ColorScheme.light
|
||||
PresentationRoot(defaultColorScheme = colorScheme, context = context) { ctx ->
|
||||
SyncSystemBarsWithTheme()
|
||||
val contentContext = ctx.content()
|
||||
Box(modifier = ctx.modifier.fillMaxSize(), contentAlignment = Alignment.Center) {
|
||||
AppRootView().Compose(context = contentContext)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<background android:drawable="@mipmap/ic_launcher_background" />
|
||||
<foreground android:drawable="@mipmap/ic_launcher_foreground" />
|
||||
<monochrome android:drawable="@mipmap/ic_launcher_monochrome" />
|
||||
</adaptive-icon>
|
||||
BIN
pedi-foods/Android/app/src/main/res/mipmap-hdpi/ic_launcher.png
Normal file
|
After Width: | Height: | Size: 5.6 KiB |
|
After Width: | Height: | Size: 4.5 KiB |
|
After Width: | Height: | Size: 1.6 KiB |
|
After Width: | Height: | Size: 1.6 KiB |
BIN
pedi-foods/Android/app/src/main/res/mipmap-mdpi/ic_launcher.png
Normal file
|
After Width: | Height: | Size: 2.7 KiB |
|
After Width: | Height: | Size: 2.1 KiB |
|
After Width: | Height: | Size: 565 B |
|
After Width: | Height: | Size: 565 B |
BIN
pedi-foods/Android/app/src/main/res/mipmap-xhdpi/ic_launcher.png
Normal file
|
After Width: | Height: | Size: 7.8 KiB |
|
After Width: | Height: | Size: 6.3 KiB |
|
After Width: | Height: | Size: 1.1 KiB |
|
After Width: | Height: | Size: 1.1 KiB |
|
After Width: | Height: | Size: 14 KiB |
|
After Width: | Height: | Size: 10 KiB |
|
After Width: | Height: | Size: 2.0 KiB |
|
After Width: | Height: | Size: 2.0 KiB |
|
After Width: | Height: | Size: 22 KiB |
|
After Width: | Height: | Size: 15 KiB |
|
After Width: | Height: | Size: 3.4 KiB |
|
After Width: | Height: | Size: 3.4 KiB |