LoginSignup
11
9

More than 1 year has passed since last update.

JetpackComposeでカレンダーを作れるライブラリ

Last updated at Posted at 2023-01-27

個人開発でカレンダーを作りたくていい感じの方法を探していた時に見つけた
良さげなライブラリの紹介です。

Calendar

知らなかったんですが結構使われてるみたいで、
大分好きに見た目など変えられるみたいで良さそうだし
サンプルのカレンダーが豊富🤔

カレンダーを作っていく方法

ライブラリの導入

build.gradleにこちらを追加

dependencies {
  // Compose用
  implementation 'com.kizitonwose.calendar:compose:<latest-version>'
}

カレンダーの作成

ここにCompose向けの利用法がまとまっている

カレンダーの描画に必要になるものなどと、
カレンダーを描画するライブラリ内のComposable関数の呼び出し部分をドキュメント参考に書いていったのが下記

@Composable
fun CalendarDisplay() {
    // 現在の年月
    val currentMonth = remember { YearMonth.now() }
    // 現在より前の年月
    val startMonth = remember { currentMonth.minusMonths(100) }
    // 現在より後の年月
    val endMonth = remember { currentMonth.plusMonths(100) }
    // 曜日
    val daysOfWeek = remember { daysOfWeek() }
    // カレンダーの状態を持つ
    val state = rememberCalendarState(
        startMonth = startMonth,
        endMonth = endMonth,
        firstVisibleMonth = currentMonth,
        firstDayOfWeek = daysOfWeek.first(),
        outDateStyle = OutDateStyle.EndOfGrid
    )

    // 横スクロールのカレンダーを作成するためのComposable関数
    // 縦スクロールのVerticalなどもある
    HorizontalCalendar(
        state = state,
        // 日付を表示する部分
        dayContent = {Day(it)},
        // カレンダーのヘッダー
        monthHeader = {DaysOfWeekTitle(daysOfWeek = daysOfWeek)}
    )
}

ヘッダー

曜日の表示を行うComposable関数を作成している

@Composable
fun DaysOfWeekTitle(daysOfWeek: List<DayOfWeek>) {
    Row(
        modifier = Modifier
            .fillMaxWidth()
    ) {
        for ((index, dayOfWeek) in daysOfWeek.withIndex()) {
            Text(
                modifier = Modifier.weight(1f),
                textAlign = TextAlign.Center,
                text = dayOfWeek.getDisplayName(TextStyle.SHORT, Locale.getDefault()),
                // 土日だけそれぞれ色を変えたいので対応したカラーコードを返している
                color = getDayOfWeekTextColor(index)
            )
        }
    }
}

日付表示部分

カレンダーの日付にあたる部分を表示するためのComposable関数を作成する。
日付をタップした時の挙動や、月始まりと終わりの前後にある前月や次の月の日付をグレーアウトさせるなどはこの中でやるのがいいっぽい。

@Composable
fun Day(day: CalendarDay) {
    Box(
        modifier = Modifier
            .aspectRatio(1f),
        contentAlignment = Alignment.Center
    ) {
        Text(
            text = day.date.dayOfMonth.toString(),
            // ここで今月でないものの日付をグレーアウトさせている
            color = if (day.position == DayPosition.MonthDate) Color.Black else Color.Gray
        )
    }
}

実際に作成した画面

個人開発の方で実際に上記のコードをもとに色々追加で書いて作成した画面がこんな感じ。
比較的簡単に実装でき、見た目もいじりやすく作成者様には感謝です。

11
9
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
11
9