[Android] ViewBinding

leeeha·2022년 12월 20일
0
post-thumbnail

레이아웃 XML 파일에 선언한 뷰 객체들을 코드 상에서 쉽게 이용하기 위한 기법들

  • findViewById()
  • Butterknife
  • Kotlin Android Extension
  • DataBinding
  • ViewBinding

findViewById()

가장 기초적인 방법이긴 하지만, 레이아웃의 뷰 객체가 10~20개 정도로 많아지면 일일이 findViewById()로 객체를 획득하는 건 매우 번거로울 수 있다.

ButterKnife

어노테이션으로 xml 파일의 뷰 객체를 획득하는 방법이다. 한때 자주 사용되었던 프레임워크라고 한다.

Kotlin Android Extension

build.gradle 파일에 플러그인으로 익스텐션을 설정해주면 import 구문에 xml 파일명을 알려주는 것만으로도, 뷰 객체를 따로 생성하지 않고 바로 사용할 수 있다.

위에 소개된 여러 방법들 중에서 코드적으로는 길이가 가장 짧다. 하지만, 서로 다른 레이아웃 파일의 뷰 객체가 동일한 id 값을 갖는 경우 명료성이 부족하므로 문제가 생길 수 있다. 이러한 문제로 deprecated 되었다.

DataBinding

build.gradle 파일에 아래처럼 설정해주면 되는데, 데이터 바인딩은 뷰와 관련된 것은 모두 xml 파일에서 처리한다. 아키텍처 자체가 다르다고 볼 수 있다.

ActivityMainBinding 클래스는 activity_main.xml 파일을 기반으로 자동으로 생성된 클래스이다. 이 바인딩 객체로 xml에 있는 뷰 객체들을 참조할 수 있다.

원래 어떤 데이터를 뷰에 적용하는 건 코드 상에서 했었는데, 데이터 바인딩은 이를 xml 파일에서 처리한다.


ViewBinding

아래처럼 build.gradle 파일에 뷰 바인딩 설정을 해주면, xml 파일에 등록된 뷰 객체를 갖는 바인딩 클래스를 사용할 수 있게 된다. (activity_main.xml → ActivityMainBinding)

android {
  viewBinding {
  	enabled = true
  }
}
  • 바인딩 클래스의 inflate 함수의 매개변수로 layoutInflater를 전달하여 바인딩 객체 획득
  • 바인딩 객체의 root 속성은 xml의 루트 태그 객체를 가리킨다.

build.gradle 파일에 뷰 바인딩을 이용하겠다고 선언하면, xml 하나당 바인딩 클래스가 자동으로 생성된다. 그런데, xml 파일을 위한 바인딩 클래스를 만들 필요가 없는 경우에는 tools:viewBindingIgnore 속성을 true로 설정해주면 된다.

실습 예제

android {
	viewBinding {
        enabled = true 
    }
}   
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity">

    <Button
        android:id="@+id/visibleBtn"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="visible"/>

    <TextView
        android:id="@+id/targetView"
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="1"
        android:text="hello world"
        android:textSize="30sp"
        android:textStyle="bold"
        android:textColor="#FFFFFF"
        android:background="#00FF00"
        android:gravity="center"/>

    <Button
        android:id="@+id/invisibleBtn"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="invisible"/>

</LinearLayout>
package com.tutorial.c90

import android.os.Bundle
import android.view.View
import androidx.appcompat.app.AppCompatActivity
import com.tutorial.c90.databinding.ActivityMainBinding

class MainActivity : AppCompatActivity() {
    lateinit var binding: ActivityMainBinding

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        binding = ActivityMainBinding.inflate(layoutInflater)
        setContentView(binding.root)

        binding.visibleBtn.setOnClickListener {
            binding.targetView.visibility = View.VISIBLE
        }

        binding.invisibleBtn.setOnClickListener {
            binding.targetView.visibility = View.INVISIBLE
        }
    }
}

profile
습관이 될 때까지 📝

0개의 댓글