Android Academy · leksjon

Laste inn bilder med Coil

Asynkron bildelasting i Compose.

Leksjon 1 av 413 trinn

Laste inn bilder med Coil er en gratis leksjon i Android Academy på CoddyKit. Dette er leksjon 1 av 4. Du kan lese valgfritt 3 leksjoner fra denne læringsstien gratis i sin helhet – deretter låser CoddyKit PRO opp alle leksjoner, samt praktisk øving med en innebygd kodeeditor og en AI-veileder som er tilgjengelig døgnet rundt. Den er en del av læringsløpet i Android Academy, og fremdriften din synkroniseres mellom nettet og CoddyKit-appen. Kurset i Android Academy inneholder totalt 4 leksjoner.

Hvorfor De trenger en bildeinnlaster

De fleste moderne apper viser bilder fra internett: profilbilder, produktbilder og miniatyrbilder av artikler. Det er vanskeligere enn det ser ut til å laste ned og dekode slike bilder på riktig måte.

De må hente byte over nettverket i en bakgrunnstråd, dekode dem til en bitmap, bufre dem slik at de ikke hentes på nytt, og avbryte forespørselen hvis brukeren blar videre. Det er lett å gjøre feil når De skriver alt dette selv.

Coil (Coroutine Image Loader) håndterer alt dette for Dem med et lite, Compose-vennlig API. I denne leksjonen laster De inn Deres første eksterne bilde.

Legge til Coil i prosjektet

Coil leveres som en Gradle-avhengighet. For Jetpack Compose trenger De artefakten coil-compose, som gir Dem composable-elementet AsyncImage.

Legg den til i modulens build.gradle.kts. Coil 3 er den gjeldende hovedversjonen og fungerer på tvers av plattformer; det er Compose-integrasjonen vi bruker her.

// build.gradle.kts (module level)
dependencies {
    implementation("io.coil-kt.coil3:coil-compose:3.0.4")
    implementation("io.coil-kt.coil3:coil-network-okhttp:3.0.4")
}

Internet-tillatelse

For å laste ned bilder fra en URL trenger appen Deres tillatelsen INTERNET. Dette er en vanlig tillatelse som gis ved installasjon, så De trenger bare å deklarere den i manifestet. Det vises ingen dialog under kjøring.

Uten den mislykkes alle nettverksforespørsler med et sikkerhetsunntak.

<!-- AndroidManifest.xml -->
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
    <uses-permission android:name="android.permission.INTERNET" />
    <application ...>
        ...
    </application>
</manifest>

Deres første AsyncImage

Den enkleste måten å vise et eksternt bilde i Compose på er AsyncImage. Gi det en model (vanligvis en URL-streng) og en contentDescription, så ordner Coil resten: henting i bakgrunnen, dekoding og visning.

Det bruker automatisk coroutines som er knyttet til komposisjonen, slik at forespørselen avbrytes hvis composable-elementet forlater skjermen.

import androidx.compose.foundation.layout.size
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp
import coil3.compose.AsyncImage

@Composable
fun Avatar() {
    AsyncImage(
        model = "https://example.com/avatar.png",
        contentDescription = "User avatar",
        modifier = Modifier.size(96.dp)
    )
}

contentScale: Slik tilpasses bildet

Bilder har sjelden nøyaktig samme størrelse som plassen i layouten. ContentScale styrer hvordan bitmapen skaleres innenfor grensene.

  • ContentScale.Crop fyller boksen og klipper bort det som går utenfor (flott for avatarer og miniatyrbilder).
  • ContentScale.Fit viser hele bildet, men kan etterlate tom plass.
  • ContentScale.FillBounds strekker bildet slik at det fyller plassen (kan forvrenge bildet).

Crop er det vanligste valget for plasser med fast størrelse.

import androidx.compose.foundation.layout.size
import androidx.compose.foundation.shape.CircleShape
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.layout.ContentScale
import androidx.compose.ui.unit.dp
import coil3.compose.AsyncImage

@Composable
fun CircleAvatar(url: String) {
    AsyncImage(
        model = url,
        contentDescription = "Avatar",
        contentScale = ContentScale.Crop,
        modifier = Modifier
            .size(80.dp)
            .clip(CircleShape)
    )
}

Bygge en forespørsel med ImageRequest

Å sende inn en URL-streng er den raske løsningen. For mer kontroll kan De bygge en ImageRequest. Da kan De angi alternativer som crossfade, headere, transformasjoner og hurtigbuffer-nøkler.

De trenger en Context, som Compose tilbyr via LocalContext.current.

import androidx.compose.runtime.Composable
import androidx.compose.ui.platform.LocalContext
import coil3.compose.AsyncImage
import coil3.request.ImageRequest
import coil3.request.crossfade

@Composable
fun ProductImage(url: String) {
    val context = LocalContext.current
    val request = ImageRequest.Builder(context)
        .data(url)
        .crossfade(true)
        .build()

    AsyncImage(
        model = request,
        contentDescription = "Product photo"
    )
}

Crossfade for jevn innlasting

Som standard vises bildet brått idet innlastingen er ferdig, noe som kan føles unaturlig. crossfade(true) toner bildet inn med en kort animasjon.

De kan også angi en varighet i millisekunder for en langsommere eller raskere inntoning. Denne lille detaljen gjør at lister føles langt mer gjennomarbeidet.

import coil3.request.ImageRequest
import coil3.request.crossfade
import android.content.Context

fun smoothRequest(context: Context, url: String) =
    ImageRequest.Builder(context)
        .data(url)
        .crossfade(durationMillis = 300)
        .build()

Laste inn fra ulike kilder

model i AsyncImage er fleksibel. Coil kan laste inn fra mange kildetyper, ikke bare eksterne URL-er:

  • En String eller Uri for nettverks- eller lokale filer.
  • En ressurs-ID for en drawable (R.drawable.logo).
  • En File fra enheten.
  • En innholds-Uri fra bildevelgeren.

Det betyr at det samme composable-elementet håndterer eksterne og lokale bilder sømløst.

import android.net.Uri
import androidx.compose.runtime.Composable
import coil3.compose.AsyncImage

@Composable
fun FlexibleImage(source: Any) {
    // source can be a URL String, a Uri, a File, or a resource id
    AsyncImage(
        model = source,
        contentDescription = null
    )
}

// Examples:
// FlexibleImage("https://example.com/pic.jpg")
// FlexibleImage(Uri.parse("content://media/external/images/1"))

Reagere på innlastingstilstand

Noen ganger vil De vite om bildet lastes inn, ble lastet inn eller ikke kunne lastes inn, slik at De kan vise forskjellig brukergrensesnitt. AsyncImagePainter viser denne tilstanden, men den enkleste metoden er SubcomposeAsyncImage, som lar Dem angi innhold for hver tilstand.

Vi går nærmere inn på plassholdere i neste leksjon; her ser De strukturen for tilstandsbasert innlasting.

import androidx.compose.material3.CircularProgressIndicator
import androidx.compose.runtime.Composable
import coil3.compose.SubcomposeAsyncImage

@Composable
fun StatefulImage(url: String) {
    SubcomposeAsyncImage(
        model = url,
        contentDescription = "Photo",
        loading = { CircularProgressIndicator() }
    )
}

Avbryting følger automatisk med

En av Coils største fordeler er automatisk avbryting. Fordi AsyncImage starter forespørselen inne i komposisjonen, avbrytes den pågående forespørselen når composable-elementet forlater skjermen, for eksempel når en rad blar ut av en LazyColumn.

Dette sparer båndbredde og CPU og hindrer bortkastet arbeid. De trenger ikke skrive avbrytingskode selv, og derfor fungerer Coil så godt i lange lister.

import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.lazy.items
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp
import coil3.compose.AsyncImage

@Composable
fun PhotoFeed(urls: List<String>) {
    LazyColumn {
        items(urls) { url ->
            AsyncImage(
                model = url,
                contentDescription = null,
                modifier = Modifier
                    .fillMaxWidth()
                    .height(200.dp)
            )
        }
    }
}

Et komplett bildekort

La oss kombinere det vi har lært: et kort med et eksternt bilde som fyller toppen, bruker crossfade og beskjæres til en fast høyde. Dette er grunnmønsteret De kommer til å bruke igjen og igjen.

import androidx.compose.foundation.layout.*
import androidx.compose.material3.Card
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.layout.ContentScale
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.unit.dp
import coil3.compose.AsyncImage
import coil3.request.ImageRequest
import coil3.request.crossfade

@Composable
fun ImageCard(title: String, imageUrl: String) {
    val context = LocalContext.current
    Card(modifier = Modifier.fillMaxWidth().padding(16.dp)) {
        Column {
            AsyncImage(
                model = ImageRequest.Builder(context)
                    .data(imageUrl)
                    .crossfade(true)
                    .build(),
                contentDescription = title,
                contentScale = ContentScale.Crop,
                modifier = Modifier.fillMaxWidth().height(180.dp)
            )
            Text(text = title, modifier = Modifier.padding(16.dp))
        }
    }
}

Rask kontroll

Hvilket composable-element fra coil-compose er den enkleste måten å vise et eksternt bilde fra en URL i Jetpack Compose på?

Oppsummering

De har lastet inn Deres første eksterne bilder med Coil. Viktige punkter:

  • Legg til coil-compose og en OkHttp-nettverksavhengighet, samt tillatelsen INTERNET.
  • AsyncImage(model = url, contentDescription = ...) er den raske løsningen.
  • Bruk ContentScale.Crop med fast størrelse for avatarer og miniatyrbilder.
  • Bygg en ImageRequest for crossfade og mer kontroll.
  • Coil avbryter automatisk pågående forespørsler når composable-elementer forlater skjermen.

Neste: gjøre innlasting smidig med plassholdere og feilstater.

Gratis å komme i gang

Lær deg Kotlin med en AI-veileder – gratis

Skriv og kjør ekte kode i nettleseren, få umiddelbar hjelp fra en AI-veileder som er tilgjengelig døgnet rundt, og fortsett der du slapp – på nettet eller i appen.

Kurs
36
Leksjoner
152

Ofte stilte spørsmål

Er leksjonen «Laste inn bilder med Coil» gratis?

Ja – du kan lese valgfritt 3 av leksjonene i læringsstien Android Academy, inkludert «Laste inn bilder med Coil», gratis i sin helhet her på nettet. Deretter låser CoddyKit PRO opp alle leksjoner, samt interaktiv øving med en innebygd kodeeditor og en AI-veileder som er tilgjengelig døgnet rundt. Kurset i Android Academy inneholder totalt 4 leksjoner.

Hva lærer jeg i «Laste inn bilder med Coil»?

Asynkron bildelasting i Compose. Du øver på Android Academy med praktisk kode som du kjører direkte i nettleseren, mens en AI-veileder som er tilgjengelig døgnet rundt, svarer på spørsmålene dine mens du jobber deg gjennom leksjonen.

Trenger jeg erfaring for å begynne med Android Academy?

Ingen tidligere erfaring er nødvendig. Android Academy på CoddyKit er lagt opp for både nybegynnere og viderekomne, så De kan begynne her eller helt fra start og lære i Deres eget tempo. Dette er leksjon 1 av 4.

Hvor lang tid tar leksjonen «Laste inn bilder med Coil»?

De fleste CoddyKit-leksjoner tar omtrent 5–10 minutter. Hver leksjon er kort og interaktiv, slik at De gjør jevne fremskritt og kan fortsette akkurat der De slapp – både på nettet og i appen.

Kan jeg skrive og kjøre kode i denne Android Academy-leksjonen?

Ja. Alle Android Academy-leksjoner har en innebygd kodeeditor, slik at De kan skrive og kjøre ekte kode direkte i nettleseren og få umiddelbar tilbakemelding fra AI – uten lokal konfigurering.

Alle leksjonene i dette kurset

  1. Laste inn bilder med Coil
  2. Plassholdere og feiltilstander
  3. Hurtigbufring og ytelse
  4. Spille av lyd og video
← Tilbake til Android Academy