SpongeBobSun의 mCalendarView 라이브러리 사용하기

2019.04.28 16:50안드로이드 개발/라이브러리 소개


오늘은 SpongeBobSun님이 제작하신 mCalendarView의 라이브러리에 대해 알아보고, 사용법에 대해서 조금 더 알아보는 시간을 갖도록 하겠습니다. 이렇게 앞으로도 제가 사용하는 라이브러리에 대해 정리하면서 저도 그 사용법을 익히고, 이 글을 읽는 분들도 사용이 용이하도록 글을 작성하려고 합니다. 이 글의 내용은 대부분 본 라이브러리 GitHub의 내용임을 밝힙니다. (원문 영어) 해석본이라고 보셔도 무방하나, 코드 등을 Kotlin으로 작성하였고 약간 저의 상황에 맞게 표현되었습니다. Java로 프로그래밍하셔도 상황에 맞게 수정이 가능합니다. 질문은 댓글로 부탁드립니다.


사용 준비하기

이 라이브러리는 어디에다 사용하나요?

저의 경우, 안드로이드 개발 중에 CalendarView를 사용하고 그 곳에 제가 지정한 특정 날짜에 강조/표시 등을 하려고 하는데 안드로이드에서 기본으로 제공하는 CalendarView 위젯이 지원하지 않아서 사용하게 되었습니다. 커스터마이징 가능하고 확장 가능한 캘린더 위젯임을 밝히고 있습니다.


라이브러리에서 제공하는 컴포넌트들

mCalendarView

라이브러리에서 제공하는 커스터마이징 가능한 캘린더 위젯입니다.

ExpCalendarView

라이브러리에서 제공하고 있는 확장 가능한 캘린더 위젯입니다.

BaseCellView

각각의 날짜 칸에 대한 추상 뷰 클래스입니다.

BaseMarkView

마크 칸이나, 강조된 날짜 칸에 대한 추상 뷰 클래스입니다.

MarkStyle

기본으로 내장되어 있는 마크 칸이나 강조되는 그 스타일 값을 제공합니다.

DefaultCellView

강조되지 않은, 기본 날짜 칸에 대한 기본값 뷰 클래스입니다.

DefaultMarkView

마크 칸이나, 강조된 날짜 칸에 대한 뷰 클래스입니다.

OnDateClickListener

날짜 칸이 클릭되었을 때 불러와지는 리스너입니다.

OnMonthChangeListener

왼쪽이나 오른쪽으로 스와이프하면 달(月)이 바뀌는데, 그 때 불러와지는 리스너입니다.


본격적으로 사용하기

프로젝트에 라이브러리 불러오기

build.gradle 파일에 다음과 같은 구문을 추가합니다.

```

dependencies {
    implementation 'sun.bob:mcalendarview:1.0.0'
}

```

레이아웃에 추가하기

저는 Kotlin으로 안드로이드 프로그래밍을 바꾸었기 때문에, Kotlin 기준으로 작성하겠습니다. 그러나 거의 Java 코드랑 비슷하므로 Java로 프로그래밍하시는 프로그래머분들도 참고 가능합니다. 너무 상이한 경우 Java 코드도 삽입했습ㄴ다.

MCalendarView의 경우

    <sun.bob.mcalendarview.MCalendarView
        android:id="@+id/calendarView"
        android:layout_width="400dp"
        android:layout_height="400dp" />

ExpCalendarView의 경우

    <sun.bob.mcalendarview.ExpCalendarView
        android:id="@+id/calendarView"
        android:layout_width="400dp"
        android:layout_height="400dp" />

날짜를 이동하려면
// calendarView 객체는 이미 'kotlin-android-extensions'에 의해 찾아져 있음
calendarView.travelTo(DateData(2000,9,28))

날짜를 표시하거나 강조할 때

사실상 제가 이 라이브러리를 쓰게 된 이유이자, 이 라이브러리의 핵심 기능이기도 합니다. 왜냐 하면 안드로이드의 기본 위젯에는 이 기능이 없기 때문이죠. 두 가지 날짜를 강조하는 방법이 있다고 합니다.

markDate(year: Int, month: Int, day: Int)
markDate(date: DateData)

여기서 DateData 객체는 이 라이브러리에서 제공하고 있는 객체입니다. 따로 import하실 필요는 없습니다. 실제로 사용하는 예시를 보면 다음과 같습니다.

calendarView.markDate(2019, 4, 28)
calendarView.markDate(DateData(2019, 4, 28).setMarkStyle(MarkStyle(MarkStyle.DOT, Color.RED))

우리가 사용할 수 있는 내장된 Mark Style들

- 배경을 변경할 때

MarkStyle.BACKGROUND

calendarView.markDate(DateData(2019, 4, 28).setMarkStyle(MarkStyle(MarkStyle.BACKGROUND, Color.RED)))

- 날짜 글자 밑에 자그만한 점을 표시할 때

MarkStyle.DOT

calendarView.markDate(DateData(2019, 4, 28).setMarkStyle(MarkStyle(MarkStyle.DOT, Color.RED)))

- 글자 왼쪽에 색칠된 세로 바를 두고 싶을 때

MarkStyle.LEFTSIDEBAR

calendarView.markDate(DateData(2019, 4, 28).setMarkStyle(MarkStyle(MarkStyle.LEFTSIDEBAR, Color.RED)))

- 글자 오른쪽에 색칠된 세로 바를 두고 싶을 때

MarkStyle.RIGHTSIDEBAR

calendarView.markDate(DateData(2019, 4, 28).setMarkStyle(MarkStyle(MarkStyle.RIGHTSIDEBAR, Color.RED)))

 

그리고, 전체적인 스타일이나 색을 지정하기 위해서는 mCalendarViewsetMarkedStyle(style: Int, color: Int)을 사용하라고 하는데, 제가 뭘 잘못했는지 저는 지정이 잘 안되네요.

calendarView.setMarkedStyle(MarkStyle.BACKGROUND)
또는 
calendarView.setMarkedStyle(MarkStyle.BACKGROUND, Color.RED)

하나의 날짜에 적용하기 위해서는 DateData의 메소드인 setMarkStyle(markStyle: MarkStyle)을 사용해야 합니다.


날짜 셀을 커스터마이징하기

또한 mCalendarView 라이브러리는 각각의 날짜 셀들을 커스터마이징할 수 있는데, 제한이 존재한다고 합니다.

- 커스터마이징하는 그 뷰는 BaseCellView라는 클래스를 상속 (extend) 해야 합니다.

- 커스터마이징하는 그 뷰는 setDisplayText라는 추상 클래스를 상속 (implement) 해야 합니다. 이 함수는 셀의 어떤 것들을 mCalendarView가 표시하는데 사용된다고 합니다. 보통 Sun, Mon, .. , Sat과 같은 요일을 표시하는 데 사용된다고 하네요. 가령 이런 형태입니다. (Kotlin)

// Language : Kotlin

abstract inner class DateCellView : BaseCellView {
        constructor(context: Context) : super(context)

        constructor(context: Context, attrs: AttributeSet) : super(context, attrs)

        fun setDisplayText(text: String) {
            id_cell_text.text = text // id_cell_text는 TextView
        }
}

Java로는 다음과 같습니다.

// Language : Java
public class DateCellView extends BaseCellView {
      public DateCellView(Context context) {
          super(context);
      }
  
      public DateCellView(Context context, AttributeSet attrs) {
          super(context, attrs);
      }
  
      @Override
      public void setDisplayText(String text) {
          ((TextView) this.findViewById(R.id.id_cell_text)).setText(text);
      }
  }

- 그리고 커스터마이징한 뷰의 레이아웃 xml을 생성해 줍니다. 여기서는 원래 라이브러리를 제작한 사람의 글을 그대로 사용하여 layout_date_cell.xml을 사용합니다.

  <?xml version="1.0" encoding="utf-8"?>
  <sun.bob.mcalendarviewtest.DateCellView 
  	xmlns:android="http://schemas.android.com/apk/res/android"
      android:orientation="vertical"
      android:layout_width="100dp"
      android:layout_height="100dp"
      android:background="#00ADA3">
      <TextView
          android:layout_width="match_parent"
          android:layout_height="match_parent"
          android:textColor="#FFFFFF"
          android:id="@+id/id_cell_text"/>
  </sun.bob.mcalendarviewtest.DateCellView>

그리고 나서 액티비티나 프래그먼트 클래스로 돌아가서 다음과 같은 구문을 추가해 줍니다.

calendarView.setDateCell(R.layout.layout_date_cell)
// Java는 세미콜론만 붙이면 같음

강조된 셀을 커스터마이징하기

강조된 날짜 셀도 커스터마이징할 수 있고 BaseMarkView를 상속 (extend)하면 다른 부분은 위의 날짜 셀 커스터마이징과 같습니다.


OnMonthChangeListener 붙이기

여기도 Java와 Kotlin이 조금 상이해서 따로 기술을 해야 할 것 같습니다. OnMonthChangeListener는 추상 클래스로 사용자가 왼쪽이나 오른쪽으로 스와이프해서 달(月)을 바꿀 때 불러와집니다. 년도와 달의 값이 들어갑니다.

// Language : Kotlin
abstract fun onMonthChange(year: Int, month: Int)
// Language : Java
public abstract void onMonthChange(int year, int month);

그리고 OnMonthChangeListener를 붙이기 위해서는 다음과 같은 구문을 이용해주면 됩니다.

// Language : Kotlin
calendarView.setOnMonthChangeListener(object : OnMonthChangeListener() {
            override fun onMonthChange(year: Int, month: Int) {
                Toast.makeText(this@MainActivity, String.format("%d-%d", year, month), Toast.LENGTH_SHORT).show()
            }
        })
// Language : Java
calendarView.setOnMonthChangeListener(new OnMonthChangeListener() {
        @Override
        public void onMonthChange(int year, int month) {
            Toast.makeText(MainActivity.this, String.format("%d-%d", year, month), Toast.LENGTH_SHORT).show();
        }
    });

OnDateClickListener 붙이기

OnMonthChangeListener랑 매우 유사한데요, 날짜 셀을 클릭했을 때 OnDateClickListener가 불러와집니다. 인자로는 DateData가 들어와집니다.

// Language : Kotlin
abstract fun onDateClick(view: View, dawte: DateData)
// Language : Java
public abstract void onDateClick(View view, DateData date);

그리고 OnDateClickListener를 붙이기 위해서는 다음과 같은 구문을 이용해주면 됩니다.

// Language : Kotlin
calendarView.setOnDateClickListener(object : OnDateClickListener() {
            override fun onDateClick(view: View, date: DateData) {
                Toast.makeText(this@MainActivity, String.format("%d-%d", date.year, date.month), Toast.LENGTH_SHORT).show()
            }
        })
// Language : Java
calendarView.setOnDateClickListener(new OnDateClickListener() {
        @Override
        public void onDateClick(View view, DateData date) {
            Toast.makeText(MainActivity.this, String.format("%d-%d", date.getMonth(), date.getDay()), Toast.LENGTH_SHORT).show();
        }
    });

ExpCalendarView에서 접고 펼치는 구문
expCalendarView.expend()
expCalendarView.shrink()

여기까지입니다. 저도 사용하면서 더 알아보고, 새로운 내용을 찾게 되면 수정하여 더 업로드할 예정입니다. 현재 개발중인 블로그 플래너에 이 라이브러리가 사용될 예정이니, 많은 기대 부탁드립니다.

아래 링크는 본 라이브러리의 GitHub입니다. 참고하시면 도움이 됩니다 (영문).

 

SpongeBobSun/mCalendarView

Customizable & Shrinkable Calendar Widget for Android - SpongeBobSun/mCalendarView

github.com