ImageLoaderとCompose

bitFlyerでAndroidプロダクトを担当しています藤原です。
最近はガンダムエボリューションばかりやってます、メイン機体はザクⅡ(射撃)を使っています。いやー面白いです。

さてさて、突然ですがみなさんCompose書いてますか？
弊社Androidプロダクトでは少しずつですが移行を進めています。

Compose化を検討しだした辺りで弊社ではImageLoaderをGlideからCoilに移行しました。
ComposeでのImageLoaderですが、Coilを使うのが一般的と思われます。公式ドキュメントでも画像読み込みにはCoilの例が挙げられています。CoilはもともとAccompanitに含まれていたので当然かもしれませんが。
今更ですが、CoilをComposeで使うとこんな感じです。

```kotlin
@Composable
fun CoilImage() {
    val painter = rememberImagePainter(
        data = "https://picsum.photos/300/300",
        builder = {
            crossfade(true)
        }
    )

    Image(
        painter = painter,
        contentDescription = stringResource(R.string.image_content_desc),
    )
}
```

またCoilの2.0.0以降ではAsyncImageが登場し以下のように書けるようになりました。う〜ん、すっきりしていい感じです。

```kotlin
@Composable
fun CoilImage() {
    AsyncImage(
            model = ImageRequest.Builder(LocalContext.current)
                .data("https://picsum.photos/300/300")
                .crossfade(true)
                .build(),
            contentDescription = stringResource(R.string.image_content_desc),
    )
}
```


ところで、ComposeにおけるImageLoaderはCoil一択のように思えますが、他の画像読み込みライブラリもCompose対応が進んでいます。ここで本当にCoilが正しい選択だったのか、他ライブラリの動向を見ながら改めて考えてみます。

いきなり結論ですが、下記の表にその状況をまとめてみました。
他にもImageLoaderライブラリはありますが、今回は私が業務で利用したことのあるライブラリに絞ってまとめていきます。
また今回はCompose化という観点で見るため、パフォーマンスなどは一旦置いておきます、あしからず。





評価
Compose化状況
備考
Coil
◎
済


Piccaso
△
アルファ版
開発停滞
Glide
○
アルファ版
composeは2022/11時点でalpha版
fresco
☓
☓
3rdパーティー製のみ



以下に詳細を書いていきます。

Piccaso
https://github.com/square/picasso

ImageLoaderの先駆けといってもいいsquare社製のPiccasoです。
picasso-composeなるモジュールが公開されていて、picasso-composeを取り込むとPiccasoにrememberPainterという拡張関数が使えるようになりComposeで利用できます。picasso-composeはPiccaso3を利用していますがPiccaso3はalpha版なので△としています。ただ、Picasso3はまさかのKotlin化されています。

```kotlin
@Composable
fun PicassoImage() {

    val imageUrl = "https://picsum.photos/300/300"
    val context = LocalContext.current
    val picasso = Picasso.Builder(context).build()
    val painter = picasso.rememberPainter(key = imageUrl) {
        it.load(imageUrl)
            .placeholder(ContextCompat.getDrawable(context, R.drawable.ic_launcher_foreground))
    }
    Image(
        painter = painter,
        contentDescription = stringResource(R.string.image_content_desc),
    )
}
```

ですが、Jake神曰く「Piccasoの開発は活発ではない、CoilかGlideを推奨する」とのことなので今から新規開発する上で選択する理由はなさそうです。


Glide
https://github.com/bumptech/glide

もともとBump社が開発していましたがGoogle傘下になり実質Google製です。
Coilが登場するまではGlideを使っていた方も多いのではないでしょうか、弊社もそのくちです。
こちらもcompose対応のモジュールが公開されていますが、現時点ではalpha版となっています。
GlideImageというComposableが用意されており、かなりシンプルに記述できます。

```gradle
implementation "com.github.bumptech.glide:compose:1.0.0-alpha.1"
```

```kotlin
@Composable
fun GlideImageComposable() {
    val imageUrl = "https://picsum.photos/300/300"
    GlideImage(
        model = imageUrl,
        contentDescription = stringResource(R.string.image_content_desc),
    )
}

```

また、機能的にもLazyList用のPreloaderを用意していたりsignatureもそのまま使えたりと機能性も問題ないです。正式版の公開が待たれます。


fresco
https://github.com/facebook/fresco

Facebook社製のfrescoです。私もCoilが登場するまでは、一時期利用していました。Piccaso, Glideに比べると比較的最近登場しましたが現段階での最終更新が2021年11月と約1年更新がありません。もちろんCompose化もされておらずJaewoong Eum氏の作成したライブラリを使えば一応Composeで利用できます。

```kotlin
@Composable
fun FrescoImageComposable() {
    val imageUrl = "https://picsum.photos/300/300"
    FrescoImage(
        imageUrl = imageUrl,
        imageOptions = ImageOptions(
            contentDescription = stringResource(R.string.image_content_desc),
        )

    )
}
```

本体のCompose化が絶望的なのと今後のサポートも不安なため、現在使われている方は他ライブラリへの移行を検討した方がよいかもしれません。


総評

Compose化の現状、今後のサポートを考えるとやはりCoil一強です。
機能面、開発速度、今後の期待、はっきり言って文句がつきません。
次点のGlideは期待できますが、Kotlin化されていないところをみるとCoilには及ばないように思えます。移行は正解だったと感じざるを得ません。
Picasso, frescoはお察し感がありますね。frescoは個人的に気に入っていたので残念です。

Coilは開発スピードが早く、どんどん最適化されていっているので情報を追いかけていきたいですね。
今後もComposeやっていきましょう！！！！


最後に、弊社bitFlyerでは[Androidエンジニアを募集](https://www.green-japan.com/company/3509/job/167514)しています。ご興味のある方はぜひご応募ください！








参考文献
https://developer.android.com/jetpack/compose/libraries
https://square.github.io/picasso/
https://github.com/square/picasso/issues/2203
https://bumptech.github.io/glide/int/compose.html#compose
https://frescolib.org/
https://github.com/skydoves/landscapist