- Code bereinigt
- MapView in MapSegment ausgelagert
This commit is contained in:
@@ -20,14 +20,6 @@ class MainActivity : ComponentActivity() {
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
|
||||
viewModel = AlbumViewModel(coroutineContext = Dispatchers.Default)
|
||||
|
||||
/*
|
||||
Wird gebraucht um die Karte in ArcGIS anzuzeigen. Die Prüfung ob man Zugang hat oder nicht
|
||||
wurde gelöscht.
|
||||
*/
|
||||
ArcGISEnvironment.apiKey = ApiKey.create(BuildConfig.ARCGIS_TOKEN)
|
||||
enableEdgeToEdge()
|
||||
|
||||
setContent {
|
||||
|
||||
@@ -18,6 +18,7 @@ import androidx.compose.foundation.verticalScroll
|
||||
import androidx.compose.material.icons.Icons
|
||||
import androidx.compose.material.icons.filled.Add
|
||||
import androidx.compose.material.icons.filled.FilterAlt
|
||||
import androidx.compose.material.icons.filled.FormatListNumbered
|
||||
import androidx.compose.material.icons.filled.Menu
|
||||
import androidx.compose.material3.*
|
||||
import androidx.compose.runtime.*
|
||||
@@ -44,9 +45,8 @@ import kotlinx.coroutines.Dispatchers
|
||||
fun MainScreen(modifier: Modifier = Modifier, application: Application) {
|
||||
var showReport by rememberSaveable { mutableStateOf(false) }
|
||||
var sliderOpen by remember { mutableStateOf(false) }
|
||||
|
||||
// ViewModel Initialisierung
|
||||
val mapViewModel = remember { MapViewModel(application) }
|
||||
val albumViewModel = remember { AlbumViewModel(Dispatchers.Default) }
|
||||
|
||||
Scaffold(
|
||||
modifier = Modifier.fillMaxSize(),
|
||||
@@ -63,19 +63,26 @@ fun MainScreen(modifier: Modifier = Modifier, application: Application) {
|
||||
},
|
||||
floatingActionButton = {
|
||||
LargeFloatingActionButton(
|
||||
onClick = { showReport = true; sliderOpen = false },
|
||||
onClick = {
|
||||
showReport = true
|
||||
sliderOpen = false
|
||||
},
|
||||
modifier = Modifier.offset(y = 64.dp),
|
||||
containerColor = ButtonColor
|
||||
) { Icon(Icons.Default.Add, contentDescription = "Add") }
|
||||
) {
|
||||
Icon(Icons.Default.Add, contentDescription = "Add")
|
||||
}
|
||||
},
|
||||
floatingActionButtonPosition = FabPosition.Center,
|
||||
) { innerPadding ->
|
||||
ContentScreen(
|
||||
modifier = Modifier.padding(innerPadding),
|
||||
mapViewModel = mapViewModel,
|
||||
mapViewModel,
|
||||
albumViewModel,
|
||||
showReport = showReport,
|
||||
sliderOpen = sliderOpen,
|
||||
onDismissReport = { showReport = false })
|
||||
onDismissReport = { showReport = false }
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -83,26 +90,20 @@ fun MainScreen(modifier: Modifier = Modifier, application: Application) {
|
||||
fun ContentScreen(
|
||||
modifier: Modifier = Modifier,
|
||||
mapViewModel: MapViewModel,
|
||||
albumViewModel: AlbumViewModel,
|
||||
showReport: Boolean,
|
||||
sliderOpen: Boolean,
|
||||
onDismissReport: () -> Unit
|
||||
) {
|
||||
val albumViewModel = remember { AlbumViewModel(Dispatchers.Default) }
|
||||
val locationDisplay = setupLocationDisplay()
|
||||
|
||||
// VERBINDUNG ZUM VIEWMODEL (Hier wird das GPS-Werkzeug übergeben)
|
||||
LaunchedEffect(locationDisplay) {
|
||||
mapViewModel.locationDisplay = locationDisplay
|
||||
}
|
||||
|
||||
Box(modifier = modifier.fillMaxSize()) {
|
||||
MapView(
|
||||
// HINTERGRUND: Die Map
|
||||
MapSegment(
|
||||
modifier = Modifier.fillMaxSize(),
|
||||
arcGISMap = mapViewModel.map,
|
||||
mapViewProxy = mapViewModel.mapViewProxy,
|
||||
locationDisplay = locationDisplay
|
||||
mapViewModel = mapViewModel,
|
||||
)
|
||||
|
||||
// VORDERGRUND: Das Overlay (wenn showReport = true)
|
||||
if (showReport) {
|
||||
ReportOverlay(
|
||||
onCancel = onDismissReport,
|
||||
@@ -118,18 +119,29 @@ fun ContentScreen(
|
||||
)
|
||||
}
|
||||
|
||||
// Slider von Links
|
||||
SideSlider(visible = sliderOpen) {
|
||||
SliderMenuItem(text = "Schäden filtern", icon = Icons.Default.FilterAlt, onClick = {})
|
||||
}
|
||||
Text(
|
||||
"Menü",
|
||||
style = MaterialTheme.typography.titleMedium,
|
||||
modifier = Modifier.padding(bottom = 12.dp)
|
||||
)
|
||||
|
||||
if (mapViewModel.snackBarMessage.isNotEmpty()) {
|
||||
Snackbar(modifier = Modifier.align(Alignment.BottomCenter).padding(bottom = 80.dp)) {
|
||||
Text(mapViewModel.snackBarMessage)
|
||||
}
|
||||
LaunchedEffect(mapViewModel.snackBarMessage) {
|
||||
kotlinx.coroutines.delay(4000)
|
||||
mapViewModel.snackBarMessage = ""
|
||||
}
|
||||
SliderMenuItem(
|
||||
text = "Schäden filtern",
|
||||
icon = Icons.Default.FilterAlt,
|
||||
onClick = {
|
||||
/* TODO */
|
||||
}
|
||||
)
|
||||
|
||||
SliderMenuItem(
|
||||
text = "Schadensliste",
|
||||
icon = Icons.Default.FormatListNumbered,
|
||||
onClick = {
|
||||
/* TODO */
|
||||
}
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -350,9 +362,3 @@ fun ReportOverlay(
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun createMap(): ArcGISMap {
|
||||
return ArcGISMap(BasemapStyle.ArcGISTopographic).apply {
|
||||
initialViewpoint = Viewpoint(53.14, 8.20, 20000.0)
|
||||
}
|
||||
}
|
||||
122
app/src/main/java/com/example/snapandsolve/MapSegment.kt
Normal file
122
app/src/main/java/com/example/snapandsolve/MapSegment.kt
Normal file
@@ -0,0 +1,122 @@
|
||||
package com.example.snapandsolve
|
||||
|
||||
import MapViewModel
|
||||
import android.Manifest
|
||||
import android.content.Context
|
||||
import android.content.pm.PackageManager
|
||||
import android.widget.Toast
|
||||
import androidx.activity.compose.rememberLauncherForActivityResult
|
||||
import androidx.activity.result.contract.ActivityResultContracts
|
||||
import androidx.compose.foundation.layout.Column
|
||||
import androidx.compose.foundation.layout.fillMaxSize
|
||||
import androidx.compose.material3.SnackbarHostState
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.LaunchedEffect
|
||||
import androidx.compose.runtime.remember
|
||||
import androidx.compose.runtime.rememberCoroutineScope
|
||||
import androidx.compose.ui.Alignment
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.platform.LocalContext
|
||||
import androidx.core.content.ContextCompat
|
||||
import com.arcgismaps.ApiKey
|
||||
import com.arcgismaps.ArcGISEnvironment
|
||||
import com.arcgismaps.location.LocationDisplayAutoPanMode
|
||||
import com.arcgismaps.toolkit.geoviewcompose.MapView
|
||||
import com.arcgismaps.toolkit.geoviewcompose.rememberLocationDisplay
|
||||
import kotlinx.coroutines.launch
|
||||
|
||||
@Composable
|
||||
fun MapSegment(
|
||||
modifier: Modifier = Modifier,
|
||||
mapViewModel: MapViewModel
|
||||
) {
|
||||
val context = LocalContext.current
|
||||
val coroutineScope = rememberCoroutineScope()
|
||||
|
||||
ArcGISEnvironment.applicationContext = context.applicationContext
|
||||
ArcGISEnvironment.apiKey = ApiKey.create(BuildConfig.ARCGIS_TOKEN)
|
||||
|
||||
// val snackbarHostState = remember { SnackbarHostState() }
|
||||
|
||||
val locationDisplay = rememberLocationDisplay().apply {
|
||||
setAutoPanMode(LocationDisplayAutoPanMode.Off)
|
||||
}
|
||||
|
||||
if (checkPermissions(context)) {
|
||||
// Permissions are already granted.
|
||||
LaunchedEffect(Unit) {
|
||||
locationDisplay.dataSource.start()
|
||||
}
|
||||
} else {
|
||||
RequestPermissions(
|
||||
context = context,
|
||||
onPermissionsGranted = {
|
||||
coroutineScope.launch {
|
||||
locationDisplay.dataSource.start()
|
||||
}
|
||||
}
|
||||
)
|
||||
}
|
||||
|
||||
Column(
|
||||
modifier = modifier
|
||||
.fillMaxSize(),
|
||||
horizontalAlignment = Alignment.CenterHorizontally,
|
||||
) {
|
||||
MapView(
|
||||
modifier = Modifier.weight(90f),
|
||||
arcGISMap = mapViewModel.map,
|
||||
locationDisplay = locationDisplay,
|
||||
mapViewProxy = mapViewModel.mapViewProxy,
|
||||
onSingleTapConfirmed = {}//mapViewModel::onTap,
|
||||
) {
|
||||
/* TODO */
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun checkPermissions(context: Context): Boolean {
|
||||
// Check permissions to see if both permissions are granted.
|
||||
// Coarse location permission.
|
||||
val permissionCheckCoarseLocation = ContextCompat.checkSelfPermission(
|
||||
context,
|
||||
Manifest.permission.ACCESS_COARSE_LOCATION
|
||||
) == PackageManager.PERMISSION_GRANTED
|
||||
// Fine location permission.
|
||||
val permissionCheckFineLocation = ContextCompat.checkSelfPermission(
|
||||
context,
|
||||
Manifest.permission.ACCESS_FINE_LOCATION
|
||||
) == PackageManager.PERMISSION_GRANTED
|
||||
|
||||
return permissionCheckCoarseLocation && permissionCheckFineLocation
|
||||
}
|
||||
|
||||
fun showError(context: Context, message: String) {
|
||||
Toast.makeText(context, message, Toast.LENGTH_LONG).show()
|
||||
}
|
||||
|
||||
@Composable
|
||||
fun RequestPermissions(context: Context, onPermissionsGranted: () -> Unit) {
|
||||
|
||||
// Create an activity result launcher using permissions contract and handle the result.
|
||||
val activityResultLauncher = rememberLauncherForActivityResult(
|
||||
ActivityResultContracts.RequestMultiplePermissions()
|
||||
) { permissions ->
|
||||
// Check if both fine & coarse location permissions are true.
|
||||
if (permissions.all { it.value }) {
|
||||
onPermissionsGranted()
|
||||
} else {
|
||||
showError(context, "Location permissions were denied")
|
||||
}
|
||||
}
|
||||
|
||||
LaunchedEffect(Unit) {
|
||||
activityResultLauncher.launch(
|
||||
// Request both fine and coarse location permissions.
|
||||
arrayOf(
|
||||
Manifest.permission.ACCESS_COARSE_LOCATION,
|
||||
Manifest.permission.ACCESS_FINE_LOCATION
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user