본문 바로가기
카테고리 없음

안드로이드 ImageView Radius 주기

by ESC-Corp 2022. 3. 2.
728x90

이미지를 넣은 경우 단순 백그라운드로 생성했던 Radius가 깨지고 정사각형의 이미지가 나오게 된다.

이것을 해결하기 위해서 라이브러리를 이용하거나 직접적으로 imageView Radius를 주는 방법이 있다.

 

라이브러리의 경우에는 각자 편하신 방법으로 사용하시면 됩니다. 저는 직접 만들어서 사용하는 방법을 소개합니다.

 

1. clipToOutline = true 이용하기

 

//kotlin
imageView.clipToOutline = true

이미지뷰의 clipToOutline을 true로 설정해 줍니다. 그 후, 우리가 적용하려는 이미지뷰의 백그라운에 Shape를 통해서 이미지뷰의 모양을 변경하는 것입니다. 

<ImageView
    android:id="@+id/iv"
    android:layout_width="100dp"
    android:layout_height="100dp"
    android:scaleType="centerCrop"
    android:background="@drawable/background_round"/>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="oval">
</shape>

이 경우 단점은 단순 모양으로 진행해야 한다는 점입니다. shape만 지정 가능하고 실제 height는 imageview를 통해 지정해야 합니다.

 

2. CardView를 통한 외곽 모서리 처리

<androidx.cardview.widget.CardView
        android:id="@+id/cardview"
        android:layout_width="100dp"
        android:layout_height="100dp"
        android:elevation="10dp"
        app:cardCornerRadius="20dp">
        
        <ImageView
                android:id="@+id/iv"
                android:layout_width="match_parent"
                android:layout_height="match_parent"/>
                
 </androidx.cardview.widget.CardView>

 

3. 직접 구현하는 방법

fun roundLeft(iv: ImageView, curveRadius : Float)  : ImageView {

   if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {

       iv.outlineProvider = object : ViewOutlineProvider() {

           @RequiresApi(Build.VERSION_CODES.LOLLIPOP)
           override fun getOutline(view: View?, outline: Outline?) {
               outline?.setRoundRect(0, 0, (view!!.width+curveRadius).toInt(), (view.height).toInt(), curveRadius)
           }
       }

       iv.clipToOutline = true
   }
   return iv
}

fun roundAll(iv: ImageView, curveRadius : Float)  : ImageView {

   if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {

       iv.outlineProvider = object : ViewOutlineProvider() {

           @RequiresApi(Build.VERSION_CODES.LOLLIPOP)
           override fun getOutline(view: View?, outline: Outline?) {
               outline?.setRoundRect(0, 0, view!!.width, view.height, curveRadius)
           }
       }

       iv.clipToOutline = true
   }
   return iv
}

fun roundTop(iv: ImageView, curveRadius : Float)  : ImageView {

   if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {

       iv.outlineProvider = object : ViewOutlineProvider() {

           @RequiresApi(Build.VERSION_CODES.LOLLIPOP)
           override fun getOutline(view: View?, outline: Outline?) {
               outline?.setRoundRect(0, 0, view!!.width, (view.height+curveRadius).toInt(), curveRadius)
           }
       }

       iv.clipToOutline = true
   }
   return iv
}

fun dipToPixels(context: Context, dipValue: Float): Float {
    val metrics = context.resources.displayMetrics
    return TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dipValue, metrics)
}

사용은 아래와 같이 필요한 곳에서 부르면 됩니다.

roundAll(binding.ivStoreDetailImage, 10f)
roundTop(imgview, dipToPixels(myContext, 20f))

그런데 아쉽게도 오른쪽만, 그리고 아래쪽만 코너를 주는 방법은 찾지 못 했습니다.

 

출처 : https://velog.io/@ejjjang0414/%EC%95%88%EB%93%9C%EB%A1%9C%EC%9D%B4%EB%93%9C-ImageView-round-corner-radius-%EC%A3%BC%EA%B8%B0-%EC%9D%B4%EB%AF%B8%EC%A7%80%EB%B7%B0-%EC%BD%94%EB%84%88-%EB%91%A5%EA%B8%80%EA%B2%8C-%ED%95%98%EA%B8%B0

728x90

댓글