https://goni95.tistory.com/173
기존에 XML 레이아웃 파일의 View에 접근하기 위해선 findViewById를 사용하는 방법이 View의 개수만큼 findViewById를 사용해야하며 잘못된 View ID로 인한 NPE가 발생할 위험이 있었습니다.
코틀린에서는 코틀린 익스텐션으로 문제가 해결되었지만 2021년 지원 중단이 되었습니다.
1️⃣ViewBinding | DataBinding
ViewBinding은 액티비티나 프래그먼트와 같은 View와 상호 작용하는 코드를 쉽게 작성할 수 있습니다. ViewBinding은 모듈에 있는 XML 레이아웃 파일에 대한 Binding 클래스를 생성합니다.
● 사용법
1. 모듈 수준의 build.gradle 파일에 종석성 추가
android {
...
buildFeatures {
viewBinding = true
}
}
2. 레이아웃 파일에 id를 가진 View를 정의
<LinearLayout ... >
<TextView android:id="@+id/logo_textView" />
</LinearLayout>
3. 액티비티와 프래그먼트에서 Binding 클래스의 인스턴스 정의
class MainActivity : AppCompatActivity() {
private lateinit var binding: ActivityMainBinding
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = ResultProfileBinding.inflate(layoutInflater)
setContentView(binding.root)
binding.logoTextView.text = "로고"
}
}
class SampleFragment : Fragment() {
/*
프래그먼트에서 Navigation component, BackStack, detach를 사용할 경우 onDestroyView() 후에
View는 종료되지만 프래그먼트의 생명주기로 인해 여전히 살아있어, 메모리 누수가 발생
*/
private var _binding: FragmentSampleBinding? = null
private val binding get() = _binding!!
override fun onCreateView(
inflater: LayoutInflater, container: ViewGroup?,
savedInstanceState: Bundle?
): View {
// 프래그먼트의 레이아웃 확장
_binding = FragmentSampleBinding.inflate(inflater, container, false)
return binding.root
}
override fun onResume() {
binding.logoTextView.text = "로고"
}
override fun onDestroyView() {
super.onDestroyView()
_binding = null
}
}
DataBinding은 레이아웃의 파일에서 Binding 표현식을 통해 레이아웃의 UI Component를 애플리케이션의 데이터와 Binding할 수 있는 라이브러리 입니다.
DataBinding은 <layout>태그를 사용하여 만든 XML 레이아웃 파일에 대한 Binding 클래스를 생성합니다.
● 사용법
1. 모듈 수준의 build.gradle 파일에 종석성 추가
android {
...
buildFeatures {
dataBinding = true
}
}
2. 레이아웃 파일에 id를 가진 View를 정의
<layout ...>
<data>
<variable
name="viewModel"
type="viewModel의 경로" />
</data>
<LinearLayout ... >
<TextView
android:id="@+id/logo_textView"
android:text="@{viewModel.logo}"/>
</LinearLayout>
</layout>
3. 액티비티와 프래그먼트에서 Binding 클래스의 인스턴스 정의
// ViewBinding의 액티비티 예제처럼 inflate 가능
class MainActivity : AppCompatActivity() {
private lateinit var binding : ActivityMainBinding
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = DataBindingUtil.setContentView(this, R.layout.activity_main)
//binding = ActivityMainBinding.inflate(layoutInflater)
}
}
class SampleFragment : Fragment() {
private lateinit var binding: FragmentSampleBinding
override fun onCreateView(
inflater: LayoutInflater,
container: ViewGroup?,
savedInstanceState: Bundle?
): View {
// 프래그먼트의 레이아웃 확장
binding = FragmentSampleBinding.inflate(inflater, container, false)
// binding = FragmentSampleBinding.inflate(layoutInflater)
// binding = DataBindingUtil.inflate(inflater, R.layout.fragment_sample, container, false)
binding.lifecycleOwner = this
return binding.root
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
//sampleViewModel 인스턴스가 있다는 가정
binding.viewModel = sampleViewModel
}
}
공통점
Binding 클래스는 해당 레이아웃에서 ID가 존재하는 모든 View를 직접 참조하고 View 타입이 일치하기 때문에 Null Pointer Exception, Class Cast Exception이 발생하지 않습니다.
차이점
DataBinding은 내부적으로 Binding 클래스를 생성할 때 RootView에 tag를 삽입하고, Binding 표현식과 양방향 바인딩 그리고 Binding Adapter를 제공해 동적 UI 콘텐츠를 선언할 수 있습니다.
ViewBinding은 Binding 클래스를 생성하기 위해 annotation processor를 사용하지 않아 DataBinding 보다 빠르고 Binding 표현식과 양방향 바인딩을 제공하지 않기 때문에 단순히 UI Component를 코드에 바인딩하는 용도로 사용됩니다.
결과
Binding 표현식이 필요없는 정도로 로직이 단순하거나 비교적 간단한 앱을 제작한다면 ViewBinding을 사용하고 View와 관련된 로직을 ViewModel에서 수행하여 불필요한 코드를 줄이고 View에 대한 의존성을 낮출 목적으로 사용하고자 한다면 DataBinding을 사용하면 된다고 판단됩니다.
*annotation processor : 자바 컴파일러 플러그인의 일종으로, 어노테이션에 대한 코드베이스를 검사, 수정, 생성하는 역할을 담당하고, 어노테이션을 사용하기 위해서는 어노테이션 프로세서가 필요하다.
'Android > Android의 모든 것' 카테고리의 다른 글
👋Android의 모든 것 : 1️⃣App Manifest, 2️⃣Context (0) | 2022.03.16 |
---|---|
👋Android의 모든 것 : 1️⃣Android, 2️⃣Android SDK, 3️⃣Platform Architecture (0) | 2022.03.16 |
👋Android의 모든 것 : 1️⃣안드로이드에서 백그라운드 작업(Service, IntentService, JobintentService , WorkManager) (0) | 2022.03.11 |
👋Android의 모든 것 : 1️⃣OkHttp, 2️⃣OkHttp Interceptor (0) | 2022.03.08 |
👋Android의 모든 것 : 1️⃣ListView, 2️⃣RecyclerView (0) | 2022.03.07 |