【Kotlin】Compose を使ってWebアプリケーションを作ってみる

この記事は [レコチョク Advent Calendar 2024](https://qiita.com/advent-calendar/2024/recochoku) の6日目の記事となります。
記事が公開される頃にはElectric Callboyの豊洲PITでのライブの余韻に浸っているAndroidアプリエンジニアの杉山です。
メタルコアバンドですがMVが印象的なのでよかったら見てみてください。

[Electric Callboy - WE GOT THE MOVES (OFFICIAL VIDEO)](https://youtu.be/D1NdGBldg3w?si=hf5pR9vat4_ZCT-M)

私達のチームでは、朝にリモート会議で雑談などのコミュニケーションを取る時間を設けています。しかし、現在会話のネタが思いつかず無言の時間が発生してしまう課題があります。
その解決策として、「お題を提案するルーレット的なものがあるといいのでは？」という意見が上がりました。リモート会議で使うことを考えると、PC上で動かせるWebアプリでそれが実現できると良いと考えました。
また、どうせなら普段扱っている言語であるKotlinで作ってみたいと思い、調べたところKotlinで、かつ現在主流になってきているJetpack Composeを使ってWebアプリを作れることを知り試してみることにしました。
課題解決のアプリは現在開発中であるので、今回は「Composeを使ってWebアプリを作る導入から開発スタートできる」ところまでの記事となります。

## 開発環境、使用技術
ComposeでWebアプリを作るにあたって今回はKotlin/Wasmを使いました。Kotlin/Wasmはブラウザでプログラムを高速実行するための、「ブラウザ上で動くバイナリコードの新しいフォーマット(仕様)」であるWasm（WebAssembly）をKotlinでコンパイル・ターゲットにできるようにしたものになります。(現在はアルファ版なので、本記事時点とは内容が異なる場合があります。)Kotlin/Wasmを利用するにあたって、Kotlinで異なるプラットフォーム間でコードを共有できるKotlin Multiplatform(KMP)が対応していたので、こちらも利用しました。
また今回の開発環境は以下になります。

* MacOS 14.5(sonoma)
* AndroidStudio Ladybug | 2024.2.1 Patch 1
* Google Chrome 131.0.6778.86

## プロジェクト作成

Webアプリ用のプロジェクトを作成するために、Kotlin Multiplatform Wizardを使用しました。

1. [Kotlin Multiplatform WizardのNew Project](https://kmp.jetbrains.com/?_gl=1*1iayk4w*_gcl_au*MTc1ODk3ODIxNS4xNzMyMjQzMDk2*_ga*MTgxNjQ0OTMyNC4xNzMyMjQzMDky*_ga_9J976DJZ68*MTczMjk4MTEwNC42LjEuMTczMjk4MTEyOC4zNi4wLjA.#newProject) ページを開く
2. ProjectNameとProject IDを設定する
3. Web のチェックボックスにチェックを入れる

今回は以下の画像のように設定をしました。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2298978/edb20c2c-69b9-3fc1-35be-367a0dcaa2cb.png" width=400 />

下部のDOWNLOADボタンを押すとzipファイルがダウンロードされます。解凍するとAndroid Studioで開くことのできるプロジェクト構成ファイルが一式入っています。実際に開いてみると以下のようなファイル構成になっていました。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2298978/97be9c47-2375-f86d-03af-af27d628de86.png" width=400 />

この状態で、実行に必要なファイルは用意されているので ` ./gradlew wasmJsBrowserRun -t` を実行すると`  http://localhost:8080/` のローカルホストでアクセスできるようになり、以下の画面がGoogle Chromeで表示されると思います。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2298978/efcc1640-4893-24cf-62f4-ff13fc874ff0.png" width=600 />

この状態になれば開発が可能になります。 

## 開発するにあたって注意点

開発をしていく中で注意するべき点が2点あったので記載しておきます。

### 日本語がデフォルトだと使えない

プロジェクト作成直後の状態では、テキストに日本語を表示しようとすると文字化けしてしまうようです。
試しに、「こんにちは こんばんわ」と表示しようとしたところ、以下の画像のように文字化けしている状態(とうふ状態)になりました。そのため自身でフォントを入れる必要があります。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2298978/36a6e586-2541-a5f5-b9af-106b4a7817be.png" width=600 />



今回はGoogleFontsから[NotoSansJP](https://fonts.google.com/noto/specimen/Noto+Sans+JP)をダウンロードして利用しています。

commonMainのcomposeResource配下にfontディレクトリを作成します。
作成後、以下のようにフォントを指定することで日本語を設定できます。

``` kotlin
val notoSansJP = FontFamily(Font(Res.font.NotoSansJP_Black))
Text("こんにちは こんばんわ",
    style = TextStyle(
    fontFamily = notoSansJP,  // フォントを指定
    )
 )
```

指定後は以下のように日本語が表示できるようになります。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2298978/420d70bf-09f3-2de1-fc22-3c517f9e0ba5.png" width=600 />


### javaのコードの呼び出しができない

これはKMPの仕様上の問題になりますが、一部javaのクラスの関数が使用できません。
自分が今回` Math.toRadians()`を使おうとしましたが、importすることができませんでした。 
必要に応じて自分で実装する必要があります。`kotlin.math`は使うことができるので、自分で実装して使いました。

``` ko
fun toRadians(degrees: Double) = degrees * (PI / 180)
```

## まとめ

今回はComposeを使ったWebアプリの導入から開発スタートするまでに関して説明させていただきました。
最後に自分が現在作っているアプリのスクショになります。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2298978/0bb7c78b-b113-437b-59ff-696b983552a6.png" width=400 />


冒頭でも話しました通りまだまだ絶賛開発中であるので、さらに開発を進め次回は完成したアプリに関して記事にできればと思っています。

明日の [レコチョク Advent Calendar 2024](https://qiita.com/advent-calendar/2024/recochoku) は7日目『今年(2024年)はメール周りの対応が大変でしたね』です。お楽しみに！

この記事はレコチョクのエンジニアブログの記事を転載したものとなります。 

https://techblog.recochoku.jp/11341

## 参考
https://kotlinlang.org/docs/wasm-get-started.html
https://matsudamper.hatenablog.com/entry/2023/06/11/091345