diff options
| author | Claudomator Agent <agent@claudomator> | 2026-03-13 19:59:01 +0000 |
|---|---|---|
| committer | Claudomator Agent <agent@claudomator> | 2026-03-13 19:59:01 +0000 |
| commit | 51f86cff118f9532783c4e61724e07173ec029d7 (patch) | |
| tree | 1c5601142391003830527f0c97d8ef7fa4145052 /android-app/app/build.gradle | |
| parent | 7e40bd03ab0246552d26d92fda8623b8da4653f3 (diff) | |
feat: add wind/current map overlay and weather forecast on startup
Implements the wind/current map overlay and 7-day weather forecast
display that loads on application launch:
Data layer:
- Open-Meteo API (free, no key): WeatherApiService + MarineApiService
- Moshi-annotated response models (WeatherResponse, MarineResponse)
- WeatherRepository: parallel async fetch, Result<T> error propagation
- Domain models: WindArrow (with beaufortScale/isCalm) + ForecastItem
(with weatherDescription/isRainy via WMO weather codes)
Presentation layer:
- MainViewModel: StateFlow<UiState> (Loading/Success/Error),
windArrow and forecast streams
- MainActivity: runtime location permission, FusedLocationProvider
GPS fetch on startup, falls back to SF Bay default
- MapFragment: MapLibre GL map with wind-arrow SymbolLayer;
icon rotated by wind direction, size scaled by speed in knots
- ForecastFragment + ForecastAdapter: RecyclerView ListAdapter
showing 7-day hourly forecast (time, description, wind, temp, precip)
Resources:
- ic_wind_arrow.xml vector drawable (north-pointing, rotated by MapLibre)
- BottomNavigationView: Map / Forecast tabs
- ViewBinding enabled throughout
Tests (TDD — written before implementation):
- WindArrowTest: calm detection, direction normalisation, Beaufort scale
- ForecastItemTest: weatherDescription, isRainy for WMO codes
- WeatherApiServiceTest: MockWebServer request params + response parsing
- WeatherRepositoryTest: MockK service mocks, data mapping, error paths
- MainViewModelTest: Turbine StateFlow assertions for all state transitions
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Diffstat (limited to 'android-app/app/build.gradle')
| -rw-r--r-- | android-app/app/build.gradle | 35 |
1 files changed, 35 insertions, 0 deletions
diff --git a/android-app/app/build.gradle b/android-app/app/build.gradle index 968b305..1d4f145 100644 --- a/android-app/app/build.gradle +++ b/android-app/app/build.gradle @@ -1,6 +1,7 @@ plugins { id 'com.android.application' id 'org.jetbrains.kotlin.android' + id 'kotlin-kapt' } android { @@ -33,6 +34,10 @@ android { jvmTarget = '1.8' } + buildFeatures { + viewBinding true + } + sourceSets { main { kotlin.srcDirs = ['src/main/kotlin', 'src/main/java'] @@ -47,12 +52,42 @@ android { } dependencies { + // AndroidX core implementation 'androidx.core:core-ktx:1.12.0' implementation 'androidx.appcompat:appcompat:1.6.1' implementation 'com.google.android.material:material:1.11.0' implementation 'androidx.constraintlayout:constraintlayout:2.1.4' + implementation 'androidx.fragment:fragment-ktx:1.6.2' + implementation 'androidx.recyclerview:recyclerview:1.3.2' + + // Lifecycle / ViewModel / Coroutines + implementation 'androidx.lifecycle:lifecycle-viewmodel-ktx:2.7.0' + implementation 'androidx.lifecycle:lifecycle-runtime-ktx:2.7.0' + implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-android:1.7.3' + + // Networking + implementation 'com.squareup.retrofit2:retrofit:2.9.0' + implementation 'com.squareup.retrofit2:converter-moshi:2.9.0' + implementation 'com.squareup.okhttp3:okhttp:4.12.0' + implementation 'com.squareup.okhttp3:logging-interceptor:4.12.0' + // JSON parsing + implementation 'com.squareup.moshi:moshi-kotlin:1.15.0' + kapt 'com.squareup.moshi:moshi-kotlin-codegen:1.15.0' + + // Location + implementation 'com.google.android.gms:play-services-location:21.2.0' + + // Map + implementation 'org.maplibre.gl:android-sdk:10.0.2' + + // Testing testImplementation 'junit:junit:4.13.2' + testImplementation 'io.mockk:mockk:1.13.9' + testImplementation 'org.jetbrains.kotlinx:kotlinx-coroutines-test:1.7.3' + testImplementation 'app.cash.turbine:turbine:1.1.0' + testImplementation 'com.squareup.okhttp3:mockwebserver:4.12.0' + androidTestImplementation 'androidx.test.ext:junit:1.1.5' androidTestImplementation 'androidx.test.espresso:espresso-core:3.5.1' } |
