diff --git a/ai/sample/core-proto/build.gradle.kts b/ai/sample/core-proto/build.gradle.kts new file mode 100644 index 0000000000..d7afeacab4 --- /dev/null +++ b/ai/sample/core-proto/build.gradle.kts @@ -0,0 +1,69 @@ +/* + * Copyright 2026 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +plugins { + id("java-library") + id("com.google.protobuf") +} + +java { + sourceCompatibility = JavaVersion.VERSION_17 + targetCompatibility = JavaVersion.VERSION_17 +} + +protobuf { + protoc { + artifact = libs.protobuf.protoc.stnd.get().toString() + } + plugins { + create("javalite") { + artifact = libs.protobuf.protoc.gen.javalite.get().toString() + } + create("grpc") { + artifact = libs.protobuf.protoc.gen.grpc.java.get().toString() + } + create("grpckt") { + artifact = libs.protobuf.protoc.gen.grpc.kotlin.get().toString() + } + } + generateProtoTasks { + all().forEach { task -> + task.builtins { + named("java") { + option("lite") + } + create("kotlin") { + option("lite") + } + } + task.plugins { + create("grpc") { + option("lite") + } + create("grpckt") { + option("lite") + } + } + } + } +} + +dependencies { + api(libs.protobuf.kotlin.lite) + api(libs.io.grpc.protobuf.lite) + api(libs.io.grpc.grpc.kotlin) + api(libs.grpc.stub) +} diff --git a/ai/sample/core/src/main/proto/ai.proto b/ai/sample/core-proto/src/main/proto/ai.proto similarity index 100% rename from ai/sample/core/src/main/proto/ai.proto rename to ai/sample/core-proto/src/main/proto/ai.proto diff --git a/ai/sample/core/build.gradle.kts b/ai/sample/core/build.gradle.kts index 7433f637c1..103f26971f 100644 --- a/ai/sample/core/build.gradle.kts +++ b/ai/sample/core/build.gradle.kts @@ -16,8 +16,7 @@ plugins { id("com.android.library") - id("com.google.protobuf") - kotlin("android") + id("com.google.devtools.ksp") id("dagger.hilt.android.plugin") } @@ -40,14 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlin.RequiresOptIn", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } packaging { resources { excludes += @@ -72,45 +63,9 @@ android { namespace = "com.google.android.horologist.ai.sample.core" } -protobuf { - protoc { - artifact = libs.protobuf.protoc.stnd.get().toString() - } - plugins { - create("javalite") { - artifact = libs.protobuf.protoc.gen.javalite.get().toString() - } - create("grpc") { - artifact = libs.protobuf.protoc.gen.grpc.java.get().toString() - } - create("grpckt") { - artifact = libs.protobuf.protoc.gen.grpc.kotlin.get().toString() - } - } - generateProtoTasks { - all().forEach { task -> - task.builtins { - create("java") { - option("lite") - } - create("kotlin") { - option("lite") - } - } - task.plugins { - create("grpc") { - option("lite") - } - create("grpckt") { - option("lite") - } - } - } - } -} - dependencies { api(projects.annotations) + api(projects.ai.sample.coreProto) implementation(libs.dagger.hiltandroid) implementation(projects.datalayer.core) diff --git a/ai/sample/phone/build.gradle.kts b/ai/sample/phone/build.gradle.kts index 064e6db8b4..f691713d88 100644 --- a/ai/sample/phone/build.gradle.kts +++ b/ai/sample/phone/build.gradle.kts @@ -16,7 +16,6 @@ plugins { id("com.android.application") - kotlin("android") id("com.google.devtools.ksp") id("dagger.hilt.android.plugin") kotlin("plugin.serialization") @@ -61,16 +60,6 @@ android { targetCompatibility = JavaVersion.VERSION_17 } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += diff --git a/ai/sample/wear-core/build.gradle.kts b/ai/sample/wear-core/build.gradle.kts index 5acdf89446..14b9a2c306 100644 --- a/ai/sample/wear-core/build.gradle.kts +++ b/ai/sample/wear-core/build.gradle.kts @@ -16,7 +16,6 @@ plugins { id("com.android.library") - kotlin("android") id("com.google.devtools.ksp") id("dagger.hilt.android.plugin") } @@ -39,14 +38,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlin.RequiresOptIn", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } packaging { resources { excludes += diff --git a/ai/sample/wear-gemini-lib/build.gradle.kts b/ai/sample/wear-gemini-lib/build.gradle.kts index 1e5a20dbdb..62b5be9c0a 100644 --- a/ai/sample/wear-gemini-lib/build.gradle.kts +++ b/ai/sample/wear-gemini-lib/build.gradle.kts @@ -34,7 +34,6 @@ import java.util.Properties plugins { id("com.android.library") - kotlin("android") id("org.jetbrains.kotlin.plugin.serialization") } @@ -68,7 +67,13 @@ android { buildConfigField( "String", "GEMINI_PROXY", - if (localProperties.containsKey("gemini.apk.proxy")) "\"" + localProperties["gemini.apk.proxy"] + "\"" else "null", + if (localProperties.containsKey("gemini.apk.proxy")) { + "\"" + + localProperties["gemini.apk.proxy"] + + "\"" + } else { + "null" + }, ) } @@ -81,16 +86,6 @@ android { buildConfig = true } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - testOptions { unitTests { isIncludeAndroidResources = true diff --git a/ai/sample/wear-gemini/build.gradle.kts b/ai/sample/wear-gemini/build.gradle.kts index 22826459b5..b96d10dc1f 100644 --- a/ai/sample/wear-gemini/build.gradle.kts +++ b/ai/sample/wear-gemini/build.gradle.kts @@ -34,7 +34,6 @@ import java.util.Properties plugins { id("com.android.application") - kotlin("android") id("com.google.devtools.ksp") id("dagger.hilt.android.plugin") id("org.jetbrains.kotlin.plugin.serialization") @@ -87,16 +86,6 @@ android { buildConfig = true } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - testOptions { unitTests { isIncludeAndroidResources = true diff --git a/ai/sample/wear-prompt-app/build.gradle.kts b/ai/sample/wear-prompt-app/build.gradle.kts index 6c23e316ce..fe65b70812 100644 --- a/ai/sample/wear-prompt-app/build.gradle.kts +++ b/ai/sample/wear-prompt-app/build.gradle.kts @@ -16,7 +16,6 @@ plugins { id("com.android.application") - kotlin("android") id("com.google.devtools.ksp") id("dagger.hilt.android.plugin") kotlin("plugin.serialization") @@ -64,16 +63,6 @@ android { buildConfig = true } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += diff --git a/ai/ui/build.gradle.kts b/ai/ui/build.gradle.kts index 6919ad91b4..f0f4c93eb1 100644 --- a/ai/ui/build.gradle.kts +++ b/ai/ui/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -41,12 +40,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=kotlin.RequiresOptIn" - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -116,12 +109,4 @@ dependencies { testImplementation(libs.truth) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("ai-ui") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/ai/ui/src/test/snapshots/images/com.google.android.horologist.ai.composables.components_PromptScreenTest_empty.png b/ai/ui/src/test/snapshots/images/com.google.android.horologist.ai.composables.components_PromptScreenTest_empty.png index 6c97537f40..558ff25058 100644 --- a/ai/ui/src/test/snapshots/images/com.google.android.horologist.ai.composables.components_PromptScreenTest_empty.png +++ b/ai/ui/src/test/snapshots/images/com.google.android.horologist.ai.composables.components_PromptScreenTest_empty.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:8a15ed8f30e968f65c063345b942da04bc3687eaf00222be63bbb36831287c71 -size 31178 +oid sha256:73608e6486519371e90d9daf486859080da42c9b08d58532d7b2d69311fed004 +size 31091 diff --git a/auth/composables-material3/build.gradle.kts b/auth/composables-material3/build.gradle.kts index 287ba812d8..b137c4c78b 100644 --- a/auth/composables-material3/build.gradle.kts +++ b/auth/composables-material3/build.gradle.kts @@ -19,7 +19,6 @@ plugins { alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) alias(libs.plugins.dependencyAnalysis) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -42,13 +41,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs += listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += @@ -130,12 +122,4 @@ dependencyAnalysis { } } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("auth-composables-material3") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/auth/composables-material3/src/main/java/com/google/android/horologist/auth/composables/material3/screens/SignedInConfirmationDialog.kt b/auth/composables-material3/src/main/java/com/google/android/horologist/auth/composables/material3/screens/SignedInConfirmationDialog.kt index cb1937d142..2bd07b2fb3 100644 --- a/auth/composables-material3/src/main/java/com/google/android/horologist/auth/composables/material3/screens/SignedInConfirmationDialog.kt +++ b/auth/composables-material3/src/main/java/com/google/android/horologist/auth/composables/material3/screens/SignedInConfirmationDialog.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -28,7 +28,6 @@ import androidx.compose.foundation.layout.size import androidx.compose.material.icons.Icons import androidx.compose.material.icons.filled.AccountCircle import androidx.compose.material.icons.outlined.AccountCircle -import androidx.compose.material3.ExperimentalMaterial3ExpressiveApi import androidx.compose.material3.Icon import androidx.compose.material3.MaterialShapes import androidx.compose.material3.toShape @@ -135,7 +134,6 @@ public fun SignedInConfirmationDialog( ) } -@OptIn(ExperimentalMaterial3ExpressiveApi::class) @Composable internal fun SignedInConfirmationDialogContent( modifier: Modifier = Modifier, @@ -197,7 +195,7 @@ internal fun SignedInConfirmationDialogContent( text = if (hasName) { stringResource( id = R.string.horologist_signedin_confirmation_greeting, - name!!, + name, ) } else { stringResource(id = R.string.horologist_signedin_confirmation_greeting_no_name) diff --git a/auth/composables-material3/src/test/snapshots/images/com.google.android.horologist.auth.composables.material3.screens_SelectAccountScreenTest_selectAccountScreen.png b/auth/composables-material3/src/test/snapshots/images/com.google.android.horologist.auth.composables.material3.screens_SelectAccountScreenTest_selectAccountScreen.png index 04ad1a35e0..62d6345e56 100644 --- a/auth/composables-material3/src/test/snapshots/images/com.google.android.horologist.auth.composables.material3.screens_SelectAccountScreenTest_selectAccountScreen.png +++ b/auth/composables-material3/src/test/snapshots/images/com.google.android.horologist.auth.composables.material3.screens_SelectAccountScreenTest_selectAccountScreen.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:d576fefee4f8a2d10c3adf986b8d991a2f09993fdb79c04441ebb2817dbc74fd -size 59473 +oid sha256:a551db0169d404613883effd586a5cf0177e3f3b2701eddcaf3b1d066a5b8a87 +size 59383 diff --git a/auth/composables-material3/src/test/snapshots/images/com.google.android.horologist.auth.composables.material3.screens_SelectAccountScreenTest_selectAccountScreenNoAvatar.png b/auth/composables-material3/src/test/snapshots/images/com.google.android.horologist.auth.composables.material3.screens_SelectAccountScreenTest_selectAccountScreenNoAvatar.png index 0e867e105f..42e788e064 100644 --- a/auth/composables-material3/src/test/snapshots/images/com.google.android.horologist.auth.composables.material3.screens_SelectAccountScreenTest_selectAccountScreenNoAvatar.png +++ b/auth/composables-material3/src/test/snapshots/images/com.google.android.horologist.auth.composables.material3.screens_SelectAccountScreenTest_selectAccountScreenNoAvatar.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:2ff5c3a1b86624a130a982a4a4df668f53f1c445ecdc50a4dc24a2bec4ad717b -size 42618 +oid sha256:3bdc887c67cc97b9e936f1fb068086cedfbd633612801ec9a292aec16694151d +size 42533 diff --git a/auth/composables/build.gradle.kts b/auth/composables/build.gradle.kts index 8537e76e71..c79dc0c19a 100644 --- a/auth/composables/build.gradle.kts +++ b/auth/composables/build.gradle.kts @@ -19,7 +19,6 @@ plugins { alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) alias(libs.plugins.dependencyAnalysis) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -42,13 +41,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs += listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += @@ -130,12 +122,4 @@ dependencyAnalysis { } } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("auth-composables") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/auth/composables/src/debug/java/com/google/android/horologist/auth/composables/screens/SelectAccountScreenPreview.kt b/auth/composables/src/debug/java/com/google/android/horologist/auth/composables/screens/SelectAccountScreenPreview.kt index e5eac0ba6e..424b0b1efe 100644 --- a/auth/composables/src/debug/java/com/google/android/horologist/auth/composables/screens/SelectAccountScreenPreview.kt +++ b/auth/composables/src/debug/java/com/google/android/horologist/auth/composables/screens/SelectAccountScreenPreview.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -14,6 +14,8 @@ * limitations under the License. */ +@file:Suppress("DEPRECATION") + package com.google.android.horologist.auth.composables.screens import androidx.compose.runtime.Composable diff --git a/auth/composables/src/main/java/com/google/android/horologist/auth/composables/dialogs/SignedInConfirmationDialog.kt b/auth/composables/src/main/java/com/google/android/horologist/auth/composables/dialogs/SignedInConfirmationDialog.kt index 7537dcc00b..8c430e8c07 100644 --- a/auth/composables/src/main/java/com/google/android/horologist/auth/composables/dialogs/SignedInConfirmationDialog.kt +++ b/auth/composables/src/main/java/com/google/android/horologist/auth/composables/dialogs/SignedInConfirmationDialog.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -140,7 +140,7 @@ internal fun SignedInConfirmationDialogContent( ) } else if (hasName) { Text( - text = name!!.first().uppercase(), + text = name.first().uppercase(), modifier = Modifier .align(Alignment.Center) .fillMaxWidth(), @@ -155,7 +155,7 @@ internal fun SignedInConfirmationDialogContent( text = if (hasName) { stringResource( id = R.string.horologist_signedin_confirmation_greeting, - name!!, + name, ) } else { stringResource(id = R.string.horologist_signedin_confirmation_greeting_no_name) diff --git a/auth/composables/src/test/snapshots/images/com.google.android.horologist.auth.composables.screens_SelectAccountScreenTest_selectAccountScreen.png b/auth/composables/src/test/snapshots/images/com.google.android.horologist.auth.composables.screens_SelectAccountScreenTest_selectAccountScreen.png index 71329164f3..405947a393 100644 --- a/auth/composables/src/test/snapshots/images/com.google.android.horologist.auth.composables.screens_SelectAccountScreenTest_selectAccountScreen.png +++ b/auth/composables/src/test/snapshots/images/com.google.android.horologist.auth.composables.screens_SelectAccountScreenTest_selectAccountScreen.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:bbde194810444eb4f278311120039f289b5df9d64d062a22960ed48b01ca6321 -size 31292 +oid sha256:d1116c0d30cd1c3a42d656ec6bc8e38ac2fc25c09fdd2e64b33a2571e7792c9f +size 31207 diff --git a/auth/composables/src/test/snapshots/images/com.google.android.horologist.auth.composables.screens_SelectAccountScreenTest_selectAccountScreenNoAvatar.png b/auth/composables/src/test/snapshots/images/com.google.android.horologist.auth.composables.screens_SelectAccountScreenTest_selectAccountScreenNoAvatar.png index 2d62bbdd77..2c5e49536f 100644 --- a/auth/composables/src/test/snapshots/images/com.google.android.horologist.auth.composables.screens_SelectAccountScreenTest_selectAccountScreenNoAvatar.png +++ b/auth/composables/src/test/snapshots/images/com.google.android.horologist.auth.composables.screens_SelectAccountScreenTest_selectAccountScreenNoAvatar.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:8fa5843f9796bd8df5749e3f64b08df66dd9fa616be0438dd03a7826c29ddc00 -size 28892 +oid sha256:cc314d780859105be111ee6d82fb92f56ba6fa48d458073fccb8306d773df67c +size 28804 diff --git a/auth/data-phone/build.gradle.kts b/auth/data-phone/build.gradle.kts index 4e43c3aeb1..7d61febf8b 100644 --- a/auth/data-phone/build.gradle.kts +++ b/auth/data-phone/build.gradle.kts @@ -16,7 +16,6 @@ plugins { id("com.android.library") - id("kotlin-android") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) alias(libs.plugins.dependencyAnalysis) @@ -42,15 +41,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlin.RequiresOptIn", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += @@ -115,12 +105,4 @@ dependencyAnalysis { } } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("auth-data-phone") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/auth/data/build.gradle.kts b/auth/data/build.gradle.kts index eaa297848d..fc58844510 100644 --- a/auth/data/build.gradle.kts +++ b/auth/data/build.gradle.kts @@ -20,7 +20,6 @@ plugins { id("com.google.devtools.ksp") alias(libs.plugins.metalavaGradle) alias(libs.plugins.dependencyAnalysis) - kotlin("android") } android { @@ -41,15 +40,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlin.RequiresOptIn", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += @@ -113,12 +103,4 @@ dependencyAnalysis { } } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("auth-data") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/auth/sample/phone/build.gradle.kts b/auth/sample/phone/build.gradle.kts index 23fe827e18..8850ed034e 100644 --- a/auth/sample/phone/build.gradle.kts +++ b/auth/sample/phone/build.gradle.kts @@ -16,7 +16,6 @@ plugins { id("com.android.application") - kotlin("android") kotlin("plugin.serialization") alias(libs.plugins.compose.compiler) } @@ -67,16 +66,6 @@ android { targetCompatibility = JavaVersion.VERSION_17 } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += "/META-INF/{AL2.0,LGPL2.1}" diff --git a/auth/sample/shared-proto/build.gradle.kts b/auth/sample/shared-proto/build.gradle.kts new file mode 100644 index 0000000000..1bf6020c46 --- /dev/null +++ b/auth/sample/shared-proto/build.gradle.kts @@ -0,0 +1,68 @@ +/* + * Copyright 2026 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +plugins { + id("java-library") + id("com.google.protobuf") +} + +java { + sourceCompatibility = JavaVersion.VERSION_17 + targetCompatibility = JavaVersion.VERSION_17 +} + +protobuf { + protoc { + artifact = libs.protobuf.protoc.stnd.get().toString() + } + plugins { + create("javalite") { + artifact = libs.protobuf.protoc.gen.javalite.get().toString() + } + create("grpc") { + artifact = libs.protobuf.protoc.gen.grpc.java.get().toString() + } + create("grpckt") { + artifact = libs.protobuf.protoc.gen.grpc.kotlin.get().toString() + } + } + generateProtoTasks { + all().forEach { task -> + task.builtins { + named("java") { + option("lite") + } + create("kotlin") { + option("lite") + } + } + task.plugins { + create("grpc") { + option("lite") + } + create("grpckt") { + option("lite") + } + } + } + } +} + +dependencies { + api(libs.protobuf.kotlin.lite) + api(libs.io.grpc.protobuf.lite) + api(libs.io.grpc.grpc.kotlin) +} diff --git a/auth/sample/shared/src/main/proto/token_bundle.proto b/auth/sample/shared-proto/src/main/proto/token_bundle.proto similarity index 100% rename from auth/sample/shared/src/main/proto/token_bundle.proto rename to auth/sample/shared-proto/src/main/proto/token_bundle.proto diff --git a/auth/sample/shared/build.gradle.kts b/auth/sample/shared/build.gradle.kts index 6dfaa39522..47c78e79ae 100644 --- a/auth/sample/shared/build.gradle.kts +++ b/auth/sample/shared/build.gradle.kts @@ -17,8 +17,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) - id("com.google.protobuf") - kotlin("android") } android { @@ -39,10 +37,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - } - packaging { resources { excludes += @@ -70,45 +64,9 @@ android { namespace = "com.google.android.horologist.auth.sample.shared" } -protobuf { - protoc { - artifact = libs.protobuf.protoc.stnd.get().toString() - } - plugins { - create("javalite") { - artifact = libs.protobuf.protoc.gen.javalite.get().toString() - } - create("grpc") { - artifact = libs.protobuf.protoc.gen.grpc.java.get().toString() - } - create("grpckt") { - artifact = libs.protobuf.protoc.gen.grpc.kotlin.get().toString() - } - } - generateProtoTasks { - all().forEach { task -> - task.builtins { - create("java") { - option("lite") - } - create("kotlin") { - option("lite") - } - } - task.plugins { - create("grpc") { - option("lite") - } - create("grpckt") { - option("lite") - } - } - } - } -} - dependencies { api(projects.annotations) + api(projects.auth.sample.sharedProto) api(projects.datalayer.grpc) implementation(libs.androidx.corektx) diff --git a/auth/sample/wear/build.gradle.kts b/auth/sample/wear/build.gradle.kts index de4e2bcb88..58a788ef74 100644 --- a/auth/sample/wear/build.gradle.kts +++ b/auth/sample/wear/build.gradle.kts @@ -16,7 +16,6 @@ plugins { id("com.android.application") - kotlin("android") alias(libs.plugins.compose.compiler) } @@ -63,16 +62,6 @@ android { buildConfig = true } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - testOptions { unitTests { isIncludeAndroidResources = true diff --git a/auth/ui-material3/build.gradle.kts b/auth/ui-material3/build.gradle.kts index 2e44c4f2b2..a92acd4ea2 100644 --- a/auth/ui-material3/build.gradle.kts +++ b/auth/ui-material3/build.gradle.kts @@ -19,7 +19,6 @@ plugins { alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) alias(libs.plugins.dependencyAnalysis) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -42,15 +41,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - "-opt-in=kotlin.RequiresOptIn", - ) - } - packaging { resources { excludes += @@ -145,12 +135,4 @@ dependencyAnalysis { } } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("auth-ui-material3-material3") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/auth/ui/build.gradle.kts b/auth/ui/build.gradle.kts index d881469aba..709c4f913a 100644 --- a/auth/ui/build.gradle.kts +++ b/auth/ui/build.gradle.kts @@ -19,7 +19,6 @@ plugins { alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) alias(libs.plugins.dependencyAnalysis) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -42,15 +41,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - "-opt-in=kotlin.RequiresOptIn", - ) - } - packaging { resources { excludes += @@ -144,12 +134,4 @@ dependencyAnalysis { } } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("auth-ui") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/build.gradle.kts b/build.gradle.kts index 8ccd23cc17..e7f1adf909 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -1,10 +1,10 @@ -import com.android.build.gradle.LibraryExtension +@file:Suppress("UnstableApiUsage") + +import com.android.build.api.dsl.LibraryExtension import com.vanniktech.maven.publish.AndroidSingleVariantLibrary import com.vanniktech.maven.publish.JavaLibrary import com.vanniktech.maven.publish.JavadocJar import org.jetbrains.kotlin.gradle.dsl.JvmTarget -import java.net.URI -import java.util.Properties /* * Copyright 2022 The Android Open Source Project @@ -124,13 +124,15 @@ subprojects { if (childProjects.isEmpty()) { spotless { kotlin { - target("**/*.kt") + target("src/**/*.kt") ktlint(libs.versions.ktlint.get()) .setEditorConfigPath(rootProject.file("quality/ktlint/.editorconfig")) licenseHeaderFile(rootProject.file("spotless/copyright.txt")) + ratchetFrom("origin/main") } kotlinGradle { target("**/*.gradle.kts") + targetExclude("**/build/**/*") ktlint(libs.versions.ktlint.get()) .setEditorConfigPath(rootProject.file("quality/ktlint/.editorconfig")) licenseHeaderFile( @@ -152,85 +154,29 @@ subprojects { listOf( // Allow use of @OptIn "-opt-in=kotlin.RequiresOptIn", + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", // Enable default methods in interfaces - "-Xjvm-default=all" + "-jvm-default=enable" ) ) } } - // Must be afterEvaluate or else com.vanniktech.maven.publish will overwrite our - // dokka and version configuration. - afterEvaluate { - if (tasks.findByName("dokkaHtmlPartial") == null) { - // If dokka isn't enabled on this module, skip - return@afterEvaluate - } - - tasks.named("dokkaHtmlPartial") { - failOnWarning.set(false) - dokkaSourceSets.configureEach { - reportUndocumented.set(true) - skipEmptyPackages.set(true) - skipDeprecated.set(true) - jdkVersion.set(8) - - // Add Android SDK packages - noAndroidSdkLink.set(false) - - // Add samples from :sample module - samples.from( - rootProject.file("auth/sample/src/main/java/"), - rootProject.file("auth/sample/wear/src/main/java/"), - rootProject.file("media/sample/src/main/java/"), - rootProject.file("sample/src/main/java/"), - ) - - // AndroidX + Compose docs - externalDocumentationLink { - url.set(URI("https://developer.android.com/reference/").toURL()) - packageListUrl.set(URI("https://developer.android.com/reference/androidx/package-list").toURL()) - } - externalDocumentationLink { - url.set(URI("https://developer.android.com/reference/kotlin/").toURL()) - packageListUrl.set(URI("https://developer.android.com/reference/kotlin/androidx/package-list").toURL()) - } - - sourceLink { - localDirectory.set(project.file("src/main/java")) - // URL showing where the source code can be accessed through the web browser - remoteUrl.set(URI("https://github.com/google/horologist/blob/main/${project.name}/src/main/java").toURL()) - // Suffix which is used to append the line number to the URL. Use #L for GitHub - remoteLineSuffix.set("#L") - } - - perPackageOption { - matchingRegex.set("com.google.android.horologist.auth.sample.shared.*") - - suppress.set(true) - } - - // Remove composable previews from docs - suppressedFiles.from(file("src/debug/java")) - } - } - - val buildDir = project.layout.buildDirectory + val buildDir = project.layout.buildDirectory val outputDirectory = buildDir.dir("generated/sources/generateVersionFile") - val generateVersionFile = tasks.register("generateVersionFile") { + val versionName = project.properties["VERSION_NAME"] as String + val moduleName = if (project.parent?.name == "horologist") + project.name + else + project.parent?.name + project.name + val generateVersionFile = tasks.register("generateVersionFile") { doLast { - val versionName = project.properties["VERSION_NAME"] as String - val manifestDir = outputDirectory.get().dir("META-INF") manifestDir.asFile.mkdirs() - val name = if (project.parent?.name == "horologist") - project.name - else - project.parent?.name + project.name manifestDir.file( - "com.google.android.horologist_$name.version" + "com.google.android.horologist_$moduleName.version" ).asFile.writeText("${versionName}\n") } } @@ -244,21 +190,16 @@ subprojects { val resources = sourceSets.findByName("main")?.resources resources?.srcDir(outputDirectory) } + } - val isLibrary = plugins.hasPlugin("com.android.library") - if (isLibrary) { - val library = extensions.getByType(LibraryExtension::class) + plugins.withId("com.android.library") { + val library = extensions.getByType(LibraryExtension::class) - val resources = library.sourceSets.findByName("main")?.resources!! - resources.srcDir(outputDirectory) - if (resources.includes.isNotEmpty()) { - resources.include("META-INF/*.version") - } + val resources = library.sourceSets.findByName("main")?.resources!! + resources.directories.add(outputDirectory.get().asFile.absolutePath) - library.libraryVariants.all { - processJavaResourcesProvider.get().dependsOn(generateVersionFile) - } + tasks.matching { it.name.startsWith("process") && it.name.endsWith("JavaResources") }.configureEach { + dependsOn(generateVersionFile) } } } -} \ No newline at end of file diff --git a/composables/build.gradle.kts b/composables/build.gradle.kts index 965e85cb0c..4384f7d738 100644 --- a/composables/build.gradle.kts +++ b/composables/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -41,13 +40,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs += listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[0].png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[0].png index 12881cb706..2da6cb9b87 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[0].png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[0].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:a2b61d98f9fb5ae7f8b313ba52a5e45fe1b54ab1620159c686ed39b00eebbed3 -size 15497 +oid sha256:4743ce6c33271fda3c4e5eea17c0a90fe7b295c280a90985811899ae33d0ea55 +size 15414 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[1].png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[1].png index cc8bf4d6a0..9c2cb6bcb6 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[1].png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[1].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:5fdcfcba02c6604eac7021871b3f1c0f081816856a08c56896939d64a547ceac -size 23081 +oid sha256:62710bd1c41b2e5550240407511501866e38788d4c4e6364f0d81ce3a8830327 +size 22992 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[2].png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[2].png index 78746d4416..bc48debee5 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[2].png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[2].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:39940e0532d5794e52e5a3abdbad1c66ab663ff70465f8cf3c1cbca25043b05a -size 18755 +oid sha256:678185975d334e28168b7b9b4878dd0d02dc8f0a7ee62d6a05fc7336f56396d3 +size 18676 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[3].png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[3].png index 97aa784205..8008887602 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[3].png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[3].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:b54ae244fd839023de21dd8090c0ef42a0179aecd48b37d2b06caff7ce543fdf -size 17928 +oid sha256:33c1830df8bb7f43176ef9dbab2351e472414efe3ef6e546617a9d1490cb0b76 +size 17845 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[4].png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[4].png index 52e9c61f41..2a47b62818 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[4].png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[4].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:834972e43264b8dfa34f40a6267ad68a04eaca163d9160ac6ed1f285c76a64b7 -size 17173 +oid sha256:abb80f93297a3385b95e98cafdeda6ccf6a607a5df22d244af7c62ad296f28f1 +size 17079 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[5].png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[5].png index 8659c512e6..6f7c5a6444 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[5].png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[5].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:183841b0eb1b32aa274e57d74140f062adeed092f3fc283156eac9fd34b8437a -size 25787 +oid sha256:4d7fa26f00a7434cf4466d39145cf46514a7ddee68e77ef4e91675be0647f42a +size 25703 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[6].png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[6].png index cbc249dd0d..d6b42b2c52 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[6].png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[6].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:05141c7948d17ca7cc9680792d913613b4baa4bd398805282502a00a653cd961 -size 20372 +oid sha256:1269266af48dbbd8dffb905dcc9673d5ccfc85e74d32f5ddb4f7607e8e316511 +size 20285 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[7].png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[7].png index 903f714fc7..3ab3495952 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[7].png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListHeaderFooterTest_test[7].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:da81c0be768d7d5491390125ffcca67b6d6481e3aea1b5152917372d353c29e6 -size 19600 +oid sha256:82f83b5facc1a1122b0974f6483fe12273d5997cef3fcaabb0eed2f1e0ac7fd3 +size 19516 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_emptyContentForStates.png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_emptyContentForStates.png index 7a3ecb12f2..758747b3d5 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_emptyContentForStates.png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_emptyContentForStates.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:4e5bece073f6a6600e9ff6d333e268d48612630408ee06cf825a00c250e926ee -size 23625 +oid sha256:4b6935168714d01b861d2ff2b0afe2e1430e538ffa70c69566fc75822cd818bb +size 23550 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_emptySection.png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_emptySection.png index 15364935fb..99a37b02e2 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_emptySection.png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_emptySection.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:a397fd8801c270a89498bd586a9c32c8cea3a10f8fce8691b0b268763a68446d -size 23986 +oid sha256:12ee3b73ac366f2319b8f20ad9df8c0698cf38850769c290908b73b6ac42b628 +size 23900 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_failedSection.png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_failedSection.png index d4f7f4b320..69152c34e8 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_failedSection.png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_failedSection.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:ba3f7d5a5dd88706edce092442c4032a510504912bb664e8cb2517ef9c0c0696 -size 27945 +oid sha256:a4f773318c7413dbb1a6ac8f7758f1cd093f72f550e9f3c7a3f22e94987a7ea7 +size 27860 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_loadedSection.png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_loadedSection.png index 03f59f90ab..1c3e26f393 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_loadedSection.png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_loadedSection.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:5630cf66e88358ce438deb8d231b9ba93edad353442cc1e6fe6a104feedc3643 -size 28300 +oid sha256:650d287c52fdc476ea1b071d8c5ebd3439c18828ecafcd653fdb5fb708363135 +size 28218 diff --git a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_loadingSection.png b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_loadingSection.png index 2de9dd2650..f6a8ed2ea3 100644 --- a/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_loadingSection.png +++ b/composables/src/test/snapshots/images/com.google.android.horologist.composables_SectionedListTest_loadingSection.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:39177d3baea99df8156aa4edf18907fce71729ca47de4e8f3964c7d1235b677d -size 28267 +oid sha256:00d2bdfdab42740d28d31e44a5a61316659853e56db88360fc553819a23d54fc +size 28189 diff --git a/compose-layout/build.gradle.kts b/compose-layout/build.gradle.kts index 18634a506b..fb8fcbbf0d 100644 --- a/compose-layout/build.gradle.kts +++ b/compose-layout/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -40,18 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - """ - kotlin.RequiresOptIn - com.google.android.horologist.annotations.ExperimentalHorologistApi - """.trim().split("\\s+".toRegex()).map { - "-opt-in=$it" - } - } - packaging { resources { excludes += diff --git a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[0]_ticwatch_pro_5.png b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[0]_ticwatch_pro_5.png index db3ded1a01..6d79c14790 100644 --- a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[0]_ticwatch_pro_5.png +++ b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[0]_ticwatch_pro_5.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:9d331110062147153f759ade38fc86b00ffa8f8c06cbab4de1185cb20da4a898 -size 35003 +oid sha256:7fef96a727c681d7bfd6e2f1c75f39ce6ece060e96a6adcf169f359544de4731 +size 34900 diff --git a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[1]_galaxy_watch_5.png b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[1]_galaxy_watch_5.png index 6a61ef56f1..e7de458bc0 100644 --- a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[1]_galaxy_watch_5.png +++ b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[1]_galaxy_watch_5.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:76c93151d33fb15a45dbf6a4769c3635397a0e37ba7ef378499e936a9ce42bad -size 29562 +oid sha256:19335a2d9b7faa8e3f43e47a01d7f17977e18e833985307e80c3e770cc51cee3 +size 29450 diff --git a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[2]_galaxy_watch_6.png b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[2]_galaxy_watch_6.png index eff52b2927..13ea26d889 100644 --- a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[2]_galaxy_watch_6.png +++ b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[2]_galaxy_watch_6.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:c37a9a8f3312a03968aae22bdadadcc395a7cb35fa7ac0a8961ef4751d0ff0c3 -size 33722 +oid sha256:6c9565d6562bfa22c9c0480adfc3d08a7228657b81a156ef0506944f98b8fd01 +size 33610 diff --git a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[3]_pixel_watch.png b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[3]_pixel_watch.png index 44a28a8979..ad4316fc44 100644 --- a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[3]_pixel_watch.png +++ b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[3]_pixel_watch.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:4c8be44d81b90e30d4712dcd9e12415c551b72d2a4a0c8fc94b92f4838a25967 -size 29194 +oid sha256:47e55cc7b86f4e57f86b2c00dba1744eb4e4d97b9ee5294054d86238ad4261b0 +size 29096 diff --git a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[4]_small_round.png b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[4]_small_round.png index 44a28a8979..ad4316fc44 100644 --- a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[4]_small_round.png +++ b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[4]_small_round.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:4c8be44d81b90e30d4712dcd9e12415c551b72d2a4a0c8fc94b92f4838a25967 -size 29194 +oid sha256:47e55cc7b86f4e57f86b2c00dba1744eb4e4d97b9ee5294054d86238ad4261b0 +size 29096 diff --git a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[5]_large_round.png b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[5]_large_round.png index 58ff201eab..be1cea0635 100644 --- a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[5]_large_round.png +++ b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[5]_large_round.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:87da6daa48a604811fe1c3dd387a9bc367f3043222f1eb398e1f9e8c05d60741 -size 33965 +oid sha256:ab33790e1edb99ada6e52f253622ab3cd56b7fb48ec5ac0901a8279d00c05f3b +size 33864 diff --git a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[6]_galaxy_watch_6_small_font.png b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[6]_galaxy_watch_6_small_font.png index e67e221b7d..e3fc845509 100644 --- a/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[6]_galaxy_watch_6_small_font.png +++ b/compose-layout/src/test/screenshots/FastScrollingTransformingLazyColumnTest_BasicExample[6]_galaxy_watch_6_small_font.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:6b383f28d8b3e1c3dfab6d32fb613229192afbeba85011dcf17aca2bc69354f5 -size 33146 +oid sha256:36f2bd07a2ca15577fe38f5a851c0944a800a3b62eeef3be2ce8a8b236aede3e +size 33051 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[0]_ticwatch_pro_5.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[0]_ticwatch_pro_5.png index 120596f47f..8f7083fed4 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[0]_ticwatch_pro_5.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[0]_ticwatch_pro_5.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:49f104d5c1f92bad81484ea53ee85e5914edad78910a75ccf2b4fea728dc881c -size 28766 +oid sha256:e938380c46f4351f1337987d47cc1c2c38dbad4f70923a1dd211e97a354cdb0c +size 28671 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[0]_ticwatch_pro_5_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[0]_ticwatch_pro_5_end.png index 247d3e76e6..1a4087fe35 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[0]_ticwatch_pro_5_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[0]_ticwatch_pro_5_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:91cbe682176b757b4cff364f327d27e050b02c237c07fe21c02cc63ddd438a7f -size 25145 +oid sha256:8bf43dc8aa3c2aa7ed430dffae96f105fe74115db0e78ba6398dfa06a3c678b9 +size 25009 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[1]_galaxy_watch_5.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[1]_galaxy_watch_5.png index 6be3fcdf57..00f7b58b7c 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[1]_galaxy_watch_5.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[1]_galaxy_watch_5.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:42c761c8662de52374eb9ee3df33667f0ea7fe63895d54bca235d6fb987435f7 -size 24418 +oid sha256:44451e95e230c1eb8727720835c1c5eca2a67131c7a47541a15faf9565af6103 +size 24309 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[1]_galaxy_watch_5_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[1]_galaxy_watch_5_end.png index 39b2de3f29..c4b813ec27 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[1]_galaxy_watch_5_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[1]_galaxy_watch_5_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:b1c8b9fa1a9edc9541e08706d1579599fe5833f846f99578123f909513326c5b -size 18753 +oid sha256:5c995df51998373c0405849e880687c0e210cbed5429d7d418164efe07569848 +size 18589 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[2]_galaxy_watch_6.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[2]_galaxy_watch_6.png index dc807a96d2..d0bab0f8e6 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[2]_galaxy_watch_6.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[2]_galaxy_watch_6.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:8aabf5ace5153b8e44e3fe3b61e170080a808291a10796df1f1ccdc39f6ab36f -size 27936 +oid sha256:0a69316dd3137af31a348bc12da4552b87c63007e31068fde03e694a1f5286c6 +size 27825 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[2]_galaxy_watch_6_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[2]_galaxy_watch_6_end.png index 30f7e0aaa1..2442501941 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[2]_galaxy_watch_6_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[2]_galaxy_watch_6_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:02c66efa6e500d0d32dfd63dcb3f1c3ce3a1ea5615024e347cc5c5457446c59e -size 23749 +oid sha256:4e2cecba44b7a2b1f244a683e6da7770eca728e0dcf4660f4fe4f8494d7d708d +size 23657 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[3]_pixel_watch.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[3]_pixel_watch.png index bbfb8eac50..e777bc3219 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[3]_pixel_watch.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[3]_pixel_watch.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:e27b2759f2676d312de635134bb0ed62f97065d57e21a1dbb72a75b9f92d1a43 -size 23382 +oid sha256:c154810c59ac9c7bd3c1106c2a89244c0303f8a6b3e6755668f1eac8d83081b9 +size 23289 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[3]_pixel_watch_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[3]_pixel_watch_end.png index 1ae2212c29..8d4c0f2e5c 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[3]_pixel_watch_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[3]_pixel_watch_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:7494cc71ced608cbf415532399b1b5c4b94b5260daa95dd5f0884602e283f865 -size 20084 +oid sha256:cebcb912c0898c56e1e69aea8d81e5207e32b9dfc1c808ac452aa5c68c6d1f36 +size 19897 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[4]_small_round.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[4]_small_round.png index bbfb8eac50..e777bc3219 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[4]_small_round.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[4]_small_round.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:e27b2759f2676d312de635134bb0ed62f97065d57e21a1dbb72a75b9f92d1a43 -size 23382 +oid sha256:c154810c59ac9c7bd3c1106c2a89244c0303f8a6b3e6755668f1eac8d83081b9 +size 23289 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[4]_small_round_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[4]_small_round_end.png index 1ae2212c29..8d4c0f2e5c 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[4]_small_round_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[4]_small_round_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:7494cc71ced608cbf415532399b1b5c4b94b5260daa95dd5f0884602e283f865 -size 20084 +oid sha256:cebcb912c0898c56e1e69aea8d81e5207e32b9dfc1c808ac452aa5c68c6d1f36 +size 19897 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[5]_large_round.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[5]_large_round.png index f9af47f278..871cf20046 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[5]_large_round.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[5]_large_round.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:9e9b7d05bd9b1731a9d6898f4cda8cadd2f686d149fc7069dc719189df362d7c -size 28107 +oid sha256:254755d88af3e294e19432af35b9fe839617f163972a67b06c11e5714220bd0c +size 28010 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[5]_large_round_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[5]_large_round_end.png index 133e6cd2cd..f34b6eed61 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[5]_large_round_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[5]_large_round_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:309b3f24bb1b09fcf3637d100c58c7560bf51ea5b434e22d9ea4cab454e4e14c -size 24069 +oid sha256:156d8bc509e95f59c2e066edfefc9b1a52468b2886b2816cb1473f1ded4c97d9 +size 23982 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[6]_galaxy_watch_6_small_font.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[6]_galaxy_watch_6_small_font.png index 5238abba5d..616fffa819 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[6]_galaxy_watch_6_small_font.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[6]_galaxy_watch_6_small_font.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:e66bf9a96f01935af23766b010cb15dc55eafc18ff4b66d6e6dd5f04c2641579 -size 26934 +oid sha256:978721e39a9ef83df1b17af914770af7521207121f082cfb0bcd960cd259e89c +size 26829 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[6]_galaxy_watch_6_small_font_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[6]_galaxy_watch_6_small_font_end.png index 41326c5fd8..51ec87cf8d 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[6]_galaxy_watch_6_small_font_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_ButtonAndEdgeButton[6]_galaxy_watch_6_small_font_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:344cb37c9c9a7133b52c37cc4a342d027bce2daad3ac67a2a26b067c188082d9 -size 23150 +oid sha256:99c0f56eefc70d1b76eed15876673a28466d7cecfc4d9497108c3df1a329ab8e +size 23092 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[0]_ticwatch_pro_5.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[0]_ticwatch_pro_5.png index 6e1a595a65..8286a724cc 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[0]_ticwatch_pro_5.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[0]_ticwatch_pro_5.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:42cbe076a97b9964c773a7cd37a1d2f4e555b60ecc9488e035d1dfdb50cb5da3 -size 28240 +oid sha256:7eb67279876c1171d0ca58e1b6348dfe4e6d94b4813a6496e105a24c874fa247 +size 28146 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[0]_ticwatch_pro_5_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[0]_ticwatch_pro_5_end.png index ed363b8e4f..fa40c55834 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[0]_ticwatch_pro_5_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[0]_ticwatch_pro_5_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:b33d6f78f458b28f9e0415caeee70d3b10fe47190f09657f5c718e4766b3901f -size 27824 +oid sha256:cbab29d4e17fbfc532a5a2b0a39779e821f5c84303d6cd368a2b9d816458526f +size 27676 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[1]_galaxy_watch_5.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[1]_galaxy_watch_5.png index 7078073554..8808bd8531 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[1]_galaxy_watch_5.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[1]_galaxy_watch_5.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:bd7ea8edda0b3d7d23bd6eab084746638ca02c0dc9d259093f0e4f8ef2d44027 -size 24869 +oid sha256:b17373080502264c0e6792d72dcb3acd8b44bd272f3118639946b1446798ef69 +size 24758 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[1]_galaxy_watch_5_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[1]_galaxy_watch_5_end.png index 7f6f942ab2..4f9e317bcd 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[1]_galaxy_watch_5_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[1]_galaxy_watch_5_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:1c63c613a36eb7bf1fd9d098b2356349d8998d9cee4f5381cfe75edcabf5e4f5 -size 23972 +oid sha256:f3d5a452cfa7c8faa4e0ce46412126b6955091df331df9b8766a7306dfa671a1 +size 23830 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[2]_galaxy_watch_6.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[2]_galaxy_watch_6.png index df1b677298..24ad698858 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[2]_galaxy_watch_6.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[2]_galaxy_watch_6.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:04e9f5bd2f2673693a2304a19e401aa376f967a1422872e15cf2635570ab81e3 -size 27805 +oid sha256:34e187ae60c9b308479b4b80263d91b0838ec4860091c7772a580da280bedaa6 +size 27703 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[2]_galaxy_watch_6_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[2]_galaxy_watch_6_end.png index 9da94c1948..f591755d39 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[2]_galaxy_watch_6_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[2]_galaxy_watch_6_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:5bd6e39946e2085a758a4ebc8da9531201d0fe6b66ec8547d9b6ebe7428bcd47 -size 27035 +oid sha256:1b09347a2945486ed80a5c2c44c107ec450e90b139987cc4b25a360b20469645 +size 26935 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[3]_pixel_watch.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[3]_pixel_watch.png index 9cc140a095..f278da31b8 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[3]_pixel_watch.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[3]_pixel_watch.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:99a10a71d0c5c2f2388fe10cec3c3512c7e3a09c466623952223558aa20999f2 -size 23685 +oid sha256:d1e98b200fb5adc4f806595d7da764d3a0561fa287ca22b5d3159b5411e3bcc6 +size 23590 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[3]_pixel_watch_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[3]_pixel_watch_end.png index e22d9b9890..56c14dee31 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[3]_pixel_watch_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[3]_pixel_watch_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:1d5ec0c00306d0698f607eb3cee9acb269076c25251b4f9d54479a51b6851ece -size 23269 +oid sha256:2fd91a9769e1af147eea2df0bf123e360046024e7b913aed0b7dd015b40830a3 +size 23134 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[4]_small_round.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[4]_small_round.png index 9cc140a095..f278da31b8 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[4]_small_round.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[4]_small_round.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:99a10a71d0c5c2f2388fe10cec3c3512c7e3a09c466623952223558aa20999f2 -size 23685 +oid sha256:d1e98b200fb5adc4f806595d7da764d3a0561fa287ca22b5d3159b5411e3bcc6 +size 23590 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[4]_small_round_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[4]_small_round_end.png index e22d9b9890..56c14dee31 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[4]_small_round_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[4]_small_round_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:1d5ec0c00306d0698f607eb3cee9acb269076c25251b4f9d54479a51b6851ece -size 23269 +oid sha256:2fd91a9769e1af147eea2df0bf123e360046024e7b913aed0b7dd015b40830a3 +size 23134 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[5]_large_round.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[5]_large_round.png index f0e8ead6a0..00a3f73502 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[5]_large_round.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[5]_large_round.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:ae274719ff5d89c442995961b7ab3200cbb077d512aafb7844fd7f8213e3e0fb -size 27929 +oid sha256:77bd67bf4f194575b66b9286adb0755f3e128eb92ec1c79f85185c6148222f08 +size 27828 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[5]_large_round_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[5]_large_round_end.png index 98c3947b04..3323f9d0af 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[5]_large_round_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[5]_large_round_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:cdc86b7d6dda751b0159dd12917df61e7c4872c7002c7a4b9ebc99c6ef00df8f -size 27254 +oid sha256:3c4e0a0d620ac29b870563449752e0fc9cbf40422227a3ff73f11deade2d2395 +size 27167 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[6]_galaxy_watch_6_small_font.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[6]_galaxy_watch_6_small_font.png index 4ebe2d016d..aebb787644 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[6]_galaxy_watch_6_small_font.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[6]_galaxy_watch_6_small_font.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:0571cbc08c28c1925b5e133228e9ebf3a2c9e394e3745a2c978a2e40f2d481ac -size 27271 +oid sha256:b4a4c8a6e3c7d65b4aee679df7b7335ed8896844c6de8f0f2646841c535ff5d8 +size 27166 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[6]_galaxy_watch_6_small_font_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[6]_galaxy_watch_6_small_font_end.png index 9c08b7c859..421fa65702 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[6]_galaxy_watch_6_small_font_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_IconButtonAndExtraSmallEdgeButton[6]_galaxy_watch_6_small_font_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:010f5a7b054a26787115863d7c6a13320f8324fc7b2256be62c03399a277503e -size 26080 +oid sha256:0b76cb9c4a078491f0530234f11180c7e2f7f1000f3876271cb231800c58440e +size 26024 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[0]_ticwatch_pro_5.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[0]_ticwatch_pro_5.png index 0c7d052617..b76ebd9883 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[0]_ticwatch_pro_5.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[0]_ticwatch_pro_5.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:89be78595a449bc57f7b41b2ac2b800872a08a312c6fcd23f42c5e0820ba04d8 -size 28272 +oid sha256:1057a7f6e59d08dfc5677c25d7317f75f98e1cd7dda6c9ed1fc25c95a9138c87 +size 28174 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[0]_ticwatch_pro_5_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[0]_ticwatch_pro_5_end.png index efef3ed019..6848f07fe3 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[0]_ticwatch_pro_5_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[0]_ticwatch_pro_5_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:86fc3284061fb47711968735e775c50d2b223bcd5753d2ad691466d70eaf4630 -size 29581 +oid sha256:ff729349064bb6e32a15e80f639272acf5bc99707f5298ad78077b1b7c5a7bfd +size 29433 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[1]_galaxy_watch_5.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[1]_galaxy_watch_5.png index d6a394770e..264eced0b5 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[1]_galaxy_watch_5.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[1]_galaxy_watch_5.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:870875eb7daf075d92eeda481c047577fe20ccdad7d8626c1c7609b545e2eac0 -size 24031 +oid sha256:db537e1e8250e3ea609b5501bd0c3ef769d401c26be638825097bea07f4c1848 +size 23917 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[1]_galaxy_watch_5_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[1]_galaxy_watch_5_end.png index 105c83494c..2ce354758d 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[1]_galaxy_watch_5_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[1]_galaxy_watch_5_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:bb2e65035ac3560782efc580e52ad397b4bae0fb7dfef8eb6fd77e5856da7681 -size 25529 +oid sha256:0799f9845c38f362d2e9453014dd6b081b15aa3f049d8715c67404582b66e5ab +size 25391 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[2]_galaxy_watch_6.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[2]_galaxy_watch_6.png index 0fe7a00a70..d4dfaa8809 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[2]_galaxy_watch_6.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[2]_galaxy_watch_6.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:d3078354e900d7c11f04eed72f214b5137c3f4cd2998e434b8730e9e4b6e8db5 -size 27557 +oid sha256:77db27a1aa85bc2148a973a65aaf34d5a2e45321039f2f372cd2af27c909ba18 +size 27449 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[2]_galaxy_watch_6_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[2]_galaxy_watch_6_end.png index e7b25ba019..65677d43ca 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[2]_galaxy_watch_6_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[2]_galaxy_watch_6_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:312a97439423050c393b802bc3cd955164dab043eacbd779bc414e3827824dca -size 28840 +oid sha256:c2866b4be35fe4520168849be560ccb0c38cfd7860bfb316e8d366f6b1c7293e +size 28751 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[3]_pixel_watch.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[3]_pixel_watch.png index 57b4dde404..8c227284cc 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[3]_pixel_watch.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[3]_pixel_watch.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:bf2ce75bd20b17de0eb50bfd9bc68b8423f59ea20028e33becd44d2dce4264b5 -size 22868 +oid sha256:199a9e2ffeb4383dd099180cb31944a3c916ddf5d9ee728146f6bd53ccdb9bc0 +size 22768 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[3]_pixel_watch_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[3]_pixel_watch_end.png index 95639317b6..1cdd48ec34 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[3]_pixel_watch_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[3]_pixel_watch_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:4bcac7e91ed118174914815469e53a7218eb6ced576b3d76bf43dee1a5a9dacf -size 24915 +oid sha256:71747909fea0be3deccc772888d692a8a4439f92859ea4c289475fa399491099 +size 24840 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[4]_small_round.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[4]_small_round.png index 57b4dde404..8c227284cc 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[4]_small_round.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[4]_small_round.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:bf2ce75bd20b17de0eb50bfd9bc68b8423f59ea20028e33becd44d2dce4264b5 -size 22868 +oid sha256:199a9e2ffeb4383dd099180cb31944a3c916ddf5d9ee728146f6bd53ccdb9bc0 +size 22768 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[4]_small_round_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[4]_small_round_end.png index 95639317b6..1cdd48ec34 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[4]_small_round_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[4]_small_round_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:4bcac7e91ed118174914815469e53a7218eb6ced576b3d76bf43dee1a5a9dacf -size 24915 +oid sha256:71747909fea0be3deccc772888d692a8a4439f92859ea4c289475fa399491099 +size 24840 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[5]_large_round.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[5]_large_round.png index bf61634b76..d3759d207d 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[5]_large_round.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[5]_large_round.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:570d70d265d7d1c18b700d4b16786961414ce80df4719671559486ee8d1a7619 -size 27740 +oid sha256:8c8edc656a9fa16652aad0a266c74f8e6a6148971409ee0461f53ad515e92363 +size 27639 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[5]_large_round_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[5]_large_round_end.png index 7d2a43ceda..f94cc601d4 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[5]_large_round_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[5]_large_round_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:9b54d848d823a3d89f1c00b25cbaf5e172ed10f00d4cc468a0cc5238a504cbc1 -size 28975 +oid sha256:5260baa3b66cf6381fa6864b09a367272730d1de8a9dd1936a097817c1b75f66 +size 28882 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[6]_galaxy_watch_6_small_font.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[6]_galaxy_watch_6_small_font.png index e3604dc7dc..531cbbd9a6 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[6]_galaxy_watch_6_small_font.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[6]_galaxy_watch_6_small_font.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:b06f09e2be99faa6c2f8ae641a956894e103451d4e40be4744adf592087d6fa7 -size 26792 +oid sha256:4e9183d2a58cab4f43972e872ca8605fc009ba66c10fbca1cd13a76b54d0a16f +size 26695 diff --git a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[6]_galaxy_watch_6_small_font_end.png b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[6]_galaxy_watch_6_small_font_end.png index f5403171db..81174088ab 100644 --- a/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[6]_galaxy_watch_6_small_font_end.png +++ b/compose-layout/src/test/screenshots/TransformingLazyColumnDefaultsTest_TitleAndCard[6]_galaxy_watch_6_small_font_end.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:96e37958ade5bdd362b703b941eb1d476aa03a9b391a4d405193b5d01e9b18b9 -size 27710 +oid sha256:d2ddf7cf7b4bd430aff3ea5144d6626f7cc0eef277458db23cd8793b1776111d +size 27657 diff --git a/compose-layout/src/test/snapshots/images/com.google.android.horologist.compose.pager_PagerScreenScreenshotTest_screens.png b/compose-layout/src/test/snapshots/images/com.google.android.horologist.compose.pager_PagerScreenScreenshotTest_screens.png index 140c352c37..c761d8ce7e 100644 --- a/compose-layout/src/test/snapshots/images/com.google.android.horologist.compose.pager_PagerScreenScreenshotTest_screens.png +++ b/compose-layout/src/test/snapshots/images/com.google.android.horologist.compose.pager_PagerScreenScreenshotTest_screens.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:7dbac7e9239281b247696a0ab646158969faabcde4d77ce49a61ea3aa879d713 -size 10448 +oid sha256:3e5f5449956637280d7dbb4a435d076a72492010fcf0f3217ab4f33660ff077a +size 10360 diff --git a/compose-layout/src/test/snapshots/images/com.google.android.horologist.compose.pager_VerticalPagerScreenScreenshotTest_screens.png b/compose-layout/src/test/snapshots/images/com.google.android.horologist.compose.pager_VerticalPagerScreenScreenshotTest_screens.png index e161012d8e..e013da1d6f 100644 --- a/compose-layout/src/test/snapshots/images/com.google.android.horologist.compose.pager_VerticalPagerScreenScreenshotTest_screens.png +++ b/compose-layout/src/test/snapshots/images/com.google.android.horologist.compose.pager_VerticalPagerScreenScreenshotTest_screens.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:f96c68b9d71cee2a5afde598e49d5c574899e722082c9cd3f571923fb4debd99 -size 10586 +oid sha256:60dbf9382ce4404fb42ee8929b3f696c115b9b4d5ba4c04ae598b5cbaef43e00 +size 10501 diff --git a/compose-material/build.gradle.kts b/compose-material/build.gradle.kts index 6cd7eef7fe..80a56fe931 100644 --- a/compose-material/build.gradle.kts +++ b/compose-material/build.gradle.kts @@ -19,7 +19,6 @@ plugins { alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) alias(libs.plugins.dependencyAnalysis) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -48,13 +47,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs += listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += diff --git a/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperA11yTest_float.png b/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperA11yTest_float.png index 290b6acf6d..e98fbf4471 100644 --- a/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperA11yTest_float.png +++ b/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperA11yTest_float.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:ba702ba1e1d82522b7391b025e4b65168b7a827e4ff0b118f33ae2c370045f11 -size 31329 +oid sha256:8639d48f100dd8518bdf2d8929531937b9c0f7ae3883428277663c092495b1f6 +size 31269 diff --git a/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperA11yTest_int.png b/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperA11yTest_int.png index 176977eb97..b1556fde75 100644 --- a/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperA11yTest_int.png +++ b/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperA11yTest_int.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:2b932a78aea1ec170754f63a3193cf58c57ed54f226df8576f9a67c9c39b4ab2 -size 31194 +oid sha256:2dadddb8ceba757f033d46204e92a601f00912e4c5bd422f8eae799eca06ea66 +size 31132 diff --git a/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperTest_float.png b/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperTest_float.png index 5c1aa500ad..19530e87b1 100644 --- a/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperTest_float.png +++ b/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperTest_float.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:41706f021f598490219d31ef87572df56b1293d05e3ee8e2c460e943a550d9d4 -size 10330 +oid sha256:156435adac708854fb77b2631adcf672210d6f4d0a4d8ef2f0581006fb3b1f31 +size 10240 diff --git a/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperTest_int.png b/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperTest_int.png index c37c178246..3750163806 100644 --- a/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperTest_int.png +++ b/compose-material/src/test/snapshots/images/com.google.android.horologist.compose.material_StepperTest_int.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:053c8e93d03bf6458be18ed8a241c0a58c7ba4d2e7597927e42be5af49289d1e -size 10231 +oid sha256:eab06ae0373a517fe1f8e40f7d1b2b2f9424ad1e20aebe22da10e541b4ac238a +size 10143 diff --git a/compose-tools/build.gradle.kts b/compose-tools/build.gradle.kts index 67cda2c113..9c951f1830 100644 --- a/compose-tools/build.gradle.kts +++ b/compose-tools/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.compose.compiler) } @@ -39,11 +38,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += diff --git a/datalayer/core-proto/build.gradle.kts b/datalayer/core-proto/build.gradle.kts new file mode 100644 index 0000000000..ae91db673b --- /dev/null +++ b/datalayer/core-proto/build.gradle.kts @@ -0,0 +1,54 @@ +/* + * Copyright 2026 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import com.google.protobuf.gradle.id + +plugins { + id("java-library") + id("com.google.protobuf") +} + +java { + sourceCompatibility = JavaVersion.VERSION_17 + targetCompatibility = JavaVersion.VERSION_17 +} + +protobuf { + protoc { + artifact = libs.protobuf.protoc.stnd.get().toString() + } + plugins { + id("javalite") { + artifact = libs.protobuf.protoc.gen.javalite.get().toString() + } + } + generateProtoTasks { + all().forEach { task -> + task.builtins { + named("java") { + option("lite") + } + create("kotlin") { + option("lite") + } + } + } + } +} + +dependencies { + api(libs.protobuf.kotlin.lite) +} diff --git a/datalayer/core/src/main/proto/app_helper_pb.proto b/datalayer/core-proto/src/main/proto/app_helper_pb.proto similarity index 100% rename from datalayer/core/src/main/proto/app_helper_pb.proto rename to datalayer/core-proto/src/main/proto/app_helper_pb.proto diff --git a/datalayer/core/build.gradle.kts b/datalayer/core/build.gradle.kts index a600f25fd8..84df15d896 100644 --- a/datalayer/core/build.gradle.kts +++ b/datalayer/core/build.gradle.kts @@ -14,13 +14,10 @@ * limitations under the License. */ -import com.google.protobuf.gradle.id - plugins { id("com.android.library") alias(libs.plugins.dokka) - id("com.google.protobuf") - kotlin("android") + alias(libs.plugins.metalavaGradle) } @@ -42,14 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlin.RequiresOptIn", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } packaging { resources { excludes += @@ -75,35 +64,13 @@ android { namespace = "com.google.android.horologist.datalayer" } -protobuf { - protoc { - artifact = libs.protobuf.protoc.stnd.get().toString() - } - plugins { - id("javalite") { - artifact = libs.protobuf.protoc.gen.javalite.get().toString() - } - } - generateProtoTasks { - all().forEach { task -> - task.builtins { - create("java") { - option("lite") - } - create("kotlin") { - option("lite") - } - } - } - } -} - metalava { filename.set("api/current.api") } dependencies { api(projects.annotations) + api(projects.datalayer.coreProto) implementation(libs.kotlin.stdlib) implementation(libs.kotlinx.coroutines.core) @@ -131,14 +98,6 @@ dependencies { androidTestImplementation(libs.truth) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("datalayer") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") // tasks.maybeCreate("prepareKotlinIdeaImport") diff --git a/datalayer/core/gradle.properties b/datalayer/core/gradle.properties deleted file mode 100644 index bb8efa86dd..0000000000 --- a/datalayer/core/gradle.properties +++ /dev/null @@ -1,3 +0,0 @@ -POM_ARTIFACT_ID=horologist-datalayer -POM_NAME=Horologist DataLayer library -POM_PACKAGING=aar diff --git a/datalayer/core/src/main/java/com/google/android/horologist/data/apphelper/DataLayerAppHelper.kt b/datalayer/core/src/main/java/com/google/android/horologist/data/apphelper/DataLayerAppHelper.kt index 757abecc38..b02f740b63 100644 --- a/datalayer/core/src/main/java/com/google/android/horologist/data/apphelper/DataLayerAppHelper.kt +++ b/datalayer/core/src/main/java/com/google/android/horologist/data/apphelper/DataLayerAppHelper.kt @@ -1,5 +1,5 @@ /* - * Copyright 2023 The Android Open Source Project + * Copyright 2023-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -29,13 +29,11 @@ import com.google.android.gms.wearable.Node import com.google.android.horologist.data.ActivityConfig import com.google.android.horologist.data.AppHelperResult import com.google.android.horologist.data.AppHelperResultCode -import com.google.android.horologist.data.AppHelperResultCode.APP_HELPER_RESULT_TEMPORARILY_UNAVAILABLE +import com.google.android.horologist.data.LaunchRequest +import com.google.android.horologist.data.OwnAppConfig import com.google.android.horologist.data.TargetNodeId import com.google.android.horologist.data.WearDataLayerRegistry import com.google.android.horologist.data.WearableApiAvailability -import com.google.android.horologist.data.appHelperResult -import com.google.android.horologist.data.launchRequest -import com.google.android.horologist.data.ownAppConfig import kotlinx.coroutines.TimeoutCancellationException import kotlinx.coroutines.channels.awaitClose import kotlinx.coroutines.flow.Flow @@ -56,10 +54,14 @@ abstract class DataLayerAppHelper( protected val context: Context, protected val registry: WearDataLayerRegistry, ) { - private val activityManager: ActivityManager by lazy { context.getSystemService(Context.ACTIVITY_SERVICE) as ActivityManager } + private val activityManager: ActivityManager by lazy { + context.getSystemService(Context.ACTIVITY_SERVICE) as ActivityManager + } protected val playStoreUri: String = "market://details?id=${context.packageName}" - protected val remoteActivityHelper: RemoteActivityHelper by lazy { RemoteActivityHelper(context) } + protected val remoteActivityHelper: RemoteActivityHelper by lazy { + RemoteActivityHelper(context) + } /** * Provides a list of connected nodes and the installation status of the app on these nodes. @@ -182,7 +184,7 @@ abstract class DataLayerAppHelper( config: ActivityConfig, ): AppHelperResultCode { checkIsForegroundOrThrow() - val request = launchRequest { activity = config } + val request = LaunchRequest.newBuilder().setActivity(config).build() return sendRequestWithTimeout(nodeId, LAUNCH_APP, request.toByteArray()) } @@ -196,7 +198,9 @@ abstract class DataLayerAppHelper( @CheckResult public suspend fun startRemoteOwnApp(nodeId: String): AppHelperResultCode { checkIsForegroundOrThrow() - val request = launchRequest { ownApp = ownAppConfig { } } + val request = LaunchRequest.newBuilder().setOwnApp( + OwnAppConfig.getDefaultInstance(), + ).build() return sendRequestWithTimeout(nodeId, LAUNCH_APP, request.toByteArray()) } @@ -263,8 +267,6 @@ abstract class DataLayerAppHelper( } fun byteArrayForResultCode(resultCode: AppHelperResultCode): ByteArray { - val response = appHelperResult { - code = resultCode - } + val response = AppHelperResult.newBuilder().setCode(resultCode).build() return response.toByteArray() } diff --git a/datalayer/grpc-proto/build.gradle.kts b/datalayer/grpc-proto/build.gradle.kts new file mode 100644 index 0000000000..1bf6020c46 --- /dev/null +++ b/datalayer/grpc-proto/build.gradle.kts @@ -0,0 +1,68 @@ +/* + * Copyright 2026 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +plugins { + id("java-library") + id("com.google.protobuf") +} + +java { + sourceCompatibility = JavaVersion.VERSION_17 + targetCompatibility = JavaVersion.VERSION_17 +} + +protobuf { + protoc { + artifact = libs.protobuf.protoc.stnd.get().toString() + } + plugins { + create("javalite") { + artifact = libs.protobuf.protoc.gen.javalite.get().toString() + } + create("grpc") { + artifact = libs.protobuf.protoc.gen.grpc.java.get().toString() + } + create("grpckt") { + artifact = libs.protobuf.protoc.gen.grpc.kotlin.get().toString() + } + } + generateProtoTasks { + all().forEach { task -> + task.builtins { + named("java") { + option("lite") + } + create("kotlin") { + option("lite") + } + } + task.plugins { + create("grpc") { + option("lite") + } + create("grpckt") { + option("lite") + } + } + } + } +} + +dependencies { + api(libs.protobuf.kotlin.lite) + api(libs.io.grpc.protobuf.lite) + api(libs.io.grpc.grpc.kotlin) +} diff --git a/datalayer/grpc/src/main/proto/wear_grpc.proto b/datalayer/grpc-proto/src/main/proto/wear_grpc.proto similarity index 100% rename from datalayer/grpc/src/main/proto/wear_grpc.proto rename to datalayer/grpc-proto/src/main/proto/wear_grpc.proto diff --git a/datalayer/grpc/build.gradle.kts b/datalayer/grpc/build.gradle.kts index 95e66c2566..59681d4b19 100644 --- a/datalayer/grpc/build.gradle.kts +++ b/datalayer/grpc/build.gradle.kts @@ -18,8 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) // alias(libs.plugins.metalavaGradle) - kotlin("android") - id("com.google.protobuf") } android { @@ -38,14 +36,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlin.RequiresOptIn", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } packaging { resources { excludes += @@ -85,47 +75,11 @@ project.tasks.withType().config // filename.set("api/current.api") // } -protobuf { - protoc { - artifact = libs.protobuf.protoc.stnd.get().toString() - } - plugins { - create("javalite") { - artifact = libs.protobuf.protoc.gen.javalite.get().toString() - } - create("grpc") { - artifact = libs.protobuf.protoc.gen.grpc.java.get().toString() - } - create("grpckt") { - artifact = libs.protobuf.protoc.gen.grpc.kotlin.get().toString() - } - } - generateProtoTasks { - all().forEach { task -> - task.builtins { - create("java") { - option("lite") - } - create("kotlin") { - option("lite") - } - } - task.plugins { - create("grpc") { - option("lite") - } - create("grpckt") { - option("lite") - } - } - } - } -} - dependencies { api(projects.annotations) api(projects.datalayer.core) + api(projects.datalayer.grpcProto) implementation(libs.kotlin.stdlib) implementation(libs.kotlinx.coroutines.core) implementation(libs.androidx.lifecycle.service) @@ -137,14 +91,6 @@ dependencies { implementation(libs.androidx.wear.remote.interactions) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("datalayer-grpc") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") // tasks.maybeCreate("prepareKotlinIdeaImport") diff --git a/datalayer/grpc/src/main/java/com/google/android/horologist/datalayer/grpc/client/MessageClientCall.kt b/datalayer/grpc/src/main/java/com/google/android/horologist/datalayer/grpc/client/MessageClientCall.kt index 39d756924a..a2af9931c1 100644 --- a/datalayer/grpc/src/main/java/com/google/android/horologist/datalayer/grpc/client/MessageClientCall.kt +++ b/datalayer/grpc/src/main/java/com/google/android/horologist/datalayer/grpc/client/MessageClientCall.kt @@ -23,9 +23,9 @@ import com.google.android.gms.wearable.MessageClient import com.google.android.gms.wearable.WearableStatusCodes import com.google.android.horologist.annotations.ExperimentalHorologistApi import com.google.android.horologist.data.WearDataLayerRegistry +import com.google.android.horologist.datalayer.grpc.proto.DataLayerGrpc import com.google.android.horologist.datalayer.grpc.proto.DataLayerGrpc.MessageResponse -import com.google.android.horologist.datalayer.grpc.proto.messageRequest -import com.google.protobuf.any +import com.google.protobuf.Any import com.google.protobuf.kotlin.toByteString import io.grpc.ClientCall import io.grpc.Metadata @@ -94,12 +94,10 @@ public class MessageClientCall( val data = methodDescriptor.streamRequest(message).use { it.readBytes() } - val request = messageRequest { - this.method = methodDescriptor.fullMethodName - this.request = any { - this.value = data.toByteString() - } - } + val request = DataLayerGrpc.MessageRequest.newBuilder() + .setMethod(methodDescriptor.fullMethodName) + .setRequest(Any.newBuilder().setValue(data.toByteString()).build()) + .build() val realData = request.toByteArray() return realData } diff --git a/datalayer/grpc/src/main/java/com/google/android/horologist/datalayer/grpc/server/BaseMessageClientServer.kt b/datalayer/grpc/src/main/java/com/google/android/horologist/datalayer/grpc/server/BaseMessageClientServer.kt index f286c5389d..087e2e7c3c 100644 --- a/datalayer/grpc/src/main/java/com/google/android/horologist/datalayer/grpc/server/BaseMessageClientServer.kt +++ b/datalayer/grpc/src/main/java/com/google/android/horologist/datalayer/grpc/server/BaseMessageClientServer.kt @@ -17,9 +17,9 @@ package com.google.android.horologist.datalayer.grpc.server import com.google.android.horologist.datalayer.grpc.proto.DataLayerGrpc.MessageRequest -import com.google.android.horologist.datalayer.grpc.proto.messageResponse +import com.google.android.horologist.datalayer.grpc.proto.DataLayerGrpc.MessageResponse +import com.google.protobuf.Any import com.google.protobuf.GeneratedMessageLite -import com.google.protobuf.any import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Deferred import kotlinx.coroutines.async @@ -32,11 +32,13 @@ public abstract class BaseMessageClientServer( return coroutineScope.async { val result = execute(request) - messageResponse { - response = any { - this.value = result.toByteString() - } - } + MessageResponse.newBuilder() + .setResponse( + Any.newBuilder() + .setValue(result.toByteString()) + .build() + ) + .build() .toByteArray() } } diff --git a/datalayer/phone-ui/build.gradle.kts b/datalayer/phone-ui/build.gradle.kts index 6cb716349d..d61bdbf7f1 100644 --- a/datalayer/phone-ui/build.gradle.kts +++ b/datalayer/phone-ui/build.gradle.kts @@ -19,7 +19,6 @@ plugins { alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) alias(libs.plugins.dependencyAnalysis) - kotlin("android") alias(libs.plugins.compose.compiler) } @@ -41,16 +40,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlin.RequiresOptIn", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += @@ -122,12 +111,4 @@ dependencyAnalysis { } } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("datalayer-phone-ui") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/datalayer/phone/build.gradle.kts b/datalayer/phone/build.gradle.kts index 2b27805d80..669c4de538 100644 --- a/datalayer/phone/build.gradle.kts +++ b/datalayer/phone/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -39,14 +38,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlin.RequiresOptIn", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } packaging { resources { excludes += @@ -107,12 +98,4 @@ dependencies { testImplementation(libs.androidx.test.runner) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("datalayer-phone") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/datalayer/sample/phone/build.gradle.kts b/datalayer/sample/phone/build.gradle.kts index b4f695c3a2..293e0e3e77 100644 --- a/datalayer/sample/phone/build.gradle.kts +++ b/datalayer/sample/phone/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.application") id("com.google.devtools.ksp") id("dagger.hilt.android.plugin") - kotlin("android") kotlin("plugin.serialization") alias(libs.plugins.compose.compiler) } @@ -71,16 +70,6 @@ android { compose = true } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - packaging { resources { excludes += "/META-INF/{AL2.0,LGPL2.1}" diff --git a/datalayer/sample/phone/src/main/java/com/google/android/horologist/datalayer/sample/screens/nodes/AppHelperNodeStatusCard.kt b/datalayer/sample/phone/src/main/java/com/google/android/horologist/datalayer/sample/screens/nodes/AppHelperNodeStatusCard.kt index ba51ccc580..2c209b727c 100644 --- a/datalayer/sample/phone/src/main/java/com/google/android/horologist/datalayer/sample/screens/nodes/AppHelperNodeStatusCard.kt +++ b/datalayer/sample/phone/src/main/java/com/google/android/horologist/datalayer/sample/screens/nodes/AppHelperNodeStatusCard.kt @@ -1,5 +1,5 @@ /* - * Copyright 2023 The Android Open Source Project + * Copyright 2023-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -34,15 +34,15 @@ import androidx.compose.ui.res.stringResource import androidx.compose.ui.text.style.TextAlign import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.dp +import com.google.android.horologist.data.ComplicationInfo +import com.google.android.horologist.data.SurfacesInfo +import com.google.android.horologist.data.TileInfo +import com.google.android.horologist.data.UsageInfo import com.google.android.horologist.data.UsageStatus import com.google.android.horologist.data.apphelper.AppHelperNodeStatus import com.google.android.horologist.data.apphelper.AppInstallationStatus import com.google.android.horologist.data.apphelper.AppInstallationStatusNodeType import com.google.android.horologist.data.apphelper.appInstalled -import com.google.android.horologist.data.complicationInfo -import com.google.android.horologist.data.surfacesInfo -import com.google.android.horologist.data.tileInfo -import com.google.android.horologist.data.usageInfo import com.google.android.horologist.datalayer.sample.R import com.google.android.horologist.datalayer.sample.ui.theme.HorologistTheme import com.google.android.horologist.datalayer.sample.util.toProtoTimestamp @@ -76,7 +76,10 @@ fun AppHelperNodeStatusCard( ) Text( style = MaterialTheme.typography.labelMedium, - text = stringResource(R.string.node_status_node_is_nearby_label, nodeStatus.isNearby), + text = stringResource( + R.string.node_status_node_is_nearby_label, + nodeStatus.isNearby, + ), ) Text( style = MaterialTheme.typography.labelMedium, @@ -108,7 +111,9 @@ fun AppHelperNodeStatusCard( style = MaterialTheme.typography.labelMedium, text = stringResource( R.string.node_status_tiles_label, - nodeStatus.surfacesInfo.tilesList.joinToString { it.name.substringAfterLast(".") }, + nodeStatus.surfacesInfo.tilesList.joinToString { + it.name.substringAfterLast(".") + }, ), ) } @@ -168,7 +173,9 @@ fun AppHelperNodeStatusCard( enabled = nodeStatus.appInstalled, ) { Text( - stringResource(id = R.string.node_status_start_remote_activity_button_label), + stringResource( + id = R.string.node_status_start_remote_activity_button_label, + ), textAlign = TextAlign.Center, ) } @@ -188,26 +195,28 @@ fun NodeCardPreview() { appInstallationStatus = AppInstallationStatus.Installed( nodeType = AppInstallationStatusNodeType.WATCH, ), - surfacesInfo = surfacesInfo { - tiles.add( - tileInfo { - name = "Horologist Tile" - timestamp = System.currentTimeMillis().toProtoTimestamp() - }, + surfacesInfo = SurfacesInfo.newBuilder() + .addTiles( + TileInfo.newBuilder() + .setName("Horologist Tile") + .setTimestamp(System.currentTimeMillis().toProtoTimestamp()) + .build(), ) - complications.add( - complicationInfo { - type = "SHORT_TEXT" - instanceId = 123 - name = "Horologist Complication" - timestamp = System.currentTimeMillis().toProtoTimestamp() - }, + .addComplications( + ComplicationInfo.newBuilder() + .setType("SHORT_TEXT") + .setInstanceId(123) + .setName("Horologist Complication") + .setTimestamp(System.currentTimeMillis().toProtoTimestamp()) + .build(), ) - usageInfo = usageInfo { - usageStatus = UsageStatus.USAGE_STATUS_LAUNCHED_ONCE - timestamp = System.currentTimeMillis().toProtoTimestamp() - } - }, + .setUsageInfo( + UsageInfo.newBuilder() + .setUsageStatus(UsageStatus.USAGE_STATUS_LAUNCHED_ONCE) + .setTimestamp(System.currentTimeMillis().toProtoTimestamp()) + .build(), + ) + .build(), ) HorologistTheme { AppHelperNodeStatusCard( diff --git a/datalayer/sample/phone/src/main/java/com/google/android/horologist/datalayer/sample/screens/nodes/NodesScreen.kt b/datalayer/sample/phone/src/main/java/com/google/android/horologist/datalayer/sample/screens/nodes/NodesScreen.kt index ea317217c1..7b43e1a4a0 100644 --- a/datalayer/sample/phone/src/main/java/com/google/android/horologist/datalayer/sample/screens/nodes/NodesScreen.kt +++ b/datalayer/sample/phone/src/main/java/com/google/android/horologist/datalayer/sample/screens/nodes/NodesScreen.kt @@ -1,5 +1,5 @@ /* - * Copyright 2023 The Android Open Source Project + * Copyright 2023-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -42,20 +42,17 @@ import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.dp import androidx.hilt.lifecycle.viewmodel.compose.hiltViewModel import androidx.lifecycle.compose.collectAsStateWithLifecycle +import com.google.android.horologist.data.ComplicationInfo +import com.google.android.horologist.data.SurfacesInfo +import com.google.android.horologist.data.TileInfo import com.google.android.horologist.data.apphelper.AppHelperNodeStatus import com.google.android.horologist.data.apphelper.AppInstallationStatus import com.google.android.horologist.data.apphelper.AppInstallationStatusNodeType -import com.google.android.horologist.data.complicationInfo -import com.google.android.horologist.data.surfacesInfo -import com.google.android.horologist.data.tileInfo import com.google.android.horologist.datalayer.sample.R import com.google.android.horologist.datalayer.sample.util.toProtoTimestamp @Composable -fun NodesScreen( - modifier: Modifier = Modifier, - viewModel: NodesViewModel = hiltViewModel(), -) { +fun NodesScreen(modifier: Modifier = Modifier, viewModel: NodesViewModel = hiltViewModel()) { val state by viewModel.uiState.collectAsStateWithLifecycle() if (state == NodesScreenState.Idle) { @@ -201,22 +198,22 @@ fun NodesScreenPreview() { appInstallationStatus = AppInstallationStatus.Installed( nodeType = AppInstallationStatusNodeType.WATCH, ), - surfacesInfo = surfacesInfo { - tiles.add( - tileInfo { - name = "MyTile" - timestamp = System.currentTimeMillis().toProtoTimestamp() - }, + surfacesInfo = SurfacesInfo.newBuilder() + .addTiles( + TileInfo.newBuilder() + .setName("MyTile") + .setTimestamp(System.currentTimeMillis().toProtoTimestamp()) + .build(), ) - complications.add( - complicationInfo { - name = "MyComplication" - instanceId = 101 - type = "SHORT_TEXT" - timestamp = System.currentTimeMillis().toProtoTimestamp() - }, + .addComplications( + ComplicationInfo.newBuilder() + .setName("MyComplication") + .setInstanceId(101) + .setType("SHORT_TEXT") + .setTimestamp(System.currentTimeMillis().toProtoTimestamp()) + .build(), ) - }, + .build(), ), ), ), diff --git a/datalayer/sample/shared-proto/build.gradle.kts b/datalayer/sample/shared-proto/build.gradle.kts new file mode 100644 index 0000000000..d7afeacab4 --- /dev/null +++ b/datalayer/sample/shared-proto/build.gradle.kts @@ -0,0 +1,69 @@ +/* + * Copyright 2026 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +plugins { + id("java-library") + id("com.google.protobuf") +} + +java { + sourceCompatibility = JavaVersion.VERSION_17 + targetCompatibility = JavaVersion.VERSION_17 +} + +protobuf { + protoc { + artifact = libs.protobuf.protoc.stnd.get().toString() + } + plugins { + create("javalite") { + artifact = libs.protobuf.protoc.gen.javalite.get().toString() + } + create("grpc") { + artifact = libs.protobuf.protoc.gen.grpc.java.get().toString() + } + create("grpckt") { + artifact = libs.protobuf.protoc.gen.grpc.kotlin.get().toString() + } + } + generateProtoTasks { + all().forEach { task -> + task.builtins { + named("java") { + option("lite") + } + create("kotlin") { + option("lite") + } + } + task.plugins { + create("grpc") { + option("lite") + } + create("grpckt") { + option("lite") + } + } + } + } +} + +dependencies { + api(libs.protobuf.kotlin.lite) + api(libs.io.grpc.protobuf.lite) + api(libs.io.grpc.grpc.kotlin) + api(libs.grpc.stub) +} diff --git a/datalayer/sample/shared/src/main/proto/grpc_demo.proto b/datalayer/sample/shared-proto/src/main/proto/grpc_demo.proto similarity index 100% rename from datalayer/sample/shared/src/main/proto/grpc_demo.proto rename to datalayer/sample/shared-proto/src/main/proto/grpc_demo.proto diff --git a/datalayer/sample/shared/build.gradle.kts b/datalayer/sample/shared/build.gradle.kts index fa952f8f6c..378487ab51 100644 --- a/datalayer/sample/shared/build.gradle.kts +++ b/datalayer/sample/shared/build.gradle.kts @@ -14,13 +14,9 @@ * limitations under the License. */ -import com.google.protobuf.gradle.id - plugins { id("com.android.library") alias(libs.plugins.dokka) - id("com.google.protobuf") - kotlin("android") } android { @@ -41,10 +37,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - } - packaging { resources { excludes += @@ -72,45 +64,9 @@ android { namespace = "com.google.android.horologist.datalayer.sample.shared" } -protobuf { - protoc { - artifact = libs.protobuf.protoc.stnd.get().toString() - } - plugins { - create("javalite") { - artifact = libs.protobuf.protoc.gen.javalite.get().toString() - } - create("grpc") { - artifact = libs.protobuf.protoc.gen.grpc.java.get().toString() - } - create("grpckt") { - artifact = libs.protobuf.protoc.gen.grpc.kotlin.get().toString() - } - } - generateProtoTasks { - all().forEach { task -> - task.builtins { - create("java") { - option("lite") - } - create("kotlin") { - option("lite") - } - } - task.plugins { - create("grpc") { - option("lite") - } - create("grpckt") { - option("lite") - } - } - } - } -} - dependencies { api(projects.annotations) + api(projects.datalayer.sample.sharedProto) api(projects.datalayer.grpc) implementation(libs.androidx.corektx) diff --git a/datalayer/sample/wear-proto/build.gradle.kts b/datalayer/sample/wear-proto/build.gradle.kts new file mode 100644 index 0000000000..6d3a6b6b4b --- /dev/null +++ b/datalayer/sample/wear-proto/build.gradle.kts @@ -0,0 +1,52 @@ +/* + * Copyright 2026 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +plugins { + id("java-library") + id("com.google.protobuf") +} + +java { + sourceCompatibility = JavaVersion.VERSION_17 + targetCompatibility = JavaVersion.VERSION_17 +} + +protobuf { + protoc { + artifact = libs.protobuf.protoc.stnd.get().toString() + } + plugins { + create("javalite") { + artifact = libs.protobuf.protoc.gen.javalite.get().toString() + } + } + generateProtoTasks { + all().forEach { task -> + task.builtins { + named("java") { + option("lite") + } + create("kotlin") { + option("lite") + } + } + } + } +} + +dependencies { + api(libs.protobuf.kotlin.lite) +} diff --git a/datalayer/sample/wear/src/main/proto/sample.proto b/datalayer/sample/wear-proto/src/main/proto/sample.proto similarity index 100% rename from datalayer/sample/wear/src/main/proto/sample.proto rename to datalayer/sample/wear-proto/src/main/proto/sample.proto diff --git a/datalayer/sample/wear/build.gradle.kts b/datalayer/sample/wear/build.gradle.kts index b3fc9ba3e2..a3acc370f6 100644 --- a/datalayer/sample/wear/build.gradle.kts +++ b/datalayer/sample/wear/build.gradle.kts @@ -14,14 +14,11 @@ * limitations under the License. */ -import com.google.protobuf.gradle.id - plugins { id("com.android.application") id("com.google.devtools.ksp") - id("com.google.protobuf") + id("dagger.hilt.android.plugin") - kotlin("android") alias(libs.plugins.compose.compiler) } @@ -68,16 +65,6 @@ android { buildConfig = true } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } - testOptions { unitTests { isIncludeAndroidResources = true @@ -93,44 +80,9 @@ android { namespace = "com.google.android.horologist.datalayer.sample" } -sourceSets { - create("main") { - java { - srcDirs( - "build/generated/source/proto/debug/java", - "build/generated/source/proto/debug/grpc", - "build/generated/source/proto/debug/kotlin", - "build/generated/source/proto/debug/grpckt", - ) - } - } -} - -protobuf { - protoc { - artifact = libs.protobuf.protoc.stnd.get().toString() - } - plugins { - id("javalite") { - artifact = libs.protobuf.protoc.gen.javalite.get().toString() - } - } - generateProtoTasks { - all().forEach { task -> - task.builtins { - create("java") { - option("lite") - } - create("kotlin") { - option("lite") - } - } - } - } -} - dependencies { api(projects.annotations) + implementation(projects.datalayer.sample.wearProto) implementation(projects.composables) implementation(projects.composeLayout) diff --git a/datalayer/watch/build.gradle.kts b/datalayer/watch/build.gradle.kts index 79ecc21033..3761ff9f99 100644 --- a/datalayer/watch/build.gradle.kts +++ b/datalayer/watch/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -39,14 +38,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlin.RequiresOptIn", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } packaging { resources { excludes += @@ -112,12 +103,4 @@ dependencies { testImplementation(libs.androidx.concurrent.future) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("datalayer-watch") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/datalayer/watch/src/main/java/com/google/android/horologist/datalayer/watch/WearDataLayerAppHelper.kt b/datalayer/watch/src/main/java/com/google/android/horologist/datalayer/watch/WearDataLayerAppHelper.kt index bf193d18c9..1836ca6cae 100644 --- a/datalayer/watch/src/main/java/com/google/android/horologist/datalayer/watch/WearDataLayerAppHelper.kt +++ b/datalayer/watch/src/main/java/com/google/android/horologist/datalayer/watch/WearDataLayerAppHelper.kt @@ -1,5 +1,5 @@ /* - * Copyright 2023 The Android Open Source Project + * Copyright 2023-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -29,21 +29,18 @@ import androidx.wear.watchface.complications.data.ComplicationType import androidx.wear.watchface.complications.datasource.ComplicationDataSourceService import com.google.android.gms.wearable.Node import com.google.android.horologist.annotations.ExperimentalHorologistApi +import com.google.android.horologist.data.ActivityLaunched import com.google.android.horologist.data.AppHelperResultCode +import com.google.android.horologist.data.CompanionConfig import com.google.android.horologist.data.ComplicationInfo +import com.google.android.horologist.data.LaunchRequest import com.google.android.horologist.data.SurfacesInfo import com.google.android.horologist.data.TileInfo +import com.google.android.horologist.data.UsageInfo import com.google.android.horologist.data.UsageStatus import com.google.android.horologist.data.WearDataLayerRegistry -import com.google.android.horologist.data.activityLaunched import com.google.android.horologist.data.apphelper.DataLayerAppHelper import com.google.android.horologist.data.apphelper.SurfacesInfoSerializer -import com.google.android.horologist.data.companionConfig -import com.google.android.horologist.data.complicationInfo -import com.google.android.horologist.data.copy -import com.google.android.horologist.data.launchRequest -import com.google.android.horologist.data.tileInfo -import com.google.android.horologist.data.usageInfo import com.google.protobuf.Timestamp import kotlinx.coroutines.CoroutineDispatcher import kotlinx.coroutines.CoroutineScope @@ -143,11 +140,13 @@ public class WearDataLayerAppHelper internal constructor( override suspend fun startCompanion(nodeId: String): AppHelperResultCode { checkIsForegroundOrThrow() val localNode = registry.nodeClient.localNode.await() - val request = launchRequest { - companion = companionConfig { - sourceNode = localNode.id - } - } + val request = LaunchRequest.newBuilder() + .setCompanion( + CompanionConfig.newBuilder() + .setSourceNode(localNode.id) + .build(), + ) + .build() return sendRequestWithTimeout(nodeId, LAUNCH_APP, request.toByteArray()) } @@ -171,17 +170,17 @@ public class WearDataLayerAppHelper internal constructor( ).await() surfacesInfoDataStore.updateData { info -> - info.copy { - tiles.clear() - for (activeTileIdentifier in activeTiles) { - tiles.add( - tileInfo { - timestamp = System.currentTimeMillis().toProtoTimestamp() - name = activeTileIdentifier.componentName.className - }, - ) - } + val builder = info.toBuilder() + builder.clearTiles() + for (activeTileIdentifier in activeTiles) { + builder.addTiles( + TileInfo.newBuilder() + .setTimestamp(System.currentTimeMillis().toProtoTimestamp()) + .setName(activeTileIdentifier.componentName.className) + .build(), + ) } + builder.build() } } @@ -190,24 +189,26 @@ public class WearDataLayerAppHelper internal constructor( */ public suspend fun markActivityLaunchedOnce() { surfacesInfoDataStore.updateData { info -> - info.copy { - val launchTimestamp = System.currentTimeMillis().toProtoTimestamp() - if (usageInfo.usageStatus == UsageStatus.USAGE_STATUS_UNSPECIFIED) { - usageInfo = usageInfo { - usageStatus = UsageStatus.USAGE_STATUS_LAUNCHED_ONCE - timestamp = launchTimestamp - } - } + val builder = info.toBuilder() + val launchTimestamp = System.currentTimeMillis().toProtoTimestamp() + if (info.usageInfo.usageStatus == UsageStatus.USAGE_STATUS_UNSPECIFIED) { + builder.setUsageInfo( + UsageInfo.newBuilder() + .setUsageStatus(UsageStatus.USAGE_STATUS_LAUNCHED_ONCE) + .setTimestamp(launchTimestamp) + .build(), + ) + } - // Temporarily support previous location for this information in [ActivityLaunched] - // Remove in the longer term - if (!activityLaunched.activityLaunchedOnce) { - activityLaunched = activityLaunched { - activityLaunchedOnce = true - timestamp = launchTimestamp - } - } + if (!info.activityLaunched.activityLaunchedOnce) { + builder.setActivityLaunched( + ActivityLaunched.newBuilder() + .setActivityLaunchedOnce(true) + .setTimestamp(launchTimestamp) + .build(), + ) } + builder.build() } } @@ -218,14 +219,16 @@ public class WearDataLayerAppHelper internal constructor( */ public suspend fun markSetupComplete() { surfacesInfoDataStore.updateData { info -> - info.copy { - if (usageInfo.usageStatus != UsageStatus.USAGE_STATUS_SETUP_COMPLETE) { - usageInfo = usageInfo { - usageStatus = UsageStatus.USAGE_STATUS_SETUP_COMPLETE - timestamp = System.currentTimeMillis().toProtoTimestamp() - } - } + val builder = info.toBuilder() + if (info.usageInfo.usageStatus != UsageStatus.USAGE_STATUS_SETUP_COMPLETE) { + builder.setUsageInfo( + UsageInfo.newBuilder() + .setUsageStatus(UsageStatus.USAGE_STATUS_SETUP_COMPLETE) + .setTimestamp(System.currentTimeMillis().toProtoTimestamp()) + .build(), + ) } + builder.build() } } @@ -236,14 +239,16 @@ public class WearDataLayerAppHelper internal constructor( */ public suspend fun markSetupNoLongerComplete() { surfacesInfoDataStore.updateData { info -> - info.copy { - if (usageInfo.usageStatus == UsageStatus.USAGE_STATUS_SETUP_COMPLETE) { - usageInfo = usageInfo { - usageStatus = UsageStatus.USAGE_STATUS_LAUNCHED_ONCE - timestamp = System.currentTimeMillis().toProtoTimestamp() - } - } + val builder = info.toBuilder() + if (info.usageInfo.usageStatus == UsageStatus.USAGE_STATUS_SETUP_COMPLETE) { + builder.setUsageInfo( + UsageInfo.newBuilder() + .setUsageStatus(UsageStatus.USAGE_STATUS_LAUNCHED_ONCE) + .setTimestamp(System.currentTimeMillis().toProtoTimestamp()) + .build(), + ) } + builder.build() } } @@ -261,18 +266,18 @@ public class WearDataLayerAppHelper internal constructor( complicationType: ComplicationType, ) { surfacesInfoDataStore.updateData { info -> - val complication = complicationInfo { - timestamp = System.currentTimeMillis().toProtoTimestamp() - name = complicationName - instanceId = complicationInstanceId - type = complicationType.name - } - info.copy { - val exists = complications.find { it.equalWithoutTimestamp(complication) } != null - if (!exists) { - complications.add(complication) - } + val complication = ComplicationInfo.newBuilder() + .setTimestamp(System.currentTimeMillis().toProtoTimestamp()) + .setName(complicationName) + .setInstanceId(complicationInstanceId) + .setType(complicationType.name) + .build() + val builder = info.toBuilder() + val exists = info.complicationsList.any { it.equalWithoutTimestamp(complication) } + if (!exists) { + builder.addComplications(complication) } + builder.build() } } @@ -282,16 +287,19 @@ public class WearDataLayerAppHelper internal constructor( * * @param complicationInstanceId Passed from [ComplicationDataSourceService.onComplicationDeactivated] */ - public suspend fun markComplicationAsDeactivated( - complicationInstanceId: Int, - ) { + public suspend fun markComplicationAsDeactivated(complicationInstanceId: Int) { surfacesInfoDataStore.updateData { info -> - info.copy { - val filtered = complications.filterNot { it.instanceId == complicationInstanceId } - if (filtered.size != complications.size) { - complications.clear() - complications.addAll(filtered) - } + val filtered = info.complicationsList.filterNot { + it.instanceId == + complicationInstanceId + } + if (filtered.size != info.complicationsList.size) { + val builder = info.toBuilder() + builder.clearComplications() + builder.addAllComplications(filtered) + builder.build() + } else { + info } } } @@ -301,25 +309,21 @@ public class WearDataLayerAppHelper internal constructor( * relevant. */ private fun TileInfo.equalWithoutTimestamp(other: TileInfo): Boolean = - this.copy { timestamp = Timestamp.getDefaultInstance() } == other.copy { - timestamp = Timestamp.getDefaultInstance() - } + this.toBuilder().setTimestamp(Timestamp.getDefaultInstance()).build() == + other.toBuilder().setTimestamp(Timestamp.getDefaultInstance()).build() /** * Compares equality of [ComplicationInfo] excluding timestamp, as when the Complication was * added is not relevant. */ private fun ComplicationInfo.equalWithoutTimestamp(other: ComplicationInfo): Boolean = - this.copy { timestamp = Timestamp.getDefaultInstance() } == other.copy { - timestamp = Timestamp.getDefaultInstance() - } + this.toBuilder().setTimestamp(Timestamp.getDefaultInstance()).build() == + other.toBuilder().setTimestamp(Timestamp.getDefaultInstance()).build() internal companion object { - internal fun Long.toProtoTimestamp(): Timestamp { - return Timestamp.newBuilder() - .setSeconds(this / 1000) - .setNanos((this % 1000).toInt() * 1000000) - .build() - } + internal fun Long.toProtoTimestamp(): Timestamp = Timestamp.newBuilder() + .setSeconds(this / 1000) + .setNanos((this % 1000).toInt() * 1000000) + .build() } } diff --git a/gradle.properties b/gradle.properties index b3de9cdc97..b7e7449ebf 100644 --- a/gradle.properties +++ b/gradle.properties @@ -14,17 +14,17 @@ # limitations under the License. # -# Turn on parallel compilation, caching and on-demand configuration -org.gradle.configureondemand=false +# Turn on parallel compilation and caching org.gradle.caching=true org.gradle.parallel=true # https://github.com/google/horologist/issues/2406 -# org.gradle.configuration-cache=true -# org.gradle.configuration-cache.problems=warn +org.gradle.configuration-cache=true +org.gradle.configuration-cache.problems=fail # Declare we support AndroidX android.useAndroidX=true +android.newDsl=true # For more information about how Gradle memory options were chosen: # - Metaspace See https://www.jasonpearson.dev/metaspace-in-jvm-builds/ @@ -63,11 +63,6 @@ POM_DEVELOPER_NAME=Google mavenCentralPublishing=true signAllPublications=true -# Plugin should be applied individually to modules that are reviewed, in order to avoid having -# unnecessary performance hit in CI. Once all modules are reviewed, this line can be removed, and -# the "apply" in each module should also be removed. -dependency.analysis.autoapply=false - # Uncomment to enable record mode #roborazzi.test.verify=true #roborazzi.test.record=true diff --git a/gradle/gradle-daemon-jvm.properties b/gradle/gradle-daemon-jvm.properties new file mode 100644 index 0000000000..52234b5ce8 --- /dev/null +++ b/gradle/gradle-daemon-jvm.properties @@ -0,0 +1 @@ +toolchainVersion=21 diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index e380dfb521..ba143685d9 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -2,75 +2,75 @@ accessibilityTestFramework = "4.1.1" accompanist = "0.36.0" androidx-benchmark = "1.4.1" -androidx-complications-data = "1.3.0-alpha07" +androidx-complications-data = "1.3.0" androidx-concurrent = "1.3.0" androidx-constraintlayout-compose = "1.1.1" -androidx-datastore = "1.2.0" +androidx-datastore = "1.2.1" androidx-graphics = "1.1.0" -androidx-health-services = "1.1.0-alpha05" +androidx-health-services = "1.1.0-rc01" androidx-hilt = "1.3.0" -androidx-media3 = "1.8.0" +androidx-media3 = "1.10.0" androidx-test-espresso = "3.7.0" androidx-test-ext = "1.3.0" androidx-test-runner = "1.7.0" -androidx-wear-watchface = "1.3.0-alpha07" -androidxActivity = "1.12.1" -androidxComposeBom = "2025.12.00" -androidxCore = "1.17.0" +androidx-wear-watchface = "1.3.0" +androidxActivity = "1.13.0" +androidxComposeBom = "2026.03.01" +androidxCore = "1.18.0" androidxLifecycle = "2.10.0" -androidxNavigation = "2.9.6" +androidxNavigation = "2.9.7" androidxPhoneInteractions = "1.1.0" -androidxRemoteInteractions = "1.1.0" +androidxRemoteInteractions = "1.2.0" androidxStartup = "1.2.0" androidxTracing = "1.3.0" -androidxWear = "1.4.0-alpha02" -androidxWork = "2.11.0" -androidxprotolayout = "1.3.0" -androidxtiles = "1.5.0" +androidxWear = "1.4.0" +androidxWork = "2.11.2" +androidxprotolayout = "1.4.0" +androidxtiles = "1.6.0" annotation = "1.0.1" app-cash-turbine = "1.2.1" appcompat = "1.7.1" com-squareup-okhttp3 = "5.3.2" com-squareup-retrofit2 = "3.0.0" -compose-material3 = "1.4.0" +compose-material3 = "1.5.0-alpha17" composesnapshot = "-" -dependencyAnalysis = "2.19.0" +dependencyAnalysis = "3.7.0" desugar_jdk_libs = "2.1.5" -dokka = "2.0.0" -googledagger = "2.57.2" -gradlePublishPlugin = "0.34.0" -grpcStub = "1.73.0" +dokka = "2.2.0" +googledagger = "2.59.2" +gradlePublishPlugin = "0.36.0" +grpcStub = "1.80.0" io-coil-kt = "2.7.0" junit = "4.13.2" -kotlin = "2.2.21" +kotlin = "2.3.20" kotlinxCoroutine = "1.10.2" -kotlinxSerialization = "1.9.0" -ksp = "2.2.10-2.0.2" -ktlint = "0.50.0" +kotlinxSerialization = "1.11.0" +ksp = "2.3.6" +ktlint = "1.8.0" material = "1.13.0" -metalava = "0.4.0-alpha03" +metalava = "0.5.0" moshi = "1.15.2" -okio = "3.16.4" -org-robolectric = "4.16" -ossLicensesPlugin = "0.10.9" -osslicenses = "0.9.0" +okio = "3.17.0" +org-robolectric = "4.16.1" +ossLicensesPlugin = "0.11.0" +osslicenses = "0.10.0" playServicesAuth = "21.4.0" -playServicesOssLicenses = "17.3.0" +playServicesOssLicenses = "17.5.0" # Stay on 4.26.1 due to https://github.com/firebase/firebase-android-sdk/issues/5997 -protobuf = "4.26.1" -protobuf-gen-grpc-java = "1.73.0" -protobuf-gen-grpc-kotlin = "1.4.3:jdk8@jar" +protobuf = "4.34.1" +protobuf-gen-grpc-java = "1.80.0" +protobuf-gen-grpc-kotlin = "1.5.0:jdk8@jar" protobuf-gen-javalite = "3.0.0" -roborazzi = "1.52.0" +roborazzi = "1.59.0" room = "2.8.4" -runtimeTracing = "1.10.0" -spotless = "7.2.1" -tiles-tooling-preview = "1.5.0" +runtimeTracing = "1.10.6" +spotless = "8.4.0" +tiles-tooling-preview = "1.6.0" truth = "1.4.5" wearInput = "1.2.0" wearToolingPreview = "1.0.0" -wearcompose = "1.6.0-alpha06" -agp = "8.12.3" +wearcompose = "1.6.1" +agp = "9.1.0" [libraries] accessibility-test-framework = { module = "com.google.android.apps.common.testing.accessibility.framework:accessibility-test-framework", version.ref = "accessibilityTestFramework" } @@ -78,13 +78,13 @@ accompanist-testharness = { module = "com.google.accompanist:accompanist-testhar android-tools-build-gradle = { module = "com.android.tools.build:gradle", version.ref = "agp" } androidx-activity = { module = "androidx.activity:activity", version.ref = "androidxActivity" } androidx-activity-compose = { module = "androidx.activity:activity-compose", version.ref = "androidxActivity" } -androidx-annotation = "androidx.annotation:annotation:1.9.1" +androidx-annotation = "androidx.annotation:annotation:1.10.0" androidx-appcompat = { group = "androidx.appcompat", name = "appcompat", version.ref = "appcompat" } androidx-benchmark-junit4 = { module = "androidx.benchmark:benchmark-junit4", version.ref = "androidx-benchmark" } androidx-benchmark-macro-junit4 = { module = "androidx.benchmark:benchmark-macro-junit4", version.ref = "androidx-benchmark" } androidx-complications-data = { module = "androidx.wear.watchface:watchface-complications-data", version.ref = "androidx-complications-data" } androidx-complications-datasource-ktx = { module = "androidx.wear.watchface:watchface-complications-data-source-ktx", version.ref = "androidx-wear-watchface" } -androidx-complications-rendering = { module = "androidx.wear.watchface:watchface-complications-rendering", version.ref = "androidx-wear-watchface" } +androidx-complications-rendering = { module = "androidx.wear.watchface:watchface-complications-rendering", version = "1.2.1" } androidx-concurrent-future = { module = "androidx.concurrent:concurrent-futures", version.ref = "androidx-concurrent" } androidx-concurrent-future-ktx = { module = "androidx.concurrent:concurrent-futures-ktx", version.ref = "androidx-concurrent" } androidx-constraintlayout-compose = { module = "androidx.constraintlayout:constraintlayout-compose", version.ref = "androidx-constraintlayout-compose" } @@ -121,7 +121,7 @@ androidx-metrics-performance = "androidx.metrics:metrics-performance:1.0.0" androidx-navigation-compose = { module = "androidx.navigation:navigation-compose", version.ref = "androidxNavigation" } androidx-navigation-runtime = { module = "androidx.navigation:navigation-runtime", version.ref = "androidxNavigation" } androidx-navigation-testing = { module = "androidx.navigation:navigation-testing", version.ref = "androidxNavigation" } -androidx-paging = "androidx.paging:paging-compose:3.3.6" +androidx-paging = "androidx.paging:paging-compose:3.4.2" androidx-palette-ktx = "androidx.palette:palette-ktx:1.0.0" androidx-runtime-tracing = { module = "androidx.compose.runtime:runtime-tracing", version.ref = "runtimeTracing" } androidx-startup = { module = "androidx.startup:startup-runtime", version.ref = "androidxStartup" } @@ -155,7 +155,7 @@ com-squareup-okhttp3-logging-interceptor = { module = "com.squareup.okhttp3:logg com-squareup-okhttp3-mockwebserver = { module = "com.squareup.okhttp3:mockwebserver", version.ref = "com-squareup-okhttp3" } com-squareup-okhttp3-okhttp = { module = "com.squareup.okhttp3:okhttp", version.ref = "com-squareup-okhttp3" } compose-animation-animationgraphics = { group = "androidx.compose.animation", name = "animation-graphics" } -compose-bom = { group = "androidx.compose", name = "compose-bom-alpha", version.ref = "androidxComposeBom" } +compose-bom = { group = "androidx.compose", name = "compose-bom", version.ref = "androidxComposeBom" } compose-foundation-foundation = { group = "androidx.compose.foundation", name = "foundation" } compose-foundation-foundation-layout = { group = "androidx.compose.foundation", name = "foundation-layout" } compose-material-iconscore = { group = "androidx.compose.material", name = "material-icons-core", version="1.7.8" } @@ -179,16 +179,16 @@ dagger-hiltandroidplugin = { module = "com.google.dagger:hilt-android-gradle-plu dagger-hiltandroidtesting = { module = "com.google.dagger:hilt-android-testing", version.ref = "googledagger" } desugar-jdk-libs = { module = "com.android.tools:desugar_jdk_libs", version.ref = "desugar_jdk_libs" } dokka = { module = "org.jetbrains.dokka:dokka-gradle-plugin", version.ref = "dokka" } -google-genai = "com.google.genai:google-genai:1.30.0" +google-genai = "com.google.genai:google-genai:1.47.0" gradleMavenPublishPlugin = { module = "com.vanniktech:gradle-maven-publish-plugin", version.ref = "gradlePublishPlugin" } grpc-stub = { module = "io.grpc:grpc-stub", version.ref = "grpcStub" } hilt-ext-compiler = { module = "androidx.hilt:hilt-compiler", version.ref = "androidx-hilt" } hilt-ext-work = { module = "androidx.hilt:hilt-work", version.ref = "androidx-hilt" } hilt-navigationcompose = { module = "androidx.hilt:hilt-navigation-compose", version.ref = "androidx-hilt" } -io-grpc-grpc-android = "io.grpc:grpc-android:1.73.0" -io-grpc-grpc-binder = "io.grpc:grpc-binder:1.73.0" -io-grpc-grpc-kotlin = "io.grpc:grpc-kotlin-stub:1.4.3" -io-grpc-protobuf-lite = "io.grpc:grpc-protobuf-lite:1.73.0" +io-grpc-grpc-android = "io.grpc:grpc-android:1.80.0" +io-grpc-grpc-binder = "io.grpc:grpc-binder:1.80.0" +io-grpc-grpc-kotlin = "io.grpc:grpc-kotlin-stub:1.5.0" +io-grpc-protobuf-lite = "io.grpc:grpc-protobuf-lite:1.80.0" junit = { module = "junit:junit", version.ref = "junit" } kotlin-gradlePlugin = { module = "org.jetbrains.kotlin:kotlin-gradle-plugin", version.ref = "kotlin" } kotlin-reflect = { module = "org.jetbrains.kotlin:kotlin-reflect", version.ref = "kotlin" } @@ -201,7 +201,7 @@ kotlinx-coroutines-test = { module = "org.jetbrains.kotlinx:kotlinx-coroutines-t kotlinx-serialization-core = { module = "org.jetbrains.kotlinx:kotlinx-serialization-core", version.ref = "kotlinxSerialization" } lottie-compose = "com.airbnb.android:lottie-compose:6.7.1" material = { group = "com.google.android.material", name = "material", version.ref = "material" } -mikepenz-markdown = "com.mikepenz:multiplatform-markdown-renderer:0.35.0" +mikepenz-markdown = "com.mikepenz:multiplatform-markdown-renderer:0.40.2" moshi-adapters = { module = "com.squareup.moshi:moshi-adapters", version.ref = "moshi" } moshi-kotlin = { module = "com.squareup.moshi:moshi-kotlin", version.ref = "moshi" } moshi-kotlin-codegen = { module = "com.squareup.moshi:moshi-kotlin-codegen", version.ref = "moshi" } @@ -246,6 +246,6 @@ kotlinGradle = { id = "org.jetbrains.kotlin.android", version.ref = "kotlin" } kotlinx-serialization = { id = "org.jetbrains.kotlin.plugin.serialization", version.ref = "kotlin" } ksp = { id = "com.google.devtools.ksp", version.ref = "ksp" } metalavaGradle = { id = "me.tylerbwong.gradle.metalava", version.ref = "metalava" } -protobuf = "com.google.protobuf:0.9.5" +protobuf = "com.google.protobuf:0.9.6" roborazzi = { id = "io.github.takahirom.roborazzi", version.ref = "roborazzi" } spotless = { id = "com.diffplug.spotless", version.ref = "spotless" } diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index 7705927e94..5f38436fc6 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,6 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-8.14.3-all.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-9.3.1-all.zip networkTimeout=10000 validateDistributionUrl=true zipStoreBase=GRADLE_USER_HOME diff --git a/health/composables/build.gradle.kts b/health/composables/build.gradle.kts index 90ac2c7c2c..0b2b4d90d2 100644 --- a/health/composables/build.gradle.kts +++ b/health/composables/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -47,12 +46,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=kotlin.RequiresOptIn" - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -120,12 +113,4 @@ dependencies { testImplementation(libs.truth) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("health-composables") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenA11yTest_metricsScreenTwoMetrics.png b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenA11yTest_metricsScreenTwoMetrics.png index d6eff1088c..c56212052c 100644 --- a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenA11yTest_metricsScreenTwoMetrics.png +++ b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenA11yTest_metricsScreenTwoMetrics.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:17f1c03b2677237df00cb1bccbd777bb21e7781dd5e5fb53fa077615b2990ae9 -size 28594 +oid sha256:5b22d7dd1bb30aa7efa509398185f1dec201debeea1149faefdaa4c11d327c40 +size 28481 diff --git a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenA11yTest_metricsScreenTwoMetrics_rtl.png b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenA11yTest_metricsScreenTwoMetrics_rtl.png index 6b62337b4b..6820114593 100644 --- a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenA11yTest_metricsScreenTwoMetrics_rtl.png +++ b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenA11yTest_metricsScreenTwoMetrics_rtl.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:6bd7285f5cfcea29ad18f9cd64b2e36858e7d6bc03e1fd1a3df0f14622a7d49b -size 28467 +oid sha256:9d9dffa1f644af63785432a0150c5cf9af9c0391ae0ae825b153f65e36dc7aea +size 28363 diff --git a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics.png b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics.png index 10c3aaccd8..e82ae966a3 100644 --- a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics.png +++ b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:d699b4aef787177795afbfc62a0c76b77bbb48af004448631ed7703be1e153a9 -size 22318 +oid sha256:fda4a20186b19bd0afd4922582694196b953580bedf9a8255126574f4a02906d +size 22233 diff --git a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics_largeScreen_smallestFont.png b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics_largeScreen_smallestFont.png index 6e2ba8fea9..e5e55242ba 100644 --- a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics_largeScreen_smallestFont.png +++ b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics_largeScreen_smallestFont.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:eb12e0960794d921020555d5ef1ba0c8fbb85cd475aad8b8c2b4964eda756869 -size 21499 +oid sha256:03e69c1e5a1ff6f876e6b3aaa4e2d715571626906dc9594c1d9ca7a6ff78670f +size 21398 diff --git a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics_smallScreen_largestFont.png b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics_smallScreen_largestFont.png index 29758af9ac..bd14da4811 100644 --- a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics_smallScreen_largestFont.png +++ b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenFourMetrics_smallScreen_largestFont.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:f71f56c9c22f641e64606ca2266f1bcb0d01b91db8686e9f91352219dcefc598 -size 20410 +oid sha256:83e371c57d654059a5f2f2285f4afd5a24706d6e3f4c099dc1fca3e5fcbceade +size 20340 diff --git a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenMetricsSkipped.png b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenMetricsSkipped.png index 615a8854eb..5fd85ba97a 100644 --- a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenMetricsSkipped.png +++ b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenMetricsSkipped.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:3fea17b6493658b005cb1477915e684b2153884b933f8efb6272e6e892f68e03 -size 17044 +oid sha256:34f8683ba5a825fb3a52eae986c1f0f44d68457ccc75f564d797adba0854e469 +size 16961 diff --git a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenOneMetric.png b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenOneMetric.png index 5cb3cb6e91..4545195397 100644 --- a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenOneMetric.png +++ b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenOneMetric.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:b102908dd013c16001934db9d6f50bce696d14b78122e47ef4c3c16734593b86 -size 13525 +oid sha256:005be4778b13986decbad4b6a03ac6915e28167d7ddbc36cd5f31e869b0e455d +size 13437 diff --git a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenThreeMetrics.png b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenThreeMetrics.png index 50910254a9..495f14400e 100644 --- a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenThreeMetrics.png +++ b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenThreeMetrics.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:daf094ff405685275b70b46be60e1b6bb67f364f28cf0bfe4284bb88d2afd7fc -size 19003 +oid sha256:6a75473dfea6755f12a9a7ea2f3b912cc8f5eac94a0a3dd19d6f2537095e3800 +size 18918 diff --git a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenTwoMetrics.png b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenTwoMetrics.png index 1e81c371fe..035869e978 100644 --- a/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenTwoMetrics.png +++ b/health/composables/src/test/snapshots/images/com.google.android.horologist.health.composables.screens_MetricsScreenTest_metricsScreenTwoMetrics.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:739af464836fac484ff281436f6a76cdbb9ac48015d17dc7c52f64acb23ee655 -size 16448 +oid sha256:d63f9f7ac599766ec804cb48695d8b5f93e41a16ac7c8eb8cba387cef7c96638 +size 16368 diff --git a/health/service/build.gradle.kts b/health/service/build.gradle.kts index 6d8a58a258..03b69bd8d6 100644 --- a/health/service/build.gradle.kts +++ b/health/service/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -39,12 +38,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=kotlin.RequiresOptIn" - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -102,12 +95,4 @@ dependencies { testImplementation(libs.truth) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("health-service") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/images/base/build.gradle.kts b/images/base/build.gradle.kts index 212d4cdb54..0ce96e3cc8 100644 --- a/images/base/build.gradle.kts +++ b/images/base/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.compose.compiler) } @@ -40,11 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -95,12 +89,4 @@ dependencies { api(libs.kotlin.stdlib) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("images-base") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/images/coil/build.gradle.kts b/images/coil/build.gradle.kts index f0fc5d6fe8..ed81619aee 100644 --- a/images/coil/build.gradle.kts +++ b/images/coil/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -41,11 +40,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -113,12 +107,4 @@ dependencies { testRuntimeOnly(libs.compose.ui.test.manifest) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("images-coil") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/audio-ui-material3/build.gradle.kts b/media/audio-ui-material3/build.gradle.kts index 6e29acba68..d733c4a117 100644 --- a/media/audio-ui-material3/build.gradle.kts +++ b/media/audio-ui-material3/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -40,11 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -123,12 +117,4 @@ dependencies { testImplementation(libs.truth) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-audio-ui-material3") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/audio-ui-model/build.gradle.kts b/media/audio-ui-model/build.gradle.kts index a3881e8094..ed44c3d68b 100644 --- a/media/audio-ui-model/build.gradle.kts +++ b/media/audio-ui-model/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -40,11 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -93,12 +87,4 @@ dependencies { implementation(libs.androidx.lifecycle.viewmodel.compose) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-audio-ui-model") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/audio-ui/build.gradle.kts b/media/audio-ui/build.gradle.kts index de6d6cf20b..193b592f75 100644 --- a/media/audio-ui/build.gradle.kts +++ b/media/audio-ui/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -40,11 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -126,12 +120,4 @@ dependencies { testImplementation(libs.truth) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-audio-ui") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/audio/build.gradle.kts b/media/audio/build.gradle.kts index 7f4c7a1294..f148d47846 100644 --- a/media/audio/build.gradle.kts +++ b/media/audio/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -38,10 +37,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - } - packaging { resources { excludes += listOf("/META-INF/AL2.0", "/META-INF/LGPL2.1") @@ -103,12 +98,4 @@ dependencies { testImplementation(libs.robolectric) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-audio") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/backend-media3/build.gradle.kts b/media/backend-media3/build.gradle.kts index 91879af028..c2d9531e92 100644 --- a/media/backend-media3/build.gradle.kts +++ b/media/backend-media3/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -38,14 +37,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlinx.coroutines.ExperimentalCoroutinesApi", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } packaging { resources { excludes += @@ -117,12 +108,4 @@ dependencies { testImplementation(libs.androidx.media3.testutils.robolectric) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-backend-media3") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/backend-media3/src/main/java/com/google/android/horologist/media3/config/WearMedia3Factory.kt b/media/backend-media3/src/main/java/com/google/android/horologist/media3/config/WearMedia3Factory.kt index 6c59f30e4c..6ff62830a0 100644 --- a/media/backend-media3/src/main/java/com/google/android/horologist/media3/config/WearMedia3Factory.kt +++ b/media/backend-media3/src/main/java/com/google/android/horologist/media3/config/WearMedia3Factory.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -27,32 +27,28 @@ import androidx.media3.exoplayer.mediacodec.MediaCodecSelector @SuppressLint("UnsafeOptInUsageError") public open class WearMedia3Factory(private val context: Context) { - public fun audioSink( - audioOffloadListener: AudioOffloadListener?, - ): DefaultAudioSink { - return DefaultAudioSink.Builder(context) + public fun audioSink(audioOffloadListener: AudioOffloadListener?): DefaultAudioSink = + DefaultAudioSink.Builder(context) .setAudioProcessorChain(DefaultAudioSink.DefaultAudioProcessorChain()) .setExperimentalAudioOffloadListener(audioOffloadListener) .setEnableFloatOutput(false) // default - .setEnableAudioTrackPlaybackParams(false) // default + .setEnableAudioOutputPlaybackParameters(false) // default .build() - } public fun audioOnlyRenderersFactory( audioSink: AudioSink, mediaCodecSelector: MediaCodecSelector = MediaCodecSelector.DEFAULT, - ): RenderersFactory = - RenderersFactory { handler, _, audioListener, _, _ -> - arrayOf( - MediaCodecAudioRenderer( - context, - mediaCodecSelector, - handler, - audioListener, - audioSink, - ), - ) - } + ): RenderersFactory = RenderersFactory { handler, _, audioListener, _, _ -> + arrayOf( + MediaCodecAudioRenderer( + context, + mediaCodecSelector, + handler, + audioListener, + audioSink, + ), + ) + } public fun mediaCodecSelector(): MediaCodecSelector = MediaCodecSelector.DEFAULT } diff --git a/media/backend-media3/src/main/java/com/google/android/horologist/media3/util/ToAudioFormat.kt b/media/backend-media3/src/main/java/com/google/android/horologist/media3/util/ToAudioFormat.kt index 62052391f8..bdb9cdea21 100644 --- a/media/backend-media3/src/main/java/com/google/android/horologist/media3/util/ToAudioFormat.kt +++ b/media/backend-media3/src/main/java/com/google/android/horologist/media3/util/ToAudioFormat.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -21,13 +21,12 @@ import android.media.AudioFormat import androidx.media3.common.C import androidx.media3.common.Format import androidx.media3.common.MimeTypes -import androidx.media3.common.util.Assertions import androidx.media3.common.util.Util @SuppressLint("WrongConstant", "UnsafeOptInUsageError") public fun Format.toAudioFormat(): AudioFormat? { val encoding: @C.Encoding Int = - MimeTypes.getEncoding(Assertions.checkNotNull(sampleMimeType), codecs) + MimeTypes.getEncoding(checkNotNull(sampleMimeType), codecs) if (encoding == C.ENCODING_INVALID) { return null diff --git a/media/benchmark/build.gradle.kts b/media/benchmark/build.gradle.kts index f06467c3ec..2631e2a61f 100644 --- a/media/benchmark/build.gradle.kts +++ b/media/benchmark/build.gradle.kts @@ -17,7 +17,6 @@ plugins { id("com.android.library") alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -34,11 +33,6 @@ android { targetCompatibility = JavaVersion.VERSION_17 } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=kotlin.RequiresOptIn" - } - packaging { resources { excludes += diff --git a/media/core/build.gradle.kts b/media/core/build.gradle.kts index 007fbb8859..55019725f9 100644 --- a/media/core/build.gradle.kts +++ b/media/core/build.gradle.kts @@ -42,15 +42,9 @@ dependencies { tasks.withType().configureEach { compilerOptions { - freeCompilerArgs.add("-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi") - } -} - -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-core") - } + freeCompilerArgs.add( + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", + ) } } diff --git a/media/data/build.gradle.kts b/media/data/build.gradle.kts index c71d9c32ad..81305d80b3 100644 --- a/media/data/build.gradle.kts +++ b/media/data/build.gradle.kts @@ -19,7 +19,6 @@ plugins { id("com.google.devtools.ksp") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -40,15 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - "-opt-in=kotlin.RequiresOptIn", - ) - } - packaging { resources { excludes += @@ -107,12 +97,4 @@ dependencies { testImplementation(libs.androidx.media3.testutils.robolectric) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-data") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/data/src/main/java/com/google/android/horologist/media/data/service/download/MediaDownloadService.kt b/media/data/src/main/java/com/google/android/horologist/media/data/service/download/MediaDownloadService.kt index 74b05ba747..442a82adee 100644 --- a/media/data/src/main/java/com/google/android/horologist/media/data/service/download/MediaDownloadService.kt +++ b/media/data/src/main/java/com/google/android/horologist/media/data/service/download/MediaDownloadService.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -53,7 +53,7 @@ public abstract class MediaDownloadService( channelId: String?, @StringRes channelNameResourceId: Int, @StringRes channelDescriptionResourceId: Int, - @DrawableRes private val notificationIcon: Int, + @param:DrawableRes private val notificationIcon: Int, ) : DownloadService( foregroundNotificationId, foregroundNotificationUpdateInterval, @@ -62,63 +62,63 @@ public abstract class MediaDownloadService( channelDescriptionResourceId, ), LifecycleOwner { - private val dispatcher = ServiceLifecycleDispatcher(this) + private val dispatcher = ServiceLifecycleDispatcher(this) - override fun onCreate() { - dispatcher.onServicePreSuperOnCreate() + override fun onCreate() { + dispatcher.onServicePreSuperOnCreate() - super.onCreate() + super.onCreate() - downloadManagerListener.onDownloadServiceCreated(downloadManager) - } - - override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int { - dispatcher.onServicePreSuperOnStart() - return super.onStartCommand(intent, flags, startId) - } - - override val lifecycle: Lifecycle - get() = dispatcher.lifecycle - - override fun onDestroy() { - downloadManagerListener.onDownloadServiceDestroyed() - - dispatcher.onServicePreSuperOnDestroy() - - super.onDestroy() - } - - override fun getScheduler(): Scheduler = workManagerScheduler + downloadManagerListener.onDownloadServiceCreated(downloadManager) + } - override fun getForegroundNotification( - downloads: MutableList, - notMetRequirements: Int, - ): Notification = downloadNotificationHelper.buildProgressNotification( - this, - notificationIcon, - downloadIntent, - null, - downloads, - notMetRequirements, - ) + override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int { + dispatcher.onServicePreSuperOnStart() + return super.onStartCommand(intent, flags, startId) + } - /** - * Used to notify of this service creation and destruction. - */ - protected abstract val downloadManagerListener: DownloadManagerListener + override val lifecycle: Lifecycle + get() = dispatcher.lifecycle - /** - * See [DownloadService.getScheduler]. - */ - protected abstract val workManagerScheduler: WorkManagerScheduler + override fun onDestroy() { + downloadManagerListener.onDownloadServiceDestroyed() - /** - * Used to build a [Notification] required by [DownloadService.getForegroundNotification]. - */ - protected abstract val downloadNotificationHelper: DownloadNotificationHelper + dispatcher.onServicePreSuperOnDestroy() - /** - * See `contentIntent` in [DownloadNotificationHelper.buildProgressNotification]. - */ - protected abstract val downloadIntent: PendingIntent + super.onDestroy() } + + override fun getScheduler(): Scheduler = workManagerScheduler + + override fun getForegroundNotification( + downloads: MutableList, + notMetRequirements: Int, + ): Notification = downloadNotificationHelper.buildProgressNotification( + this, + notificationIcon, + downloadIntent, + null, + downloads, + notMetRequirements, + ) + + /** + * Used to notify of this service creation and destruction. + */ + protected abstract val downloadManagerListener: DownloadManagerListener + + /** + * See [DownloadService.getScheduler]. + */ + protected abstract val workManagerScheduler: WorkManagerScheduler + + /** + * Used to build a [Notification] required by [DownloadService.getForegroundNotification]. + */ + protected abstract val downloadNotificationHelper: DownloadNotificationHelper + + /** + * See `contentIntent` in [DownloadNotificationHelper.buildProgressNotification]. + */ + protected abstract val downloadIntent: PendingIntent +} diff --git a/media/media3-logging/build.gradle.kts b/media/media3-logging/build.gradle.kts index 7b9dd7f5e5..6b1ec0c7a4 100644 --- a/media/media3-logging/build.gradle.kts +++ b/media/media3-logging/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -38,14 +37,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlinx.coroutines.ExperimentalCoroutinesApi", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } packaging { resources { excludes += @@ -108,12 +99,4 @@ dependencies { testImplementation(libs.androidx.media3.testutils.robolectric) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-media3-logging") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/media3-outputswitcher/build.gradle.kts b/media/media3-outputswitcher/build.gradle.kts index de79ef04a1..9f117a62d0 100644 --- a/media/media3-outputswitcher/build.gradle.kts +++ b/media/media3-outputswitcher/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -38,14 +37,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + - listOf( - "-opt-in=kotlinx.coroutines.ExperimentalCoroutinesApi", - "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi", - ) - } packaging { resources { excludes += @@ -109,12 +100,4 @@ dependencies { testImplementation(libs.androidx.media3.testutils.robolectric) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-media3-outputswitcher") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/sample-benchmark/build.gradle.kts b/media/sample-benchmark/build.gradle.kts index 809b8b7a86..2b7ad685a4 100644 --- a/media/sample-benchmark/build.gradle.kts +++ b/media/sample-benchmark/build.gradle.kts @@ -16,7 +16,6 @@ plugins { id("com.android.test") - kotlin("android") } android { @@ -28,10 +27,6 @@ android { targetCompatibility = JavaVersion.VERSION_17 } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - } - defaultConfig { minSdk = 30 targetSdk = 34 diff --git a/media/sample-proto/build.gradle.kts b/media/sample-proto/build.gradle.kts new file mode 100644 index 0000000000..6d3a6b6b4b --- /dev/null +++ b/media/sample-proto/build.gradle.kts @@ -0,0 +1,52 @@ +/* + * Copyright 2026 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +plugins { + id("java-library") + id("com.google.protobuf") +} + +java { + sourceCompatibility = JavaVersion.VERSION_17 + targetCompatibility = JavaVersion.VERSION_17 +} + +protobuf { + protoc { + artifact = libs.protobuf.protoc.stnd.get().toString() + } + plugins { + create("javalite") { + artifact = libs.protobuf.protoc.gen.javalite.get().toString() + } + } + generateProtoTasks { + all().forEach { task -> + task.builtins { + named("java") { + option("lite") + } + create("kotlin") { + option("lite") + } + } + } + } +} + +dependencies { + api(libs.protobuf.kotlin.lite) +} diff --git a/media/sample/src/main/proto/settings.proto b/media/sample-proto/src/main/proto/settings.proto similarity index 100% rename from media/sample/src/main/proto/settings.proto rename to media/sample-proto/src/main/proto/settings.proto diff --git a/media/sample/build.gradle.kts b/media/sample/build.gradle.kts index b5f27cce3a..01c501f991 100644 --- a/media/sample/build.gradle.kts +++ b/media/sample/build.gradle.kts @@ -14,15 +14,13 @@ * limitations under the License. */ -import com.google.protobuf.gradle.id import java.util.Properties plugins { id("com.android.application") id("dagger.hilt.android.plugin") id("com.google.devtools.ksp") - id("com.google.protobuf") - kotlin("android") + kotlin("plugin.serialization") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) @@ -105,21 +103,6 @@ android { buildConfig = true } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + """ - androidx.compose.foundation.ExperimentalFoundationApi - androidx.compose.ui.ExperimentalComposeUiApi - androidx.wear.compose.material.ExperimentalWearMaterialApi - com.google.android.horologist.annotations.ExperimentalHorologistApi - kotlin.RequiresOptIn - kotlinx.coroutines.ExperimentalCoroutinesApi - """.trim().split("\\s+".toRegex()).map { - "-opt-in=$it" - } - } - lint { // https://buganizer.corp.google.com/issues/328279054 disable.add("UnsafeOptInUsageError") @@ -128,31 +111,9 @@ android { namespace = "com.google.android.horologist.mediasample" } -protobuf { - protoc { - artifact = libs.protobuf.protoc.stnd.get().toString() - } - plugins { - id("javalite") { - artifact = libs.protobuf.protoc.gen.javalite.get().toString() - } - } - generateProtoTasks { - all().forEach { task -> - task.builtins { - create("java") { - option("lite") - } - create("kotlin") { - option("lite") - } - } - } - } -} - dependencies { api(projects.annotations) + implementation(projects.media.sampleProto) implementation(projects.media.audio) implementation(projects.media.audioUi) diff --git a/media/sample/src/main/AndroidManifest.xml b/media/sample/src/main/AndroidManifest.xml index 1c8b173b3e..dc03db374c 100644 --- a/media/sample/src/main/AndroidManifest.xml +++ b/media/sample/src/main/AndroidManifest.xml @@ -15,7 +15,6 @@ --> @@ -33,7 +32,6 @@ - - diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/data/settings/SettingsSerializer.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/data/settings/SettingsSerializer.kt index bc3e9ff296..9bbed698b4 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/data/settings/SettingsSerializer.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/data/settings/SettingsSerializer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -22,20 +22,19 @@ import androidx.datastore.core.DataStore import androidx.datastore.core.Serializer import androidx.datastore.dataStore import com.google.android.horologist.mediasample.domain.proto.SettingsProto.Settings -import com.google.android.horologist.mediasample.domain.proto.settings import com.google.protobuf.InvalidProtocolBufferException import java.io.InputStream import java.io.OutputStream object SettingsSerializer : Serializer { - override val defaultValue: Settings = settings { - this.animated = true - this.debugOffload = false - this.loadItemsAtStartup = false - this.podcastControls = false - this.showTimeTextInfo = false - this.currentPosition = 0 - } + override val defaultValue: Settings = Settings.newBuilder() + .setAnimated(true) + .setDebugOffload(false) + .setLoadItemsAtStartup(false) + .setPodcastControls(false) + .setShowTimeTextInfo(false) + .setCurrentPosition(0) + .build() override suspend fun readFrom(input: InputStream): Settings { try { diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/di/ViewModelModule.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/di/ViewModelModule.kt index d3ecec94d1..37e8d3bfa6 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/di/ViewModelModule.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/di/ViewModelModule.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -38,11 +38,13 @@ import dagger.hilt.android.scopes.ActivityRetainedScoped import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Deferred import kotlinx.coroutines.Dispatchers +import kotlinx.coroutines.ExperimentalCoroutinesApi import kotlinx.coroutines.SupervisorJob import kotlinx.coroutines.async import kotlinx.coroutines.cancel import kotlinx.coroutines.launch +@OptIn(ExperimentalCoroutinesApi::class) @Module @InstallIn(ActivityRetainedComponent::class) object ViewModelModule { @@ -51,11 +53,9 @@ object ViewModelModule { @Provides fun providesCoroutineScope( activityRetainedLifecycle: ActivityRetainedLifecycle, - ): CoroutineScope { - return CoroutineScope(SupervisorJob() + Dispatchers.Default).also { - activityRetainedLifecycle.addOnClearedListener { - it.cancel() - } + ): CoroutineScope = CoroutineScope(SupervisorJob() + Dispatchers.Default).also { + activityRetainedLifecycle.addOnClearedListener { + it.cancel() } } @@ -65,20 +65,19 @@ object ViewModelModule { @ApplicationContext application: Context, activityRetainedLifecycle: ActivityRetainedLifecycle, coroutineScope: CoroutineScope, - ): Deferred = - coroutineScope.async { - MediaBrowser.Builder( - application, - SessionToken(application, ComponentName(application, PlaybackService::class.java)), - ).buildSuspend() - }.also { - activityRetainedLifecycle.addOnClearedListener { - it.cancel() - if (it.isCompleted && !it.isCancelled) { - it.getCompleted().release() - } + ): Deferred = coroutineScope.async { + MediaBrowser.Builder( + application, + SessionToken(application, ComponentName(application, PlaybackService::class.java)), + ).buildSuspend() + }.also { + activityRetainedLifecycle.addOnClearedListener { + it.cancel() + if (it.isCompleted && !it.isCancelled) { + it.getCompleted().release() } } + } @Provides @ActivityRetainedScoped @@ -88,29 +87,27 @@ object ViewModelModule { activityRetainedLifecycle: ActivityRetainedLifecycle, coroutineScope: CoroutineScope, mediaController: Deferred, - ): PlayerRepositoryImpl = - PlayerRepositoryImpl( - mediaMapper = mediaMapper, - mediaItemMapper = mediaItemMapper, - ).also { playerRepository -> - activityRetainedLifecycle.addOnClearedListener { - playerRepository.close() - } + ): PlayerRepositoryImpl = PlayerRepositoryImpl( + mediaMapper = mediaMapper, + mediaItemMapper = mediaItemMapper, + ).also { playerRepository -> + activityRetainedLifecycle.addOnClearedListener { + playerRepository.close() + } - coroutineScope.launch(Dispatchers.Main) { - val player = mediaController.await() - playerRepository.connect( - player = player, - onClose = player::release, - ) - } + coroutineScope.launch(Dispatchers.Main) { + val player = mediaController.await() + playerRepository.connect( + player = player, + onClose = player::release, + ) } + } @Provides @ActivityRetainedScoped - fun playerRepository( - playerRepositoryImpl: PlayerRepositoryImpl, - ): PlayerRepository = playerRepositoryImpl + fun playerRepository(playerRepositoryImpl: PlayerRepositoryImpl): PlayerRepository = + playerRepositoryImpl @Provides fun mediaItemExtrasMapper(): MediaItemExtrasMapper = MediaItemExtrasMapperNoopImpl diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/app/MediaPlayerAppViewModel.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/app/MediaPlayerAppViewModel.kt index a0bce21195..d52e69b97c 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/app/MediaPlayerAppViewModel.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/app/MediaPlayerAppViewModel.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -26,10 +26,14 @@ import com.google.android.horologist.media.ui.snackbar.SnackbarManager import com.google.android.horologist.media.ui.snackbar.UiMessage import com.google.android.horologist.mediasample.R import com.google.android.horologist.mediasample.domain.SettingsRepository -import com.google.android.horologist.mediasample.domain.proto.copy import com.google.android.horologist.mediasample.ui.AppConfig import com.google.android.horologist.mediasample.ui.util.ResourceProvider import dagger.hilt.android.lifecycle.HiltViewModel +import java.io.IOException +import javax.inject.Inject +import kotlin.time.DurationUnit +import kotlin.time.toDuration +import kotlinx.coroutines.ExperimentalCoroutinesApi import kotlinx.coroutines.FlowPreview import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.asFlow @@ -40,152 +44,152 @@ import kotlinx.coroutines.flow.flatMapConcat import kotlinx.coroutines.flow.map import kotlinx.coroutines.flow.reduce import kotlinx.coroutines.flow.stateIn -import java.io.IOException -import javax.inject.Inject -import kotlin.time.DurationUnit -import kotlin.time.toDuration +@OptIn(ExperimentalCoroutinesApi::class) @HiltViewModel class MediaPlayerAppViewModel - @Inject - constructor( - appConfig: AppConfig, - private val settingsRepository: SettingsRepository, - private val playerRepository: PlayerRepository, - private val playlistRepository: PlaylistRepository, - private val snackbarManager: SnackbarManager, - private val resourceProvider: ResourceProvider, - private val authUserRepository: AuthUserRepository, - ) : ViewModel() { - - val deepLinkPrefix: String = appConfig.deeplinkUriPrefix - - val appState = settingsRepository.settingsFlow.map { - UampAppState( - streamingMode = it.streamingMode, - guestMode = it.guestMode, - ) - }.stateIn(viewModelScope, started = SharingStarted.WhileSubscribed(5_000), initialValue = UampAppState()) - - @OptIn(FlowPreview::class) - private suspend fun loadItems() { - playlistRepository.getAll() - .catch { throwable -> - when (throwable) { - is IOException -> { - snackbarManager.showMessage( - UiMessage( - message = resourceProvider.getString(R.string.sample_network_error), - error = true, +@Inject +constructor( + appConfig: AppConfig, + private val settingsRepository: SettingsRepository, + private val playerRepository: PlayerRepository, + private val playlistRepository: PlaylistRepository, + private val snackbarManager: SnackbarManager, + private val resourceProvider: ResourceProvider, + private val authUserRepository: AuthUserRepository, +) : ViewModel() { + + val deepLinkPrefix: String = appConfig.deeplinkUriPrefix + + val appState = settingsRepository.settingsFlow.map { + UampAppState( + streamingMode = it.streamingMode, + guestMode = it.guestMode, + ) + }.stateIn( + viewModelScope, + started = SharingStarted.WhileSubscribed(5_000), + initialValue = UampAppState(), + ) + + @OptIn(FlowPreview::class) + private suspend fun loadItems() { + playlistRepository.getAll() + .catch { throwable -> + when (throwable) { + is IOException -> { + snackbarManager.showMessage( + UiMessage( + message = resourceProvider.getString( + R.string.sample_network_error, ), - ) - } - else -> throw throwable + error = true, + ), + ) } - } - .flatMapConcat { it.asFlow() } - .map { it.mediaList } - .reduce { accumulator, value -> accumulator + value } - .also { list -> - playerRepository.setMediaList(list) - } - } - suspend fun startupSetup(navigateToLibrary: () -> Unit) { - waitForConnection() + else -> throw throwable + } + } + .flatMapConcat { it.asFlow() } + .map { it.mediaList } + .reduce { accumulator, value -> accumulator + value } + .also { list -> + playerRepository.setMediaList(list) + } + } - val currentMediaItem = playerRepository.currentMedia.value - val settings = settingsRepository.settingsFlow.first() + suspend fun startupSetup(navigateToLibrary: () -> Unit) { + waitForConnection() - // If it's currently not playing and user opted in to load items at startup, - // then we start playing using the last played media item. - if (currentMediaItem == null && settings.loadItemsAtStartup) { - playItems(settings.currentMediaItemId, settings.currentMediaListId, settings.currentPosition) - } else if (currentMediaItem == null) { - val loadAtStartup = - settingsRepository.settingsFlow.first().loadItemsAtStartup + val currentMediaItem = playerRepository.currentMedia.value + val settings = settingsRepository.settingsFlow.first() - if (loadAtStartup) { - loadItems() - } else { - navigateToLibrary() - } + // If it's currently not playing and user opted in to load items at startup, + // then we start playing using the last played media item. + if (currentMediaItem == null && settings.loadItemsAtStartup) { + playItems( + settings.currentMediaItemId, + settings.currentMediaListId, + settings.currentPosition, + ) + } else if (currentMediaItem == null) { + val loadAtStartup = + settingsRepository.settingsFlow.first().loadItemsAtStartup + + if (loadAtStartup) { + loadItems() + } else { + navigateToLibrary() } } + } - private suspend fun loadDownloadedItems(): List { - return playlistRepository.getAllDownloaded() - .flatMapConcat { it.asFlow() } - .map { it.mediaList } - .first() - } + private suspend fun loadDownloadedItems(): List = playlistRepository.getAllDownloaded() + .flatMapConcat { it.asFlow() } + .map { it.mediaList } + .first() - suspend fun startBenchmarkPlayback() { - waitForConnection() + suspend fun startBenchmarkPlayback() { + waitForConnection() - val items = loadDownloadedItems() + val items = loadDownloadedItems() - playerRepository.setMediaList(items) - playerRepository.play() - } + playerRepository.setMediaList(items) + playerRepository.play() + } - suspend fun stopBenchmarkPlayback() { - playerRepository.pause() - } + suspend fun stopBenchmarkPlayback() { + playerRepository.pause() + } - suspend fun playItems(mediaId: String?, collectionId: String, position: Long) { - try { - playlistRepository.get(collectionId)?.let { playlist -> - val index = playlist.mediaList - .indexOfFirst { it.id == mediaId } - .coerceAtLeast(0) + suspend fun playItems(mediaId: String?, collectionId: String, position: Long) { + try { + playlistRepository.get(collectionId)?.let { playlist -> + val index = playlist.mediaList + .indexOfFirst { it.id == mediaId } + .coerceAtLeast(0) - waitForConnection() + waitForConnection() - settingsRepository.edit { it.copy { currentMediaListId = collectionId } } - mediaId?.let { - id -> - settingsRepository.edit { it.copy { currentMediaItemId = id } } - } - settingsRepository.edit { it.copy { currentPosition = position } } - - playerRepository.setMediaList( - playlist.mediaList, - index, - position.toDuration( - DurationUnit.MILLISECONDS, - ), - ) + settingsRepository.edit { + it.toBuilder().setCurrentMediaListId(collectionId).build() } - } catch (e: IOException) { - snackbarManager.showMessage( - UiMessage( - message = resourceProvider.getString(R.string.sample_network_error), - error = true, + mediaId?.let { id -> + settingsRepository.edit { it.toBuilder().setCurrentMediaItemId(id).build() } + } + settingsRepository.edit { it.toBuilder().setCurrentPosition(position).build() } + + playerRepository.setMediaList( + playlist.mediaList, + index, + position.toDuration( + DurationUnit.MILLISECONDS, ), ) } + } catch (e: IOException) { + snackbarManager.showMessage( + UiMessage( + message = resourceProvider.getString(R.string.sample_network_error), + error = true, + ), + ) } + } - private suspend fun waitForConnection() { - // setMediaItems is a noop before this point - playerRepository.connected.filter { it }.first() - } + private suspend fun waitForConnection() { + // setMediaItems is a noop before this point + playerRepository.connected.filter { it }.first() + } - suspend fun shouldShowLoginPrompt(): Boolean { - return !isGuestMode() && !isLoggedIn() - } + suspend fun shouldShowLoginPrompt(): Boolean = !isGuestMode() && !isLoggedIn() - suspend fun isGuestMode(): Boolean { - return appState.filter { it.guestMode != null }.first().guestMode == true - } + suspend fun isGuestMode(): Boolean = appState.filter { + it.guestMode != null + }.first().guestMode == true - suspend fun isLoggedIn(): Boolean { - return authUserRepository.getAuthenticated() != null - } - } + suspend fun isLoggedIn(): Boolean = authUserRepository.getAuthenticated() != null +} -data class UampAppState( - val streamingMode: Boolean? = null, - val guestMode: Boolean? = null, -) +data class UampAppState(val streamingMode: Boolean? = null, val guestMode: Boolean? = null) diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/auth/prompt/UampSignInPromptViewModel.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/auth/prompt/UampSignInPromptViewModel.kt index 636a6e2303..213464c51f 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/auth/prompt/UampSignInPromptViewModel.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/auth/prompt/UampSignInPromptViewModel.kt @@ -1,5 +1,5 @@ /* - * Copyright 2023 The Android Open Source Project + * Copyright 2023-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -20,26 +20,22 @@ import androidx.lifecycle.viewModelScope import com.google.android.horologist.auth.data.common.repository.AuthUserRepository import com.google.android.horologist.auth.ui.common.screens.prompt.SignInPromptViewModel import com.google.android.horologist.mediasample.domain.SettingsRepository -import com.google.android.horologist.mediasample.domain.proto.copy import dagger.hilt.android.lifecycle.HiltViewModel -import kotlinx.coroutines.launch import javax.inject.Inject +import kotlinx.coroutines.launch @HiltViewModel class UampSignInPromptViewModel - @Inject - constructor( - authUserRepository: AuthUserRepository, - private val settingsRepository: SettingsRepository, - ) : - SignInPromptViewModel(authUserRepository) { - fun selectGuestMode() { - viewModelScope.launch { - settingsRepository.edit { - it.copy { - guestMode = true - } - } +@Inject +constructor( + authUserRepository: AuthUserRepository, + private val settingsRepository: SettingsRepository, +) : SignInPromptViewModel(authUserRepository) { + fun selectGuestMode() { + viewModelScope.launch { + settingsRepository.edit { + it.toBuilder().setGuestMode(true).build() } } } +} diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/debug/AudioDebugScreenViewModel.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/debug/AudioDebugScreenViewModel.kt index b97ac761f6..8c18f0dcff 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/debug/AudioDebugScreenViewModel.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/debug/AudioDebugScreenViewModel.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -29,6 +29,8 @@ import com.google.android.horologist.mediasample.data.service.offload.AudioOfflo import com.google.android.horologist.mediasample.data.service.offload.AudioOffloadStatus import com.google.android.horologist.mediasample.ui.AppConfig import dagger.hilt.android.lifecycle.HiltViewModel +import javax.inject.Inject +import javax.inject.Provider import kotlinx.coroutines.Deferred import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.SharingStarted @@ -37,65 +39,63 @@ import kotlinx.coroutines.flow.combine import kotlinx.coroutines.flow.flow import kotlinx.coroutines.flow.flowOf import kotlinx.coroutines.flow.stateIn -import javax.inject.Inject -import javax.inject.Provider @HiltViewModel class AudioDebugScreenViewModel - @Inject - constructor( - private val audioOffloadManager: Provider, - private val appConfig: AppConfig, - playerRepository: PlayerRepository, - private val mediaController: Deferred, - ) : ViewModel() { - val mediaControllerFlow = flow { - emit(null) - emit(mediaController.await()) - } +@Inject +constructor( + private val audioOffloadManager: Provider, + private val appConfig: AppConfig, + playerRepository: PlayerRepository, + private val mediaController: Deferred, +) : ViewModel() { + val mediaControllerFlow = flow { + emit(null) + emit(mediaController.await()) + } - fun audioOffloadFlow(): Flow = if (appConfig.offloadEnabled) { - audioOffloadManager.get().offloadStatus - } else { - flowOf(AudioOffloadStatus.Disabled) - } + fun audioOffloadFlow(): Flow = if (appConfig.offloadEnabled) { + audioOffloadManager.get().offloadStatus + } else { + flowOf(AudioOffloadStatus.Disabled) + } - val uiState: StateFlow = combine( - audioOffloadFlow(), - playerRepository.currentMedia, - mediaControllerFlow, - ) { audioOffloadStatus, currentMedia, mediaController -> + val uiState: StateFlow = combine( + audioOffloadFlow(), + playerRepository.currentMedia, + mediaControllerFlow, + ) { audioOffloadStatus, currentMedia, mediaController -> - UiState( - currentTrack = currentMedia?.title, - audioOffloadStatus = audioOffloadStatus, - formatSupported = isFormatSupported(mediaController, audioOffloadStatus.format), - ) - }.stateIn( - scope = viewModelScope, - started = SharingStarted.WhileSubscribed(5000), - initialValue = null, + UiState( + currentTrack = currentMedia?.title, + audioOffloadStatus = audioOffloadStatus, + formatSupported = isFormatSupported(mediaController, audioOffloadStatus.format), ) + }.stateIn( + scope = viewModelScope, + started = SharingStarted.WhileSubscribed(5000), + initialValue = null, + ) - public fun isFormatSupported(mediaController: MediaController?, format: Format?): Boolean? { - val audioFormat = format?.toAudioFormat() ?: return null - - if (mediaController == null) { - return null - } + public fun isFormatSupported(mediaController: MediaController?, format: Format?): Boolean? { + val audioFormat = format?.toAudioFormat() ?: return null - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) { - val audioAttributes = mediaController.audioAttributes.audioAttributesV21.audioAttributes - return AudioManager.isOffloadedPlaybackSupported(audioFormat, audioAttributes) - } + if (mediaController == null) { + return null + } - // Not supported before 30 - return false + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) { + val audioAttributes = mediaController.audioAttributes.platformAudioAttributes + return AudioManager.isOffloadedPlaybackSupported(audioFormat, audioAttributes) } - data class UiState( - val currentTrack: String?, - val audioOffloadStatus: AudioOffloadStatus, - val formatSupported: Boolean?, - ) + // Not supported before 30 + return false } + + data class UiState( + val currentTrack: String?, + val audioOffloadStatus: AudioOffloadStatus, + val formatSupported: Boolean?, + ) +} diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/debug/MediaInfoTimeTextViewModel.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/debug/MediaInfoTimeTextViewModel.kt index da7862804d..71c440bd86 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/debug/MediaInfoTimeTextViewModel.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/debug/MediaInfoTimeTextViewModel.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -28,6 +28,9 @@ import com.google.android.horologist.networks.data.Networks import com.google.android.horologist.networks.highbandwidth.HighBandwidthNetworkMediator import com.google.android.horologist.networks.status.NetworkRepository import dagger.hilt.android.lifecycle.HiltViewModel +import javax.inject.Inject +import kotlin.time.Duration.Companion.seconds +import kotlinx.coroutines.ExperimentalCoroutinesApi import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.combine @@ -35,53 +38,52 @@ import kotlinx.coroutines.flow.flatMapLatest import kotlinx.coroutines.flow.flowOf import kotlinx.coroutines.flow.map import kotlinx.coroutines.flow.stateIn -import javax.inject.Inject -import kotlin.time.Duration.Companion.seconds +@OptIn(ExperimentalCoroutinesApi::class) @HiltViewModel class MediaInfoTimeTextViewModel - @Inject - constructor( - networkRepository: NetworkRepository, - dataRequestRepository: DataRequestRepository, - audioOffloadManager: AudioOffloadManager, - highBandwidthNetworkMediator: HighBandwidthNetworkMediator, - settingsRepository: SettingsRepository, - ) : ViewModel() { - val enabledFlow: Flow = - settingsRepository.settingsFlow.map { it.showTimeTextInfo } +@Inject +constructor( + networkRepository: NetworkRepository, + dataRequestRepository: DataRequestRepository, + audioOffloadManager: AudioOffloadManager, + highBandwidthNetworkMediator: HighBandwidthNetworkMediator, + settingsRepository: SettingsRepository, +) : ViewModel() { + val enabledFlow: Flow = + settingsRepository.settingsFlow.map { it.showTimeTextInfo } - val uiState = enabledFlow.flatMapLatest { enabled -> - if (enabled) { - combine( - networkRepository.networkStatus, - audioOffloadManager.offloadStatus, - dataRequestRepository.currentPeriodUsage(), - highBandwidthNetworkMediator.pinned, - ) { networkStatus, offloadStatus, currentPeriodUsage, pinnedNetworks -> - UiState( - enabled = enabled, - networks = networkStatus, - audioOffloadStatus = offloadStatus, - dataUsageReport = currentPeriodUsage, - pinnedNetworks = pinnedNetworks, - ) - } - } else { - flowOf(UiState()) + val uiState = enabledFlow.flatMapLatest { enabled -> + if (enabled) { + combine( + networkRepository.networkStatus, + audioOffloadManager.offloadStatus, + dataRequestRepository.currentPeriodUsage(), + highBandwidthNetworkMediator.pinned, + ) { networkStatus, offloadStatus, currentPeriodUsage, pinnedNetworks -> + UiState( + enabled = enabled, + networks = networkStatus, + audioOffloadStatus = offloadStatus, + dataUsageReport = currentPeriodUsage, + pinnedNetworks = pinnedNetworks, + ) } + } else { + flowOf(UiState()) } - .stateIn( - viewModelScope, - started = SharingStarted.WhileSubscribed(5.seconds.inWholeMilliseconds), - initialValue = UiState(), - ) - - data class UiState( - val enabled: Boolean = false, - val networks: Networks = Networks(null, listOf()), - val audioOffloadStatus: AudioOffloadStatus? = null, - val dataUsageReport: DataUsageReport? = null, - val pinnedNetworks: Set = setOf(), - ) } + .stateIn( + viewModelScope, + started = SharingStarted.WhileSubscribed(5.seconds.inWholeMilliseconds), + initialValue = UiState(), + ) + + data class UiState( + val enabled: Boolean = false, + val networks: Networks = Networks(null, listOf()), + val audioOffloadStatus: AudioOffloadStatus? = null, + val dataUsageReport: DataUsageReport? = null, + val pinnedNetworks: Set = setOf(), + ) +} diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/entity/UampEntityScreenViewModel.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/entity/UampEntityScreenViewModel.kt index ea0105dc3e..5e0fca8780 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/entity/UampEntityScreenViewModel.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/entity/UampEntityScreenViewModel.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -32,77 +32,84 @@ import com.google.android.horologist.media.ui.state.mapper.PlaylistUiModelMapper import com.google.android.horologist.media.ui.state.model.DownloadMediaUiModel import com.google.android.horologist.media.ui.state.model.PlaylistUiModel import com.google.android.horologist.mediasample.domain.SettingsRepository -import com.google.android.horologist.mediasample.domain.proto.copy import dagger.hilt.android.lifecycle.HiltViewModel +import javax.inject.Inject import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.StateFlow import kotlinx.coroutines.flow.catch import kotlinx.coroutines.flow.map import kotlinx.coroutines.flow.stateIn import kotlinx.coroutines.launch -import javax.inject.Inject @HiltViewModel class UampEntityScreenViewModel - @Inject - constructor( - savedStateHandle: SavedStateHandle, - private val playlistDownloadRepository: PlaylistDownloadRepository, - private val mediaDownloadRepository: MediaDownloadRepository, - private val playerRepository: PlayerRepository, - private val settingsRepository: SettingsRepository, - ) : ViewModel() { - private val route = savedStateHandle.toRoute() +@Inject +constructor( + savedStateHandle: SavedStateHandle, + private val playlistDownloadRepository: PlaylistDownloadRepository, + private val mediaDownloadRepository: MediaDownloadRepository, + private val playerRepository: PlayerRepository, + private val settingsRepository: SettingsRepository, +) : ViewModel() { + private val route = savedStateHandle.toRoute() - private val playlistDownload: StateFlow = - playlistDownloadRepository.get(route.id) - .stateIn(viewModelScope, started = SharingStarted.Eagerly, initialValue = null) + private val playlistDownload: StateFlow = + playlistDownloadRepository.get(route.id) + .stateIn(viewModelScope, started = SharingStarted.Eagerly, initialValue = null) - val uiState: StateFlow> = - playlistDownload.map { playlistDownload -> - if (playlistDownload != null) { - createPlaylistDownloadScreenStateLoaded( - playlistModel = PlaylistUiModelMapper.map(playlistDownload.playlist), - downloadMediaList = playlistDownload.mediaList.map(DownloadMediaUiModelMapper::map), - ) - } else { - PlaylistDownloadScreenState.Failed - } - }.catch { - emit(PlaylistDownloadScreenState.Failed) - }.stateIn( - viewModelScope, - SharingStarted.WhileSubscribed(5000), - PlaylistDownloadScreenState.Loading, - ) + val uiState: StateFlow> = + playlistDownload.map { playlistDownload -> + if (playlistDownload != null) { + createPlaylistDownloadScreenStateLoaded( + playlistModel = PlaylistUiModelMapper.map(playlistDownload.playlist), + downloadMediaList = playlistDownload.mediaList.map( + DownloadMediaUiModelMapper::map, + ), + ) + } else { + PlaylistDownloadScreenState.Failed + } + }.catch { + emit(PlaylistDownloadScreenState.Failed) + }.stateIn( + viewModelScope, + SharingStarted.WhileSubscribed(5000), + PlaylistDownloadScreenState.Loading, + ) - fun play(mediaId: String? = null) { - play(shuffled = false, mediaId = mediaId) - } + fun play(mediaId: String? = null) { + play(shuffled = false, mediaId = mediaId) + } - fun shufflePlay() { - play(shuffled = true) - } + fun shufflePlay() { + play(shuffled = true) + } - private fun play(shuffled: Boolean, mediaId: String? = null) { - playlistDownload.value?.let { playlistDownload -> - val index = playlistDownload.mediaList - .indexOfFirst { it.media.id == mediaId } - .coerceAtLeast(0) - viewModelScope.launch { - settingsRepository.edit { it.copy { currentMediaListId = route.id } } + private fun play(shuffled: Boolean, mediaId: String? = null) { + playlistDownload.value?.let { playlistDownload -> + val index = playlistDownload.mediaList + .indexOfFirst { it.media.id == mediaId } + .coerceAtLeast(0) + viewModelScope.launch { + settingsRepository.edit { + it.toBuilder().setCurrentMediaListId(route.id).build() } - playerRepository.setShuffleModeEnabled(shuffled) - playerRepository.setMediaList(playlistDownload.playlist.mediaList, index) - playerRepository.play() } + playerRepository.setShuffleModeEnabled(shuffled) + playerRepository.setMediaList(playlistDownload.playlist.mediaList, index) + playerRepository.play() } + } - fun download() = playlistDownload.value?.let { playlistDownloadRepository.download(it.playlist) } + fun download() = playlistDownload.value?.let { + playlistDownloadRepository.download(it.playlist) + } - fun remove() = playlistDownload.value?.let { playlistDownloadRepository.remove(it.playlist) } + fun remove() = playlistDownload.value?.let { + playlistDownloadRepository.remove(it.playlist) + } - fun removeMediaItem(mediaId: String) { - mediaDownloadRepository.remove(mediaId) - } + fun removeMediaItem(mediaId: String) { + mediaDownloadRepository.remove(mediaId) } +} diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/entity/UampStreamingPlaylistScreenViewModel.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/entity/UampStreamingPlaylistScreenViewModel.kt index d7daf414c4..a16e7a8c9b 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/entity/UampStreamingPlaylistScreenViewModel.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/entity/UampStreamingPlaylistScreenViewModel.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -31,67 +31,70 @@ import com.google.android.horologist.media.ui.state.mapper.PlaylistUiModelMapper import com.google.android.horologist.media.ui.state.model.DownloadMediaUiModel import com.google.android.horologist.media.ui.state.model.PlaylistUiModel import com.google.android.horologist.mediasample.domain.SettingsRepository -import com.google.android.horologist.mediasample.domain.proto.copy import dagger.hilt.android.lifecycle.HiltViewModel +import javax.inject.Inject import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.StateFlow import kotlinx.coroutines.flow.catch import kotlinx.coroutines.flow.map import kotlinx.coroutines.flow.stateIn import kotlinx.coroutines.launch -import javax.inject.Inject @HiltViewModel class UampStreamingPlaylistScreenViewModel - @Inject - constructor( - savedStateHandle: SavedStateHandle, - private val playlistDownloadRepository: PlaylistDownloadRepository, - private val playerRepository: PlayerRepository, - private val settingsRepository: SettingsRepository, - ) : ViewModel() { - private val route = savedStateHandle.toRoute() +@Inject +constructor( + savedStateHandle: SavedStateHandle, + private val playlistDownloadRepository: PlaylistDownloadRepository, + private val playerRepository: PlayerRepository, + private val settingsRepository: SettingsRepository, +) : ViewModel() { + private val route = savedStateHandle.toRoute() - private val playlistDownload: StateFlow = - playlistDownloadRepository.get(route.id) - .stateIn(viewModelScope, started = SharingStarted.Eagerly, initialValue = null) + private val playlistDownload: StateFlow = + playlistDownloadRepository.get(route.id) + .stateIn(viewModelScope, started = SharingStarted.Eagerly, initialValue = null) - val uiState: StateFlow> = - playlistDownload.map { playlistDownload -> - if (playlistDownload != null) { - createPlaylistDownloadScreenStateLoaded( - playlistModel = PlaylistUiModelMapper.map(playlistDownload.playlist), - downloadMediaList = playlistDownload.mediaList.map(DownloadMediaUiModelMapper::map), - ) - } else { - PlaylistDownloadScreenState.Failed - } - }.catch { - emit(PlaylistDownloadScreenState.Failed) - }.stateIn( - viewModelScope, - SharingStarted.WhileSubscribed(5000), - PlaylistDownloadScreenState.Loading, - ) + val uiState: StateFlow> = + playlistDownload.map { playlistDownload -> + if (playlistDownload != null) { + createPlaylistDownloadScreenStateLoaded( + playlistModel = PlaylistUiModelMapper.map(playlistDownload.playlist), + downloadMediaList = playlistDownload.mediaList.map( + DownloadMediaUiModelMapper::map, + ), + ) + } else { + PlaylistDownloadScreenState.Failed + } + }.catch { + emit(PlaylistDownloadScreenState.Failed) + }.stateIn( + viewModelScope, + SharingStarted.WhileSubscribed(5000), + PlaylistDownloadScreenState.Loading, + ) - fun play(mediaId: String? = null) { - play(shuffled = false, mediaId = mediaId) - } + fun play(mediaId: String? = null) { + play(shuffled = false, mediaId = mediaId) + } - fun shufflePlay() { - play(shuffled = true) - } + fun shufflePlay() { + play(shuffled = true) + } - private fun play(shuffled: Boolean, mediaId: String? = null) { - playlistDownload.value?.let { playlistDownload -> - val index = playlistDownload.mediaList - .indexOfFirst { it.media.id == mediaId } - .coerceAtLeast(0) - viewModelScope.launch { - settingsRepository.edit { it.copy { currentMediaListId = route.id } } + private fun play(shuffled: Boolean, mediaId: String? = null) { + playlistDownload.value?.let { playlistDownload -> + val index = playlistDownload.mediaList + .indexOfFirst { it.media.id == mediaId } + .coerceAtLeast(0) + viewModelScope.launch { + settingsRepository.edit { + it.toBuilder().setCurrentMediaListId(route.id).build() } - playerRepository.setShuffleModeEnabled(shuffled) - playerRepository.setMediaList(playlistDownload.playlist.mediaList, index) } + playerRepository.setShuffleModeEnabled(shuffled) + playerRepository.setMediaList(playlistDownload.playlist.mediaList, index) } } +} diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/player/MediaPlayerScreenViewModel.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/player/MediaPlayerScreenViewModel.kt index 8212f21171..db95c3ccca 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/player/MediaPlayerScreenViewModel.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/player/MediaPlayerScreenViewModel.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -21,43 +21,42 @@ import com.google.android.horologist.media.data.repository.PlayerRepositoryImpl import com.google.android.horologist.media.ui.state.PlayerViewModel import com.google.android.horologist.mediasample.domain.SettingsRepository import com.google.android.horologist.mediasample.domain.proto.SettingsProto.Settings -import com.google.android.horologist.mediasample.domain.proto.copy import dagger.hilt.android.lifecycle.HiltViewModel +import javax.inject.Inject +import kotlin.time.Duration.Companion.seconds import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.StateFlow import kotlinx.coroutines.flow.stateIn import kotlinx.coroutines.launch -import javax.inject.Inject -import kotlin.time.Duration.Companion.seconds @HiltViewModel class MediaPlayerScreenViewModel - @Inject - constructor( - playerRepository: PlayerRepositoryImpl, - settingsRepository: SettingsRepository, - ) : PlayerViewModel(playerRepository) { +@Inject +constructor( + playerRepository: PlayerRepositoryImpl, + settingsRepository: SettingsRepository, +) : PlayerViewModel(playerRepository) { - init { - // TODO: consider if this should be done elsewhere - // https://github.com/google/horologist/issues/900 - viewModelScope.launch { - playerRepository.currentMedia.collect { media -> - if (media != null) { - settingsRepository.edit { - it.copy { currentMediaItemId = media.id } - } + init { + // TODO: consider if this should be done elsewhere + // https://github.com/google/horologist/issues/900 + viewModelScope.launch { + playerRepository.currentMedia.collect { media -> + if (media != null) { + settingsRepository.edit { + it.toBuilder().setCurrentMediaItemId(media.id).build() } } } } + } - val playerState = playerRepository.player + val playerState = playerRepository.player - val settingsState: StateFlow = settingsRepository.settingsFlow - .stateIn( - viewModelScope, - started = SharingStarted.WhileSubscribed(5.seconds.inWholeMilliseconds), - initialValue = Settings.getDefaultInstance(), - ) - } + val settingsState: StateFlow = settingsRepository.settingsFlow + .stateIn( + viewModelScope, + started = SharingStarted.WhileSubscribed(5.seconds.inWholeMilliseconds), + initialValue = Settings.getDefaultInstance(), + ) +} diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/settings/DeveloperOptionsScreenViewModel.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/settings/DeveloperOptionsScreenViewModel.kt index 5b83b73077..96b69c896c 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/settings/DeveloperOptionsScreenViewModel.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/settings/DeveloperOptionsScreenViewModel.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -23,11 +23,11 @@ import com.google.android.horologist.media.ui.snackbar.SnackbarManager import com.google.android.horologist.media.ui.snackbar.UiMessage import com.google.android.horologist.mediasample.di.IsEmulator import com.google.android.horologist.mediasample.domain.SettingsRepository -import com.google.android.horologist.mediasample.domain.proto.copy import com.google.android.horologist.networks.highbandwidth.HighBandwidthConnectionLease import com.google.android.horologist.networks.highbandwidth.HighBandwidthNetworkMediator import com.google.android.horologist.networks.request.HighBandwidthRequest import dagger.hilt.android.lifecycle.HiltViewModel +import javax.inject.Inject import kotlinx.coroutines.flow.MutableStateFlow import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.StateFlow @@ -35,122 +35,121 @@ import kotlinx.coroutines.flow.combine import kotlinx.coroutines.flow.stateIn import kotlinx.coroutines.flow.update import kotlinx.coroutines.launch -import javax.inject.Inject @HiltViewModel class DeveloperOptionsScreenViewModel - @Inject - constructor( - private val settingsRepository: SettingsRepository, - private val snackbarManager: SnackbarManager, - private val highBandwidthNetworkMediator: HighBandwidthNetworkMediator, - @IsEmulator private val isEmulator: Boolean, - ) : ViewModel() { - private val networkRequest = MutableStateFlow(null) +@Inject +constructor( + private val settingsRepository: SettingsRepository, + private val snackbarManager: SnackbarManager, + private val highBandwidthNetworkMediator: HighBandwidthNetworkMediator, + @param:IsEmulator private val isEmulator: Boolean, +) : ViewModel() { + private val networkRequest = MutableStateFlow(null) - val uiState: StateFlow = - combine(settingsRepository.settingsFlow, networkRequest) { it, networkRequest -> - UiState( - showTimeTextInfo = it.showTimeTextInfo, - podcastControls = it.podcastControls, - loadItemsAtStartup = it.loadItemsAtStartup, - animated = it.animated, - debugOffload = it.debugOffload, - writable = true, - networkRequest = networkRequest, - streamingMode = it.streamingMode, - ) - }.stateIn( - scope = viewModelScope, - started = SharingStarted.WhileSubscribed(5000), - initialValue = UiState(writable = false), + val uiState: StateFlow = + combine(settingsRepository.settingsFlow, networkRequest) { it, networkRequest -> + UiState( + showTimeTextInfo = it.showTimeTextInfo, + podcastControls = it.podcastControls, + loadItemsAtStartup = it.loadItemsAtStartup, + animated = it.animated, + debugOffload = it.debugOffload, + writable = true, + networkRequest = networkRequest, + streamingMode = it.streamingMode, ) - - data class UiState( - val showTimeTextInfo: Boolean = false, - val podcastControls: Boolean = false, - val loadItemsAtStartup: Boolean = false, - val animated: Boolean = true, - val debugOffload: Boolean = false, - val writable: Boolean = false, - val networkRequest: HighBandwidthConnectionLease? = null, - val streamingMode: Boolean = false, + }.stateIn( + scope = viewModelScope, + started = SharingStarted.WhileSubscribed(5000), + initialValue = UiState(writable = false), ) - fun setShowTimeTextInfo(enabled: Boolean) { - viewModelScope.launch { - settingsRepository.edit { - it.copy { showTimeTextInfo = enabled } - } + data class UiState( + val showTimeTextInfo: Boolean = false, + val podcastControls: Boolean = false, + val loadItemsAtStartup: Boolean = false, + val animated: Boolean = true, + val debugOffload: Boolean = false, + val writable: Boolean = false, + val networkRequest: HighBandwidthConnectionLease? = null, + val streamingMode: Boolean = false, + ) + + fun setShowTimeTextInfo(enabled: Boolean) { + viewModelScope.launch { + settingsRepository.edit { + it.toBuilder().setShowTimeTextInfo(enabled).build() } } + } - fun setPodcastControls(enabled: Boolean) { - viewModelScope.launch { - settingsRepository.edit { - it.copy { podcastControls = enabled } - } + fun setPodcastControls(enabled: Boolean) { + viewModelScope.launch { + settingsRepository.edit { + it.toBuilder().setPodcastControls(enabled).build() } } + } - fun setLoadItemsAtStartup(enabled: Boolean) { - viewModelScope.launch { - settingsRepository.edit { - it.copy { loadItemsAtStartup = enabled } - } + fun setLoadItemsAtStartup(enabled: Boolean) { + viewModelScope.launch { + settingsRepository.edit { + it.toBuilder().setLoadItemsAtStartup(enabled).build() } } + } - fun setAnimated(enabled: Boolean) { - viewModelScope.launch { - settingsRepository.edit { - it.copy { animated = enabled } - } + fun setAnimated(enabled: Boolean) { + viewModelScope.launch { + settingsRepository.edit { + it.toBuilder().setAnimated(enabled).build() } } + } - fun setDebugOffload(enabled: Boolean) { - viewModelScope.launch { - settingsRepository.edit { - it.copy { debugOffload = enabled } - } + fun setDebugOffload(enabled: Boolean) { + viewModelScope.launch { + settingsRepository.edit { + it.toBuilder().setDebugOffload(enabled).build() } } + } - fun setStreamingMode(mode: Boolean) { - viewModelScope.launch { - settingsRepository.edit { - it.copy { streamingMode = mode } - } + fun setStreamingMode(mode: Boolean) { + viewModelScope.launch { + settingsRepository.edit { + it.toBuilder().setStreamingMode(mode).build() } } + } - fun showDialog(message: String) { - snackbarManager.showMessage( - UiMessage( - message = message, - error = true, - ), - ) - } + fun showDialog(message: String) { + snackbarManager.showMessage( + UiMessage( + message = message, + error = true, + ), + ) + } - fun toggleNetworkRequest() { - networkRequest.update { - if (it != null) { - it.close() - null - } else { - val type = if (isEmulator) HighBandwidthRequest.Cell else HighBandwidthRequest.All - highBandwidthNetworkMediator.requestHighBandwidthNetwork(type) - } + fun toggleNetworkRequest() { + networkRequest.update { + if (it != null) { + it.close() + null + } else { + val type = if (isEmulator) HighBandwidthRequest.Cell else HighBandwidthRequest.All + highBandwidthNetworkMediator.requestHighBandwidthNetwork(type) } } + } - override fun onCleared() { - networkRequest.value?.close() - } + override fun onCleared() { + networkRequest.value?.close() + } - fun forceStop() { - Process.killProcess(Process.myPid()) - } + fun forceStop() { + Process.killProcess(Process.myPid()) } +} diff --git a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/settings/SettingsScreenViewModel.kt b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/settings/SettingsScreenViewModel.kt index 31af1e67cf..9eadacce1a 100644 --- a/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/settings/SettingsScreenViewModel.kt +++ b/media/sample/src/main/java/com/google/android/horologist/mediasample/ui/settings/SettingsScreenViewModel.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -22,53 +22,52 @@ import com.google.android.horologist.auth.data.common.model.AuthUser import com.google.android.horologist.mediasample.BuildConfig import com.google.android.horologist.mediasample.data.auth.GoogleSignInAuthUserRepository import com.google.android.horologist.mediasample.domain.SettingsRepository -import com.google.android.horologist.mediasample.domain.proto.copy import dagger.hilt.android.lifecycle.HiltViewModel +import javax.inject.Inject import kotlinx.coroutines.flow.SharingStarted import kotlinx.coroutines.flow.combine import kotlinx.coroutines.flow.stateIn import kotlinx.coroutines.launch -import javax.inject.Inject @HiltViewModel class SettingsScreenViewModel - @Inject - constructor( - private val settingsRepository: SettingsRepository, - private val authUserRepository: GoogleSignInAuthUserRepository, - ) : ViewModel() { - val screenState = combine( - settingsRepository.settingsFlow, - authUserRepository.authState, - ) { settings, authState -> - SettingsScreenState( - authUser = authState, - guestMode = settings.guestMode, - writable = true, - showDeveloperOptions = BuildConfig.DEBUG, - ) - }.stateIn( - viewModelScope, - SharingStarted.WhileSubscribed(5000), - SettingsScreenState( - authUser = null, - guestMode = false, - writable = false, - showDeveloperOptions = BuildConfig.DEBUG, - ), +@Inject +constructor( + private val settingsRepository: SettingsRepository, + private val authUserRepository: GoogleSignInAuthUserRepository, +) : ViewModel() { + val screenState = combine( + settingsRepository.settingsFlow, + authUserRepository.authState, + ) { settings, authState -> + SettingsScreenState( + authUser = authState, + guestMode = settings.guestMode, + writable = true, + showDeveloperOptions = BuildConfig.DEBUG, ) + }.stateIn( + viewModelScope, + SharingStarted.WhileSubscribed(5000), + SettingsScreenState( + authUser = null, + guestMode = false, + writable = false, + showDeveloperOptions = BuildConfig.DEBUG, + ), + ) - fun setGuestMode(enabled: Boolean) { - viewModelScope.launch { - settingsRepository.edit { - it.copy { guestMode = enabled } - } - if (enabled) { - authUserRepository.signOut() - } + fun setGuestMode(enabled: Boolean) { + viewModelScope.launch { + settingsRepository.edit { + it.toBuilder().setGuestMode(enabled).build() + } + if (enabled) { + authUserRepository.signOut() } } } +} data class SettingsScreenState( val authUser: AuthUser?, diff --git a/media/sync/build.gradle.kts b/media/sync/build.gradle.kts index 9764cbd7fa..44cef07569 100644 --- a/media/sync/build.gradle.kts +++ b/media/sync/build.gradle.kts @@ -19,7 +19,6 @@ plugins { alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) id("com.google.devtools.ksp") - kotlin("android") } android { @@ -40,9 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - } packaging { resources { excludes += @@ -81,7 +77,11 @@ project.tasks.withType().config metalava { filename.set("api/current.api") - hiddenAnnotations.addAll("dagger.internal.DaggerGenerated", "dagger.assisted.AssistedFactory", "javax.annotation.processing.Generated") + hiddenAnnotations.addAll( + "dagger.internal.DaggerGenerated", + "dagger.assisted.AssistedFactory", + "javax.annotation.processing.Generated", + ) } dependencies { @@ -100,11 +100,3 @@ dependencies { kspAndroidTest(libs.dagger.hiltandroidcompiler) kspAndroidTest(libs.hilt.ext.compiler) } - -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-sync") - } - } -} diff --git a/media/ui-material3/build.gradle.kts b/media/ui-material3/build.gradle.kts index 5f76ba92ab..111a6391d2 100644 --- a/media/ui-material3/build.gradle.kts +++ b/media/ui-material3/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) kotlin("plugin.serialization") alias(libs.plugins.compose.compiler) @@ -42,19 +41,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - """ - com.google.android.horologist.annotations.ExperimentalHorologistApi - kotlin.RequiresOptIn - kotlinx.coroutines.ExperimentalCoroutinesApi - """.trim().split("\\s+".toRegex()).map { - "-opt-in=$it" - } - } - packaging { resources { excludes += @@ -165,12 +151,4 @@ dependencies { testImplementation(libs.androidx.test.ext) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-ui-material3") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[0].png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[0].png index 6d396b4d83..1687f6f8a4 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[0].png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[0].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:104e45054fa198016ebcd746d5b333c3cb95e5079d24c299a8804eeb06fe9570 -size 14137 +oid sha256:2fb67de2ed97fdb67c50b0eebdbb625d3d9a51fde8b0dea08b0b7d9c0e635853 +size 14043 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[1].png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[1].png index db79a14ee4..032177fdfe 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[1].png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[1].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:fc60ef9b467e37896fb0ff226d71e970693c71859d49c864e75146e804322e15 -size 23081 +oid sha256:dc899cafdc8fc662f604dcf3ed00ffecb63eaf43523bc198dd66c2837d1503c2 +size 22997 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[2].png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[2].png index 2ed028748a..030adedf69 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[2].png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[2].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:f746dc86ab3dc819d2e0acb6252ca7f4a1c61ac1a5f8011009cd118a216baa75 -size 18774 +oid sha256:887b190e5b0566d991c474d7ee6d6c03620c38861a8dee354c5f1abf9c5eb7a5 +size 18698 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[3].png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[3].png index 01c3cf85b9..ccc0093124 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[3].png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[3].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:b4a3b58df782a8eb7cffff585eb93da8496d4fd240204938b49816dda2eabd50 -size 17393 +oid sha256:6bb6c53e48bd4cbdb7e2de4968687c6f0b26c9d807360ad43361bfed94cc157b +size 17315 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[4].png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[4].png index 54cc35be0e..dc6fc4eb34 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[4].png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[4].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:028ace58019fa7608899efff1b71f4dfb9ffec5f22bc7a3fee6ff03f6937e56c -size 15978 +oid sha256:e7a01e0440aabd2f2ff871c434068b4ef2d56915e0014b1c24dbc2d94d685a88 +size 15891 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[5].png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[5].png index 0e3613492e..af9faad396 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[5].png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[5].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:3d6f36fd9b47390278a4763f299ca171fb98bb809ebddbec04b07d173dd89d15 -size 24872 +oid sha256:0191cdc30637bda0915f0572ddce3feed7f32b132628279aa2e6a9cef1a244aa +size 24786 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[6].png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[6].png index af82bea08f..5576eaccac 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[6].png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[6].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:4bb9a244e7de7084dbe17190d65802a2b2ac9c29a8e249cac19da69a7ec3497d -size 21107 +oid sha256:b452e7c79d3840d8ba2ec2f7ef678c2d41fdf1be014a7e0e24bf054fcafdb95f +size 21027 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[7].png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[7].png index b57c32c2cd..77c1aa08e8 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[7].png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListHeaderFooterTest_test[7].png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:e7f3bb4e52ac5a2419c21d703fe0f478fe96fe50a0d1d17cbd3f15a135cf9cb6 -size 19793 +oid sha256:7bcb3aad30bcdceaa24f949e670214c830092ea448553f291dc44f94fb55bc63 +size 19713 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_emptyContentForStates.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_emptyContentForStates.png index 9ae0423c08..164855ef17 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_emptyContentForStates.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_emptyContentForStates.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:e0426803de225baef1a3db94549833b229944cad1861601630e2f45262970bce -size 22307 +oid sha256:b875a7c65c15f37a20f2c5edfda0317b55f43ad2e390ef5e0570af97172d48c9 +size 22225 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_emptySection.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_emptySection.png index 1fef4eba5d..a51792b8c3 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_emptySection.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_emptySection.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:366a54bf37237357d8762af3d25a64beb1b6a4b92483061d5d28fb00394e758a -size 22791 +oid sha256:4c5b9c14377da4bbae6c02e65c92c8c85513c9a81a792128d3e5fb7e61a45220 +size 22715 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_failedSection.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_failedSection.png index 90c054a0f8..9fddf5b0df 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_failedSection.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_failedSection.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:85c1a4be782d004193e90b2d20dbce4681c1712318c80cd90f4fbbf7ee3cd56e -size 27350 +oid sha256:93be2d6f941ad94a0aae5c32e6f29c248d5fcd00b6c20cb56e0b4d14a239ec98 +size 27266 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_loadedSection.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_loadedSection.png index 509fee0637..fa63e9ab7d 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_loadedSection.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_loadedSection.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:41c8d7bd4bfb37d4851bed1764488700feecb0e5dc75eddf196223cd44ba381e -size 27071 +oid sha256:c37ee52bb9a255164efc319b2f0d783ce7f3c636bdb4327516ea01c5c636d9a8 +size 26992 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_loadingSection.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_loadingSection.png index f8fadc7586..3b924c1338 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_loadingSection.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3.composables_SectionedListTest_loadingSection.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:6e03da645f8e13ff130bb448225d92fadf303c219180a675be5660b56b0b573f -size 25047 +oid sha256:ebb66f15cde1654d5bea0e4415e8247d56c9782aae254dd81d673a773ac7ffa8 +size 24965 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerA11yScreenshotTest_mediaPlayerLargeRound.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerA11yScreenshotTest_mediaPlayerLargeRound.png index bc2fb8f538..56922f2610 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerA11yScreenshotTest_mediaPlayerLargeRound.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerA11yScreenshotTest_mediaPlayerLargeRound.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:57aac7703db8b4745e83fb4b9e9eb6074497e7756e67413a5f8880b1f4684c50 -size 63109 +oid sha256:3794ada0aa26cfad56229df1fef9c898952c0e069f1a862a1f3b36b63723f888 +size 63007 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerA11yScreenshotTest_mediaPlayerSmallRound.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerA11yScreenshotTest_mediaPlayerSmallRound.png index deb6176289..4a284385fe 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerA11yScreenshotTest_mediaPlayerSmallRound.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerA11yScreenshotTest_mediaPlayerSmallRound.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:821d7b9b867df4d9b40cf99c99538ca482bd30d63bf812b2464795c00c38d966 -size 53489 +oid sha256:bf5613c33d8e570a248e7dc343d354c2995040b19e580cb734d8359e02d14ce2 +size 53439 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerLargeRound.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerLargeRound.png index 2fdaf9dd6f..54a9fb7483 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerLargeRound.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerLargeRound.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:79d0c1cfe2dfe27e02185bd87750321f694b1b512de2be463cd1353f4399c3a4 -size 28635 +oid sha256:357bb6f780dab71d1248a2023f17cdfd6e339ab5b5ddfd1b8c088d848255f9a2 +size 28555 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerScreen.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerScreen.png index 2fdaf9dd6f..54a9fb7483 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerScreen.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerScreen.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:79d0c1cfe2dfe27e02185bd87750321f694b1b512de2be463cd1353f4399c3a4 -size 28635 +oid sha256:357bb6f780dab71d1248a2023f17cdfd6e339ab5b5ddfd1b8c088d848255f9a2 +size 28555 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerSmallRound.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerSmallRound.png index a42d8ee044..0359b709d7 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerSmallRound.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerDeviceScreenTest_mediaPlayerSmallRound.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:20a2b3f09a11010c7ea957c883c946300464fa5b99b3318a0d31590ac9cee66a -size 25342 +oid sha256:d302cc0f8397f8a3c82e83a5cc836c606d8f8279d02c7af6bdd1d2439102ce9c +size 25271 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerScreenTest_ambientMediaPlayerScreen_defaultColorScheme.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerScreenTest_ambientMediaPlayerScreen_defaultColorScheme.png index 91d7deb6f5..defd46661c 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerScreenTest_ambientMediaPlayerScreen_defaultColorScheme.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerScreenTest_ambientMediaPlayerScreen_defaultColorScheme.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:a1d8e22b15ab6ae62a245e4ac7d1a8ff01dbea53a63b10f8f2f925005718312d -size 29898 +oid sha256:5f3bd4519089514747f5f054ba062f134e10bbec31744924d1c706f06c80ef1d +size 29811 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerScreenTest_mediaPlayerScreen_defaultColorScheme.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerScreenTest_mediaPlayerScreen_defaultColorScheme.png index 50ed05aa55..7b27736e69 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerScreenTest_mediaPlayerScreen_defaultColorScheme.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerScreenTest_mediaPlayerScreen_defaultColorScheme.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:61bba7beae02ce79ac71c8b4947f967bb9924bf99f72e5c40d980c218925376d -size 28583 +oid sha256:06ecdbed0827667cc42b1fb0b04440a71e5845bd0d1b2906082086021263f886 +size 28495 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_ambientMediaPlayerScreen[0]_nomedia.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_ambientMediaPlayerScreen[0]_nomedia.png index 91301b9994..24a6a08b57 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_ambientMediaPlayerScreen[0]_nomedia.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_ambientMediaPlayerScreen[0]_nomedia.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:995c04bf6f8b36a465dde05e7908d61763a6e31e8d37f7d41507bf8b14be83cb -size 27069 +oid sha256:edd32084b7cda4cbd6bc4ea6e53fe6b085d35832df6b4ad1ef54ad44dbc5453c +size 26982 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_ambientMediaPlayerScreen[1]_notconnected.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_ambientMediaPlayerScreen[1]_notconnected.png index 4243d074b4..d9a3cdb69e 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_ambientMediaPlayerScreen[1]_notconnected.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_ambientMediaPlayerScreen[1]_notconnected.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:2a45499a933283ba387a774da2f24194f92719e5fc9a43c436730b36ac6ad518 -size 22912 +oid sha256:4a0dd4573700e2f02a04a648105f404fec097c090587c1d4a793eda237cecc53 +size 22823 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_mediaPlayerScreen[0]_nomedia.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_mediaPlayerScreen[0]_nomedia.png index 8c34a6f404..761dee7585 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_mediaPlayerScreen[0]_nomedia.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_mediaPlayerScreen[0]_nomedia.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:d151a426832d60fcacdffb12bb496c3c6fff9c38d8248c504851fef7ed918005 -size 25779 +oid sha256:8b1b094e3e9c13a79bf60d7880d39631987d082823db9ee47e6d918265eb63dd +size 25689 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_mediaPlayerScreen[1]_notconnected.png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_mediaPlayerScreen[1]_notconnected.png index ac9cf562be..895ce7c19e 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_mediaPlayerScreen[1]_notconnected.png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_MediaPlayerStatesScreenTest_mediaPlayerScreen[1]_notconnected.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:5c0bdc9bab8c80dbe52c73901d271c7d5fafec5768ddc951af28dfcb164ca37e -size 23620 +oid sha256:a3ee0e5d7485bc35e4a010ffc857e2c2e703f776d8989d42d42c02986888c348 +size 23525 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[0]_seekbuttonincrement(unknown)_seekbuttonincrement(unknown).png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[0]_seekbuttonincrement(unknown)_seekbuttonincrement(unknown).png index f54a2a49a7..d0fe594184 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[0]_seekbuttonincrement(unknown)_seekbuttonincrement(unknown).png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[0]_seekbuttonincrement(unknown)_seekbuttonincrement(unknown).png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:97b15d58e9dae48b1ff092651e197c2bc7b86920378479befcdd7f81153aa192 -size 28223 +oid sha256:23502e7eb35da35d16bca6f2ba1a91ae246f64751aa98eb3ae3a20170b0ce3f3 +size 28137 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[1]_known(seconds=10)_known(seconds=10).png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[1]_known(seconds=10)_known(seconds=10).png index f2f1b125e6..3105673b12 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[1]_known(seconds=10)_known(seconds=10).png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[1]_known(seconds=10)_known(seconds=10).png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:48d8728fee19828d389635a3ad527bfc587cd5bd13667cacc68d556ffab5e9f9 -size 28782 +oid sha256:e0d72e646dfc21b6eda3c2863c3863a6cc4a1c253418b20b3f72804029b7abac +size 28697 diff --git a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[2]_known(seconds=5)_known(seconds=30).png b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[2]_known(seconds=5)_known(seconds=30).png index 3926f28c18..2904a5ddda 100644 --- a/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[2]_known(seconds=5)_known(seconds=30).png +++ b/media/ui-material3/src/test/snapshots/images/com.google.android.horologist.media.ui.material3_PodcastPlayerScreenTest_mediaPlayerScreen[2]_known(seconds=5)_known(seconds=30).png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:f8389b3be252f7495e2370567d7dae70dec93cc0f86d7aa8c83c5e78fb6fb14a -size 28657 +oid sha256:177c53e702ad090cdbdf3898705602b7665578cd77abffb89dc0cd35ef74eca3 +size 28572 diff --git a/media/ui-model/build.gradle.kts b/media/ui-model/build.gradle.kts index 3d8965019a..880edca111 100644 --- a/media/ui-model/build.gradle.kts +++ b/media/ui-model/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) kotlin("plugin.serialization") alias(libs.plugins.compose.compiler) @@ -42,19 +41,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - """ - com.google.android.horologist.annotations.ExperimentalHorologistApi - kotlin.RequiresOptIn - kotlinx.coroutines.ExperimentalCoroutinesApi - """.trim().split("\\s+".toRegex()).map { - "-opt-in=$it" - } - } - packaging { resources { excludes += @@ -113,12 +99,4 @@ dependencies { testImplementation(libs.robolectric) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-ui-model") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/ui/build.gradle.kts b/media/ui/build.gradle.kts index 58084959df..7ce9296e9a 100644 --- a/media/ui/build.gradle.kts +++ b/media/ui/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) kotlin("plugin.serialization") alias(libs.plugins.compose.compiler) @@ -42,19 +41,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - """ - com.google.android.horologist.annotations.ExperimentalHorologistApi - kotlin.RequiresOptIn - kotlinx.coroutines.ExperimentalCoroutinesApi - """.trim().split("\\s+".toRegex()).map { - "-opt-in=$it" - } - } - packaging { resources { excludes += @@ -163,12 +149,4 @@ dependencies { testImplementation(libs.androidx.test.ext) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("media-ui") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/media/ui/src/main/java/com/google/android/horologist/media/ui/complication/MediaStatusTemplate.kt b/media/ui/src/main/java/com/google/android/horologist/media/ui/complication/MediaStatusTemplate.kt index 6626f53a5f..78dbfd3ab1 100644 --- a/media/ui/src/main/java/com/google/android/horologist/media/ui/complication/MediaStatusTemplate.kt +++ b/media/ui/src/main/java/com/google/android/horologist/media/ui/complication/MediaStatusTemplate.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -34,81 +34,79 @@ import com.google.android.horologist.tiles.complication.DataTemplates.shortText import com.google.android.horologist.tiles.complication.DataTemplates.smallImage import com.google.android.horologist.tiles.complication.TypedComplicationTemplate -public class MediaStatusTemplate( - context: Context, -) : +public class MediaStatusTemplate(context: Context) : TypedComplicationTemplate(context) { - public data class Data( - @DrawableRes public val appIconRes: Int? = null, - public val icon: Icon? = null, - public val type: SmallImageType, - public val title: String?, - public val text: String, - public val launchIntent: PendingIntent?, - public val contentDescription: ComplicationText? = null, - ) - - override fun previewData(): Data = Data( - title = context.getString(com.google.android.horologist.media.ui.model.R.string.horologist_preview_app_name), - text = context.getString(com.google.android.horologist.media.ui.model.R.string.horologist_preview_favorites), - appIconRes = R.drawable.ic_baseline_queue_music_24, - type = SmallImageType.ICON, - launchIntent = null, - ) + public data class Data( + @param:DrawableRes public val appIconRes: Int? = null, + public val icon: Icon? = null, + public val type: SmallImageType, + public val title: String?, + public val text: String, + public val launchIntent: PendingIntent?, + public val contentDescription: ComplicationText? = null, + ) - override fun supportedTypes(): List = - listOf( - ComplicationType.SMALL_IMAGE, - ComplicationType.SHORT_TEXT, - ComplicationType.LONG_TEXT, - ComplicationType.PHOTO_IMAGE, - ) + override fun previewData(): Data = Data( + title = context.getString( + com.google.android.horologist.media.ui.model.R.string.horologist_preview_app_name, + ), + text = context.getString( + com.google.android.horologist.media.ui.model.R.string.horologist_preview_favorites, + ), + appIconRes = R.drawable.ic_baseline_queue_music_24, + type = SmallImageType.ICON, + launchIntent = null, + ) - override fun renderShortText(data: Data): ShortTextComplicationData = - shortText( - title = data.title, - text = data.text, - icon = data.appIconRes, - launchIntent = data.launchIntent, - contentDescription = data.contentDescription, - ) + override fun supportedTypes(): List = listOf( + ComplicationType.SMALL_IMAGE, + ComplicationType.SHORT_TEXT, + ComplicationType.LONG_TEXT, + ComplicationType.PHOTO_IMAGE, + ) - override fun renderSmallImage(data: Data): SmallImageComplicationData? { - if (data.icon == null) { - return null - } + override fun renderShortText(data: Data): ShortTextComplicationData = shortText( + title = data.title, + text = data.text, + icon = data.appIconRes, + launchIntent = data.launchIntent, + contentDescription = data.contentDescription, + ) - return smallImage( - icon = data.icon, - type = data.type, - name = data.text, - launchIntent = data.launchIntent, - contentDescription = data.contentDescription, - ) + override fun renderSmallImage(data: Data): SmallImageComplicationData? { + if (data.icon == null) { + return null } - override fun renderLongText(data: Data): LongTextComplicationData { - return longText( - icon = data.icon, - type = data.type, - title = data.title, - text = data.text, - launchIntent = data.launchIntent, - contentDescription = data.contentDescription, - ) - } + return smallImage( + icon = data.icon, + type = data.type, + name = data.text, + launchIntent = data.launchIntent, + contentDescription = data.contentDescription, + ) + } - override fun renderPhotoImage(data: Data): PhotoImageComplicationData? { - if (data.icon == null) { - return null - } + override fun renderLongText(data: Data): LongTextComplicationData = longText( + icon = data.icon, + type = data.type, + title = data.title, + text = data.text, + launchIntent = data.launchIntent, + contentDescription = data.contentDescription, + ) - return photoImage( - photoImage = data.icon, - name = data.text, - launchIntent = data.launchIntent, - contentDescription = data.contentDescription, - ) + override fun renderPhotoImage(data: Data): PhotoImageComplicationData? { + if (data.icon == null) { + return null } + + return photoImage( + photoImage = data.icon, + name = data.text, + launchIntent = data.launchIntent, + contentDescription = data.contentDescription, + ) } +} diff --git a/media/ui/src/main/java/com/google/android/horologist/media/ui/screens/browse/BrowseScreen.kt b/media/ui/src/main/java/com/google/android/horologist/media/ui/screens/browse/BrowseScreen.kt index a2cc9d58e8..db7cec69e2 100644 --- a/media/ui/src/main/java/com/google/android/horologist/media/ui/screens/browse/BrowseScreen.kt +++ b/media/ui/src/main/java/com/google/android/horologist/media/ui/screens/browse/BrowseScreen.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -58,10 +58,7 @@ import com.google.android.horologist.media.ui.state.model.PlaylistDownloadUiMode */ @ExperimentalHorologistApi @Composable -public fun BrowseScreen( - modifier: Modifier = Modifier, - content: BrowseScreenScope.() -> Unit, -) { +public fun BrowseScreen(modifier: Modifier = Modifier, content: BrowseScreenScope.() -> Unit) { val columnState = rememberResponsiveColumnState( contentPadding = padding( first = ItemType.Text, @@ -245,16 +242,14 @@ public sealed class BrowseScreenState { public object Loading : BrowseScreenState() - public data class Loaded( - val downloadList: List, - ) : BrowseScreenState() + public data class Loaded(val downloadList: List) : BrowseScreenState() public object Failed : BrowseScreenState() } @ExperimentalHorologistApi public data class BrowseScreenPlaylistsSectionButton( - @StringRes val textId: Int, + @param:StringRes val textId: Int, val icon: ImageVector, val onClick: () -> Unit, ) diff --git a/media/ui/src/main/java/com/google/android/horologist/media/ui/tiles/MediaCollectionsTileRenderer.kt b/media/ui/src/main/java/com/google/android/horologist/media/ui/tiles/MediaCollectionsTileRenderer.kt index 6699f78671..d51cfe10d7 100644 --- a/media/ui/src/main/java/com/google/android/horologist/media/ui/tiles/MediaCollectionsTileRenderer.kt +++ b/media/ui/src/main/java/com/google/android/horologist/media/ui/tiles/MediaCollectionsTileRenderer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -46,7 +46,10 @@ public class MediaCollectionsTileRenderer( context: Context, private val materialTheme: Colors, debugResourceMode: Boolean, -) : SingleTileLayoutRenderer( +) : SingleTileLayoutRenderer< + MediaCollectionsTileRenderer.MediaCollectionsState, + MediaCollectionsTileRenderer.ResourceState, + >( context, debugResourceMode, ) { @@ -59,59 +62,54 @@ public class MediaCollectionsTileRenderer( override fun renderTile( state: MediaCollectionsState, deviceParameters: DeviceParameters, - ): LayoutElementBuilders.LayoutElement { - return PrimaryLayout.Builder(deviceParameters) - .setResponsiveContentInsetEnabled(true) - .setContent( - Column.Builder() - .setWidth(expandedDimensionProp) - .setHeight(wrapDimensionProp) - .addContent( - collectionChip( - state.collection1, - deviceParameters, - ), - ) - .addContent(spacer(4f)) - .addContent( - collectionChip( - state.collection2, - deviceParameters, - ), - ).build(), - ).setPrimaryChipContent( - CompactChip.Builder( - context, - context.getString(state.chipName), - Clickable.Builder().setOnClick( - state.chipAction, - ).build(), - deviceParameters, - ).setChipColors(ChipColors.primaryChipColors(theme)).build(), - ).build() - } + ): LayoutElementBuilders.LayoutElement = PrimaryLayout.Builder(deviceParameters) + .setResponsiveContentInsetEnabled(true) + .setContent( + Column.Builder() + .setWidth(expandedDimensionProp) + .setHeight(wrapDimensionProp) + .addContent( + collectionChip( + state.collection1, + deviceParameters, + ), + ) + .addContent(spacer(4f)) + .addContent( + collectionChip( + state.collection2, + deviceParameters, + ), + ).build(), + ).setPrimaryChipContent( + CompactChip.Builder( + context, + context.getString(state.chipName), + Clickable.Builder().setOnClick( + state.chipAction, + ).build(), + deviceParameters, + ).setChipColors(ChipColors.primaryChipColors(theme)).build(), + ).build() - override fun getResourcesVersionForTileState(state: MediaCollectionsState): String { - return state.collection1.artworkId + ":" + state.collection2.artworkId - } + override fun getResourcesVersionForTileState(state: MediaCollectionsState): String = + state.collection1.artworkId + ":" + state.collection2.artworkId private fun spacer(size: Float) = Spacer.Builder().setHeight( DimensionBuilders.DpProp.Builder(size).build(), ).build() - private fun collectionChip( - collection: MediaCollection, - deviceParameters: DeviceParameters, - ) = Chip.Builder( - context, - Clickable.Builder().setOnClick(collection.action).build(), - deviceParameters, - ) - .setChipColors(ChipColors.secondaryChipColors(theme)) - .setPrimaryLabelContent(collection.name) - .setIconContent(collection.artworkId) - .setWidth(expandedDimensionProp) - .build() + private fun collectionChip(collection: MediaCollection, deviceParameters: DeviceParameters) = + Chip.Builder( + context, + Clickable.Builder().setOnClick(collection.action).build(), + deviceParameters, + ) + .setChipColors(ChipColors.secondaryChipColors(theme)) + .setPrimaryLabelContent(collection.name) + .setIconContent(collection.artworkId) + .setWidth(expandedDimensionProp) + .build() override fun Resources.Builder.produceRequestedResources( resourceState: ResourceState, @@ -132,14 +130,14 @@ public class MediaCollectionsTileRenderer( ) public data class MediaCollectionsState( - @StringRes public val chipName: Int, + @param:StringRes public val chipName: Int, public val chipAction: ActionBuilders.Action, public val collection1: MediaCollection, public val collection2: MediaCollection, ) public data class ResourceState( - @DrawableRes public val appIcon: Int, + @param:DrawableRes public val appIcon: Int, public val images: Map, ) } diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_largeRound.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_largeRound.png index bab248502e..0a5ea0865e 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_largeRound.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_largeRound.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:621703830dab568a55ce321ca1a7176eb19f8607220f2529fb871399dafff3ed -size 20685 +oid sha256:72b51b2c8c95b5657e34cbb32772f8ce8bb13591ab4c075d669d543a844d6fac +size 20597 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_smallRound.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_smallRound.png index ce10b08ff0..3cc341014c 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_smallRound.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_smallRound.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:b2a7d4d17619ff98ff9450ee9dea868f2473de2d0ad61e112ada368494d48de0 -size 19249 +oid sha256:cafd44084867f3c9bfc38174b277bcd457b04860ec63af50948d7876e33d6781 +size 19176 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_square.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_square.png index af7a1b3530..232089a80d 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_square.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui.tiles_MediaCollectionsTileTest_square.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:0f247ff7fbea80c596b210366bda9f76a957203bbe3aa0ed929a08670274202c -size 14263 +oid sha256:da7c23fbf66f9ec6d1184d6b20c7965c46bdc394d7a2105c195eedb988e7cd24 +size 14160 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerA11yScreenshotTest_mediaPlayerLargeRound.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerA11yScreenshotTest_mediaPlayerLargeRound.png index a46e6a98b8..57cc4a4112 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerA11yScreenshotTest_mediaPlayerLargeRound.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerA11yScreenshotTest_mediaPlayerLargeRound.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:203854e8498553892a5932842fa19edf2f6f2d25ff0d8c272b396ad694d9f599 -size 118427 +oid sha256:6f9d2d5ee1077a617a0c198ea967ff13a72e9005fdf5f70ba3808f521ea9b845 +size 118337 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerA11yScreenshotTest_mediaPlayerSmallRound.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerA11yScreenshotTest_mediaPlayerSmallRound.png index 91b3a7016e..8669ee0683 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerA11yScreenshotTest_mediaPlayerSmallRound.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerA11yScreenshotTest_mediaPlayerSmallRound.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:e735aff745e79a1c2b07abdce7f73b85ae44b95b9c13f5b96ab23719d8674ca6 -size 95348 +oid sha256:81f7493214c683c598d4943943f5b2b2c15729fe10e81deeee2a8a804d22210c +size 95297 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerLargeRound.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerLargeRound.png index b0e82c223d..13a5b68f0c 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerLargeRound.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerLargeRound.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:6ba117e284f105ab6351cb705db39e888c08645bf2663a5fd230248c9fdd4fdb -size 107376 +oid sha256:e842fa03afbaad17f962212a56decb559f3bd021af9eceace4589dc117a77da6 +size 107249 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerScreen.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerScreen.png index b0e82c223d..13a5b68f0c 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerScreen.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerScreen.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:6ba117e284f105ab6351cb705db39e888c08645bf2663a5fd230248c9fdd4fdb -size 107376 +oid sha256:e842fa03afbaad17f962212a56decb559f3bd021af9eceace4589dc117a77da6 +size 107249 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerSmallRound.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerSmallRound.png index 443cda78e8..6b7840dcfd 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerSmallRound.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerSmallRound.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:eb448226310fa3a39fb04d3a4023dae5042cff09d5798413b852bf0f86762e5a -size 83114 +oid sha256:71940d42ccd15b6f86dc437511d7eebc20630280827281ad1aa1718d5af45d3b +size 83025 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerSquare.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerSquare.png index 0f7dce0361..439722d59f 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerSquare.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerDeviceScreenTest_mediaPlayerSquare.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:6b2c694d0714f25d0c33aed8c64052c27eff2752e4c98ff4f315897a90cff098 -size 53061 +oid sha256:ffb90b8ad4c2e460465a1f8f8161297788b127412da255a126c1bd92af2f3061 +size 52974 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[0]_bluedefaultaecbfa.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[0]_bluedefaultaecbfa.png index a2adb6dc3f..53fa40363d 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[0]_bluedefaultaecbfa.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[0]_bluedefaultaecbfa.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:a397d7ac170519c09159c614bc7f6df6601b4e545925b917aa6cbf480de7791e -size 126325 +oid sha256:bee6b0c9b7f950b7747fdfcdd9955f57bd69014709fcce6a5c4a3b8474200b2f +size 126237 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[1]_blue7fcfff.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[1]_blue7fcfff.png index acd2957a73..bd875c2989 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[1]_blue7fcfff.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[1]_blue7fcfff.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:cac155445669188c31e19419e5af5ac126725add467c129b017d91bc458d9dc7 -size 123987 +oid sha256:719cc684401ca485146157fbb6758e9d700064d1cacaa35f2bb249bcc3250293 +size 123933 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[2]_lilacd0bcff.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[2]_lilacd0bcff.png index 2d3cbb6faa..3e783a6a99 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[2]_lilacd0bcff.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[2]_lilacd0bcff.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:48e365ceeb6794b64dc8eabd0c32d32267ca9032ac778549ce264791e8cffacb -size 126938 +oid sha256:e904a7b0cef5607b6b619b79e39dabeb82debbd1f19d64507a9e6ecedb2c3d3b +size 126872 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[3]_green6dd58c.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[3]_green6dd58c.png index 6f61f99263..bf3e80c9d4 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[3]_green6dd58c.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[3]_green6dd58c.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:df39b79f97c3a60016563e245fdf8a20b700ff291bd7c0b5853062ae3d94ad40 -size 119379 +oid sha256:ffb16b87d71491c677fabbea9a0b22112a5521dae60c5b1dd55502855a1ac292 +size 119264 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[4]_bluewithtext7fcfff.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[4]_bluewithtext7fcfff.png index 49b543ffdf..30df5a7675 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[4]_bluewithtext7fcfff.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[4]_bluewithtext7fcfff.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:fa86e7aa14af9616fe03bf68a727684961337e5dc333287227c9366353334026 -size 123906 +oid sha256:58a51fd910eac66128239347e25e1a5201ccc9b2a316474793ce9a91222135bf +size 123856 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[5]_orangey.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[5]_orangey.png index 3d2631ab3d..68226a9324 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[5]_orangey.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[5]_orangey.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:ccf02d131d5f44169e7a4502ccbe905af44d275f2dbd7cc6d2bb2e4f6d9216e6 -size 126289 +oid sha256:485e48ff4c374fe24e8293f4397c71a6018dc42cda7074c02f8c7b81f07c9740 +size 126200 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[6]_uamp.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[6]_uamp.png index 233510f280..5379eaeb60 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[6]_uamp.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerScreenTest_mediaPlayerScreen[6]_uamp.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:b4b8f743c9afc5b10f5ad390633bee369f21c3c874dbc55bf06b564cd62e44e3 -size 107403 +oid sha256:8743c36e318c05dce047a02e49aa296d03d43200489c7323a49d693a106c9d06 +size 107273 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerStatesScreenTest_mediaPlayerScreen[0]_nomedia.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerStatesScreenTest_mediaPlayerScreen[0]_nomedia.png index 292a06fc44..2deb13dc05 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerStatesScreenTest_mediaPlayerScreen[0]_nomedia.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerStatesScreenTest_mediaPlayerScreen[0]_nomedia.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:b499843b2d51df4a879be2f6b37b5ceef6fdec905af45cdd45ac057e3c5f0235 -size 122767 +oid sha256:fe4dc45e9bc1ab275077f0f74a4f7ab0cc739d49f110d08fbbbab5223bd44e36 +size 122661 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerStatesScreenTest_mediaPlayerScreen[1]_notconnected.png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerStatesScreenTest_mediaPlayerScreen[1]_notconnected.png index 7b0ec61703..d07c799966 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerStatesScreenTest_mediaPlayerScreen[1]_notconnected.png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_MediaPlayerStatesScreenTest_mediaPlayerScreen[1]_notconnected.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:2544552ca6063430430f2593e42dd755c63377c2fccfb6e940714377e3befe5e -size 124604 +oid sha256:77a0142c40cfcb184145f3cdfaf4180d2ced29209c7dae5cd0297354f4d465b3 +size 124503 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[0]_seekbuttonincrement(unknown)_seekbuttonincrement(unknown).png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[0]_seekbuttonincrement(unknown)_seekbuttonincrement(unknown).png index 4b86972d8c..2c1106c7d1 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[0]_seekbuttonincrement(unknown)_seekbuttonincrement(unknown).png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[0]_seekbuttonincrement(unknown)_seekbuttonincrement(unknown).png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:527ddefb05600d37f3193df6342c3f764093e54179c805b7bc71e6ef844c2b0c -size 126365 +oid sha256:45c535674f14230a1b2c773e083463a02ab2e34674aa8a6cec4a5859577fc12f +size 126267 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[1]_known(seconds=10)_known(seconds=10).png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[1]_known(seconds=10)_known(seconds=10).png index b74040c241..09809f8f86 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[1]_known(seconds=10)_known(seconds=10).png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[1]_known(seconds=10)_known(seconds=10).png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:841f89301afb2e40ba423c268deaff8c96353e373b03c29925ed123f3904b0a5 -size 126908 +oid sha256:c5f7f81c50be038b1e42b22f8500c5361ed0eff13e77f3e7fe18330feaf1f574 +size 126805 diff --git a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[2]_known(seconds=5)_known(seconds=30).png b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[2]_known(seconds=5)_known(seconds=30).png index 2e7720104f..bb22967daf 100644 --- a/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[2]_known(seconds=5)_known(seconds=30).png +++ b/media/ui/src/test/snapshots/images/com.google.android.horologist.media.ui_PodcastPlayerScreenTest_mediaPlayerScreen[2]_known(seconds=5)_known(seconds=30).png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:d801b0f68cc1252f91e8d1e504270ef7b8ae2e5d5ca220c3d556b2f8db3be8e0 -size 126900 +oid sha256:8b33ab6af1d47e4c301786489f24cea061dc4a27c19d05713184c9a581e90a8e +size 126803 diff --git a/network-awareness/core/build.gradle.kts b/network-awareness/core/build.gradle.kts index 3bb7ba1c15..db5fd11685 100644 --- a/network-awareness/core/build.gradle.kts +++ b/network-awareness/core/build.gradle.kts @@ -20,7 +20,6 @@ plugins { id("com.google.devtools.ksp") alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -37,12 +36,6 @@ android { targetCompatibility = JavaVersion.VERSION_17 } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=kotlin.RequiresOptIn" - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -105,12 +98,4 @@ dependencies { androidTestImplementation(libs.kotlinx.coroutines.test) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("network-awareness-core") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/network-awareness/db/build.gradle.kts b/network-awareness/db/build.gradle.kts index e063c15465..325cde9c69 100644 --- a/network-awareness/db/build.gradle.kts +++ b/network-awareness/db/build.gradle.kts @@ -19,7 +19,6 @@ plugins { alias(libs.plugins.dokka) id("com.google.devtools.ksp") alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -40,12 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=kotlin.RequiresOptIn" - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -116,12 +109,4 @@ dependencies { androidTestImplementation(libs.truth) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("network-awareness-db") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/network-awareness/okhttp/build.gradle.kts b/network-awareness/okhttp/build.gradle.kts index 2ed6a12e12..3dfe3b4645 100644 --- a/network-awareness/okhttp/build.gradle.kts +++ b/network-awareness/okhttp/build.gradle.kts @@ -19,7 +19,6 @@ plugins { alias(libs.plugins.dokka) id("com.google.devtools.ksp") alias(libs.plugins.metalavaGradle) - kotlin("android") } android { @@ -40,12 +39,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=kotlin.RequiresOptIn" - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -106,12 +99,4 @@ dependencies { testImplementation(libs.com.squareup.okhttp3.mockwebserver) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("network-awareness-okhttp") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/network-awareness/ui/build.gradle.kts b/network-awareness/ui/build.gradle.kts index b7af3c2a20..2236516eba 100644 --- a/network-awareness/ui/build.gradle.kts +++ b/network-awareness/ui/build.gradle.kts @@ -19,7 +19,6 @@ plugins { alias(libs.plugins.dokka) id("com.google.devtools.ksp") alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.compose.compiler) } @@ -41,12 +40,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=kotlin.RequiresOptIn" - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += @@ -120,12 +113,4 @@ dependencies { androidTestImplementation(libs.truth) } -tasks.withType().configureEach { - dokkaSourceSets { - configureEach { - moduleName.set("network-awareness-ui") - } - } -} - apply(plugin = "com.vanniktech.maven.publish") diff --git a/quality/ktlint/.editorconfig b/quality/ktlint/.editorconfig index 6755098c31..ff6ad919a6 100644 --- a/quality/ktlint/.editorconfig +++ b/quality/ktlint/.editorconfig @@ -1,2 +1,17 @@ +[*] +end_of_line = lf +indent_style = space +insert_final_newline = true +trim_trailing_whitespace = true + +[**/generated/**/*] +ktlint = disabled + [*.{kt,kts}] -ktlint_code_style = ktlint_official \ No newline at end of file +ij_kotlin_allow_trailing_comma = true +ij_kotlin_allow_trailing_comma_on_call_site = true +ktlint_code_style = android_studio +ktlint_function_naming_ignore_when_annotated_with=Composable + +[*.md] +trim_trailing_whitespace = false diff --git a/roboscreenshots/build.gradle.kts b/roboscreenshots/build.gradle.kts index 8f03216a11..82661cc4fb 100644 --- a/roboscreenshots/build.gradle.kts +++ b/roboscreenshots/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.compose.compiler) } @@ -39,12 +38,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = - freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes += diff --git a/sample/build.gradle.kts b/sample/build.gradle.kts index e5891bf84e..30e26fdb18 100644 --- a/sample/build.gradle.kts +++ b/sample/build.gradle.kts @@ -20,7 +20,6 @@ import java.util.Locale plugins { id("com.android.application") - kotlin("android") alias(libs.plugins.roborazzi) kotlin("plugin.serialization") alias(libs.plugins.compose.compiler) @@ -67,22 +66,6 @@ android { targetCompatibility = JavaVersion.VERSION_17 } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - // Allow for widescale experimental APIs in Alpha libraries we build upon - freeCompilerArgs = freeCompilerArgs + - """ - androidx.compose.ui.ExperimentalComposeUiApi - androidx.wear.compose.material.ExperimentalWearMaterialApi - com.google.android.horologist.annotations.ExperimentalHorologistApi - androidx.compose.foundation.ExperimentalFoundationApi - kotlin.RequiresOptIn - kotlinx.coroutines.ExperimentalCoroutinesApi - """.trim().split("\\s+".toRegex()).map { - "-opt-in=$it" - } - } - testOptions { unitTests { isIncludeAndroidResources = true diff --git a/sample/src/main/java/com/google/android/horologist/paging/PagingScreen.kt b/sample/src/main/java/com/google/android/horologist/paging/PagingScreen.kt index 7e2f7a936b..03a5e6d234 100644 --- a/sample/src/main/java/com/google/android/horologist/paging/PagingScreen.kt +++ b/sample/src/main/java/com/google/android/horologist/paging/PagingScreen.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -14,6 +14,8 @@ * limitations under the License. */ +@file:OptIn(ExperimentalWearMaterialApi::class) + package com.google.android.horologist.paging import androidx.compose.foundation.layout.Column @@ -37,6 +39,7 @@ import androidx.paging.PagingSource import androidx.paging.PagingState import androidx.paging.compose.collectAsLazyPagingItems import androidx.wear.compose.material.CardDefaults +import androidx.wear.compose.material.ExperimentalWearMaterialApi import androidx.wear.compose.material.PlaceholderDefaults import androidx.wear.compose.material.PlaceholderState import androidx.wear.compose.material.Text @@ -49,11 +52,11 @@ import com.google.android.horologist.compose.layout.ScalingLazyColumnState import com.google.android.horologist.compose.layout.rememberActivePlaceholderState import com.google.android.horologist.compose.paging.items import com.google.android.horologist.sample.R -import kotlinx.coroutines.delay import java.time.LocalTime import java.time.format.DateTimeFormatter import kotlin.math.ceil import kotlin.time.Duration.Companion.seconds +import kotlinx.coroutines.delay @Composable fun PagingScreen( @@ -193,23 +196,16 @@ private class MyBackend { ) } - override fun getRefreshKey(state: PagingState): Int { - return ( - (state.anchorPosition ?: 0) - - state.config.initialLoadSize / 2.coerceAtLeast(0) - ) - } + override fun getRefreshKey(state: PagingState): Int = ( + (state.anchorPosition ?: 0) - + state.config.initialLoadSize / 2.coerceAtLeast(0) + ) } } } -data class PagingItem( - val item: Int, - val loadedAt: LocalTime = LocalTime.now(), -) { - override fun toString(): String { - return "$item (${loadedAt.format(timeFormatter)})" - } +data class PagingItem(val item: Int, val loadedAt: LocalTime = LocalTime.now()) { + override fun toString(): String = "$item (${loadedAt.format(timeFormatter)})" companion object { private val timeFormatter: DateTimeFormatter = DateTimeFormatter.ofPattern("hh:mm:ss") diff --git a/sample/src/main/java/com/google/android/horologist/sample/tiles/ComposableTileService.kt b/sample/src/main/java/com/google/android/horologist/sample/tiles/ComposableTileService.kt index dc60a01d8f..7bb9509f9c 100644 --- a/sample/src/main/java/com/google/android/horologist/sample/tiles/ComposableTileService.kt +++ b/sample/src/main/java/com/google/android/horologist/sample/tiles/ComposableTileService.kt @@ -1,5 +1,5 @@ /* - * Copyright 2025 The Android Open Source Project + * Copyright 2025-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -40,9 +40,10 @@ import com.google.android.horologist.tiles.composable.ServiceComposableBitmapRen import com.google.android.horologist.tiles.images.toImageResource import java.util.UUID +@Deprecated("Use Material3TileService instead") class ComposableTileService : SuspendingTileService() { private lateinit var renderer: ServiceComposableBitmapRenderer - val ComposeId = "circleCompose" + val composeId = "circleCompose" override fun onCreate() { super.onCreate() @@ -51,11 +52,12 @@ class ComposableTileService : SuspendingTileService() { } /** This method returns a Tile object, which describes the layout of the Tile. */ + @Suppress("DEPRECATION") override suspend fun tileRequest(requestParams: TileRequest): Tile { val layoutElement = LayoutElementBuilders.Box.Builder().setWidth(expand()).setHeight(expand()).addContent( LayoutElementBuilders.Image.Builder().setWidth(dp(100f)).setHeight(dp(100f)) - .setResourceId(ComposeId).build(), + .setResourceId(composeId).build(), ).build() return Tile.Builder().setResourcesVersion(UUID.randomUUID().toString()) @@ -68,7 +70,7 @@ class ComposableTileService : SuspendingTileService() { return Resources.Builder().setVersion(requestParams.version).apply { if (circleComposeBitmap != null) { addIdToImageMapping( - ComposeId, + composeId, circleComposeBitmap.toImageResource(), ) } diff --git a/sample/src/main/java/com/google/android/horologist/sectionedlist/stateful/SectionedListStatefulScreen.kt b/sample/src/main/java/com/google/android/horologist/sectionedlist/stateful/SectionedListStatefulScreen.kt index 06f6f9c5ba..d74b049ee0 100644 --- a/sample/src/main/java/com/google/android/horologist/sectionedlist/stateful/SectionedListStatefulScreen.kt +++ b/sample/src/main/java/com/google/android/horologist/sectionedlist/stateful/SectionedListStatefulScreen.kt @@ -1,5 +1,5 @@ /* - * Copyright 2022 The Android Open Source Project + * Copyright 2022-2026 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -14,6 +14,8 @@ * limitations under the License. */ +@file:OptIn(ExperimentalWearMaterialApi::class) + package com.google.android.horologist.sectionedlist.stateful import androidx.compose.foundation.clickable @@ -41,6 +43,7 @@ import androidx.compose.ui.unit.dp import androidx.lifecycle.compose.collectAsStateWithLifecycle import androidx.lifecycle.viewmodel.compose.viewModel import androidx.wear.compose.material.ChipDefaults +import androidx.wear.compose.material.ExperimentalWearMaterialApi import androidx.wear.compose.material.Icon import androidx.wear.compose.material.MaterialTheme import androidx.wear.compose.material.Text @@ -108,6 +111,7 @@ private fun SectionedListScope.recommendationsSection( val recommendationsState: Section.State = when (val recommendationSectionState = state.recommendationSectionState) { RecommendationSectionState.Loading -> Section.State.Loading + is RecommendationSectionState.Loaded -> Section.State.Loaded( recommendationSectionState.list, ) @@ -159,6 +163,7 @@ private fun SectionedListScope.trendingSection( val trendingState: Section.State = when (val recommendationSectionState = state.trendingSectionState) { TrendingSectionState.Loading -> Section.State.Loading + is TrendingSectionState.Loaded -> Section.State.Loaded( recommendationSectionState.list, ) diff --git a/settings.gradle.kts b/settings.gradle.kts index 34bee3e888..ec4226338a 100644 --- a/settings.gradle.kts +++ b/settings.gradle.kts @@ -28,6 +28,7 @@ develocity { rootProject.name = "horologist" include(":ai:sample:core") +include(":ai:sample:core-proto") include(":ai:sample:phone") include(":ai:sample:wear-core") include(":ai:sample:wear-prompt-app") @@ -41,6 +42,7 @@ include(":auth:data") include(":auth:data-phone") include(":auth:sample:phone") include(":auth:sample:shared") +include(":auth:sample:shared-proto") include(":auth:sample:wear") include(":auth:ui") include(":auth:ui-material3") @@ -49,13 +51,17 @@ include(":compose-material") include(":compose-tools") include(":composables") include(":datalayer:core") +include(":datalayer:core-proto") include(":datalayer:grpc") +include(":datalayer:grpc-proto") include(":datalayer:watch") include(":datalayer:phone") include(":datalayer:phone-ui") include(":datalayer:sample:phone") include(":datalayer:sample:shared") +include(":datalayer:sample:shared-proto") include(":datalayer:sample:wear") +include(":datalayer:sample:wear-proto") include(":health:composables") include(":health:service") include(":images:base") @@ -75,6 +81,7 @@ include(":media:ui-model") include(":media:benchmark") include(":media:data") include(":media:sample") +include(":media:sample-proto") include(":media:sample-benchmark") include(":media:sync") include(":network-awareness:core") diff --git a/tiles/build.gradle.kts b/tiles/build.gradle.kts index 561108b5f5..1341c3f2d1 100644 --- a/tiles/build.gradle.kts +++ b/tiles/build.gradle.kts @@ -18,7 +18,6 @@ plugins { id("com.android.library") alias(libs.plugins.dokka) alias(libs.plugins.metalavaGradle) - kotlin("android") alias(libs.plugins.roborazzi) alias(libs.plugins.compose.compiler) } @@ -43,11 +42,6 @@ android { buildConfig = false } - kotlinOptions { - jvmTarget = JavaVersion.VERSION_17.majorVersion - freeCompilerArgs = freeCompilerArgs + "-opt-in=com.google.android.horologist.annotations.ExperimentalHorologistApi" - } - packaging { resources { excludes +=