提问人:Dzy 提问时间:11/17/2023 更新时间:11/19/2023 访问量:30
Jetpack Compose 错误(java.lang.NoSuchMethodError:没有接口方法 startRestartGroup)
Jetpack Compose Error ( java.lang.NoSuchMethodError: No interface method startRestartGroup )
问:
大家好,我目前正在做一些小项目,使用 Jetpack Compose 和 Coil 依赖项来显示来自 viewModel 的图像,但我的应用程序有这样的错误:
No interface method startRestartGroup(ILjava/lang/String;)Landroidx/compose/runtime/Composer; in class Landroidx/compose/runtime/Composer; or its super classes (declaration of 'androidx.compose.runtime.Composer'
....
at com.google.accompanist.coil.CoilImage__CoilKt.CoilImage(Coil.kt:324)
at com.google.accompanist.coil.CoilImage.CoilImage(Coil.kt:1)
at PokemonListScreenKt.PokedexEntry(PokemonListScreen.kt:172)
at PokemonListScreenKt.PokedexRow(PokemonListScreen.kt:212)
at PokemonListScreenKt$PokemonList$1$1.invoke(PokemonListScreen.kt:136)
at PokemonListScreenKt$PokemonList$1$1.invoke(PokemonListScreen.kt:132)
我试图更改为新版本的 Coil 依赖项,但出现错误 stil
这是我的build.gradle(app)
plugins {
id 'com.android.application'
id 'org.jetbrains.kotlin.android'
id 'kotlin-android'
id 'kotlin-kapt'
id 'dagger.hilt.android.plugin'
}
android {
namespace 'com.example.pokedex'
compileSdk 34
defaultConfig {
applicationId "com.example.pokedex"
minSdk 24
targetSdk 34
versionCode 1
versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
vectorDrawables {
useSupportLibrary true
}
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
compileOptions {
sourceCompatibility JavaVersion.VERSION_17
targetCompatibility JavaVersion.VERSION_17
}
kotlinOptions {
jvmTarget = '17'
}
buildFeatures {
compose true
}
composeOptions {
kotlinCompilerExtensionVersion '1.4.6'
}
packagingOptions {
resources {
excludes += '/META-INF/{AL2.0,LGPL2.1}'
}
}
}
dependencies {
implementation 'androidx.core:core-ktx:1.8.0'
implementation platform('org.jetbrains.kotlin:kotlin-bom:1.8.0')
implementation 'androidx.lifecycle:lifecycle-runtime-ktx:2.3.1'
implementation 'androidx.activity:activity-compose:1.5.1'
implementation platform('androidx.compose:compose-bom:2022.10.00')
implementation 'androidx.compose.ui:ui'
implementation 'androidx.compose.ui:ui-graphics'
implementation 'androidx.compose.ui:ui-tooling-preview'
implementation 'androidx.compose.material3:material3'
implementation 'com.google.android.material:material:1.3.0'
testImplementation 'junit:junit:4.13.2'
androidTestImplementation 'androidx.test.ext:junit:1.1.5'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.5.1'
androidTestImplementation platform('androidx.compose:compose-bom:2022.10.00')
androidTestImplementation 'androidx.compose.ui:ui-test-junit4'
debugImplementation 'androidx.compose.ui:ui-tooling'
debugImplementation 'androidx.compose.ui:ui-test-manifest'
implementation "androidx.compose.material:material-icons-core:1.5.4"
implementation "androidx.compose.material:material-icons-extended:1.5.4"
implementation "androidx.lifecycle:lifecycle-viewmodel-compose:2.7.0-beta01"
implementation "androidx.navigation:navigation-compose:2.7.5"
implementation "androidx.constraintlayout:constraintlayout-compose:1.1.0-alpha13"
// Retrofit
implementation 'com.squareup.retrofit2:retrofit:2.9.0'
implementation 'com.squareup.retrofit2:converter-gson:2.9.0'
implementation "com.squareup.okhttp3:okhttp:4.11.0"
implementation "com.squareup.okhttp3:logging-interceptor:4.9.0"
// Timber
implementation 'com.jakewharton.timber:timber:4.7.1'
// Coroutines
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-core:1.4.3'
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-android:1.4.3'
// Coroutine Lifecycle Scopes
implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:2.3.1"
implementation "androidx.lifecycle:lifecycle-runtime-ktx:2.3.1"
// Coil
implementation "io.coil-kt:coil-compose:2.5.0"
// implementation("io.coil-kt:coil-compose:1.3.2")
//Dagger - Hilt
kapt "androidx.hilt:hilt-compiler:1.1.0"
kapt("org.jetbrains.kotlinx:kotlinx-metadata-jvm:0.5.0")
//Dagger - Hilt
implementation "com.google.dagger:hilt-android:2.44"
kapt "com.google.dagger:hilt-compiler:2.44"
implementation 'androidx.hilt:hilt-navigation-compose:1.1.0'
kapt("org.jetbrains.kotlinx:kotlinx-metadata-jvm:0.5.0")
// Palette
implementation 'androidx.palette:palette-ktx:1.0.0'
}
口袋妖怪ListScreen.kt
import androidx.compose.foundation.Image
import androidx.compose.foundation.background
import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.*
import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.shape.CircleShape
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.foundation.text.BasicTextField
import androidx.compose.material3.CircularProgressIndicator
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.Surface
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.*
import androidx.compose.ui.Alignment
import androidx.compose.ui.Alignment.Companion.Center
import androidx.compose.ui.Alignment.Companion.CenterHorizontally
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.draw.scale
import androidx.compose.ui.draw.shadow
import androidx.compose.ui.focus.FocusState
import androidx.compose.ui.focus.onFocusChanged
import androidx.compose.ui.graphics.Brush
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.toArgb
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.res.painterResource
import androidx.compose.ui.text.TextStyle
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import androidx.hilt.navigation.compose.hiltViewModel
import androidx.navigation.NavController
import coil.compose.SubcomposeAsyncImage
import coil.request.ImageRequest
import com.example.pokedex.R
import com.example.pokedex.data.models.PokedexListEntry
import com.example.pokedex.pokemonList.PokemonListViewModel
import com.example.pokedex.ui.theme.RobotoCondensed
@Composable
fun PokemonListScreen(
navController: NavController
) {
Surface(
color = MaterialTheme.colorScheme.background,
modifier = Modifier.fillMaxSize()
) {
Column {
Spacer(modifier = Modifier.height(20.dp))
Image(
painter = painterResource(id = R.drawable.ic_international_pok_mon_logo),
contentDescription = "Pokemon",
modifier = Modifier
.fillMaxWidth()
.align(CenterHorizontally)
)
SearchBar(
hint = "Search...",
modifier = Modifier
.fillMaxWidth()
.padding(16.dp)
) {
}
Spacer(modifier = Modifier.height(16.dp))
PokemonList(navController = navController)
}
}
}
@Composable
fun SearchBar(
modifier: Modifier = Modifier,
hint: String = "",
onSearch: (String) -> Unit = {}
) {
var text by remember {
mutableStateOf("")
}
var isHintDisplayed by remember {
mutableStateOf(hint != "")
}
Box(modifier = modifier) {
BasicTextField(
value = text,
onValueChange = {
text = it
onSearch(it)
},
maxLines = 1,
singleLine = true,
textStyle = TextStyle(color = Color.Black),
modifier = Modifier
.fillMaxWidth()
.shadow(5.dp, CircleShape)
.background(Color.White, CircleShape)
.padding(horizontal = 20.dp, vertical = 12.dp)
.onFocusChanged {
isHintDisplayed = it != FocusState::isFocused
}
)
if (isHintDisplayed) {
Text(
text = hint,
color = Color.LightGray,
modifier = Modifier
.padding(horizontal = 20.dp, vertical = 12.dp)
)
}
}
}
@Composable
fun PokemonList(
navController: NavController,
viewModel: PokemonListViewModel = hiltViewModel()
) {
val pokemonList by remember { viewModel.pokemonList }
val endReached by remember { viewModel.endReached }
val loadError by remember { viewModel.loadError }
val isLoading by remember { viewModel.isLoading }
LazyColumn(contentPadding = PaddingValues(16.dp)) {
val itemCount = if(pokemonList.size % 2 == 0) {
pokemonList.size / 2
} else {
pokemonList.size / 2 + 1
}
items(itemCount) {
if(it >= itemCount && !endReached) {
viewModel.loadPokemonPaginated()
}
PokedexRow(rowIndex = it, entries = pokemonList, navController = navController)
}
}
}
@Composable
fun PokedexEntry(
entry: PokedexListEntry,
navController: NavController,
modifier: Modifier = Modifier,
viewModel: PokemonListViewModel = hiltViewModel()
) {
val defaultDominantColor = MaterialTheme.colorScheme.surface
var dominantColor by remember {
mutableStateOf(defaultDominantColor)
}
Box(
contentAlignment = Center,
modifier = modifier
.shadow(5.dp, RoundedCornerShape(10.dp))
.clip(RoundedCornerShape(10.dp))
.aspectRatio(1f)
.background(
Brush.verticalGradient(
listOf(
dominantColor,
defaultDominantColor
)
)
)
.clickable {
navController.navigate("pokemon_detail_screen/${dominantColor.toArgb()}/${entry.pokemonName}")
}
) {
Column {
SubcomposeAsyncImage(
model = ImageRequest.Builder(LocalContext.current)
.data(entry.imageUrl)
.target {
viewModel.calcDominantColor(it) { color ->
dominantColor = color
}
}
.crossfade(true)
.build(),
contentDescription = entry.pokemonName,
modifier = Modifier
.size(120.dp)
.align(CenterHorizontally)
) {
CircularProgressIndicator(
color = MaterialTheme.colorScheme.primary,
modifier = Modifier.scale(0.5f)
)
}
Text(
text = entry.pokemonName,
fontFamily = RobotoCondensed,
fontSize = 20.sp,
textAlign = TextAlign.Center,
modifier = Modifier.fillMaxWidth()
)
}
}
}
@Composable
fun PokedexRow(
rowIndex: Int,
entries: List<PokedexListEntry>,
navController: NavController
) {
Column {
Row {
PokedexEntry(
entry = entries[rowIndex * 2],
navController = navController,
modifier = Modifier.weight(1f)
)
Spacer(modifier = Modifier.width(16.dp))
if (entries.size >= rowIndex * 2 + 2) {
PokedexEntry(
entry = entries[rowIndex * 2 + 1],
navController = navController,
modifier = Modifier.weight(1f)
)
} else {
Spacer(modifier = Modifier.weight(1f))
}
}
Spacer(modifier = Modifier.height(16.dp))
}
}
我希望有人能帮我找到这个问题的解决方案,谢谢
答:
1赞
Colin White
11/19/2023
#1
看起来您正在使用 Accompanist 的 Coil 集成。这已被 Coil 的第一方集成及其可组合项所取代。Accompanist 的 Coil 集成可能不适用于最新的 Compose 版本,因为它不再受支持。尝试使用和替换 的用法 with .AsyncImage
implementation("io.coil-kt:coil-compose:2.5.0")
CoilImage
AsyncImage
评论
0赞
Dzy
11/19/2023
非常感谢怀特先生的解决方案。它对我来说非常有效,现在,我可以直接回到我的开发任务中。你的帮助对我来说意义重大
评论