배경 크기를 조정하지 않고 Android 버튼의 히트 영역을 늘리는 방법은 무엇입니까?
커스텀 드로어 블이있는 버튼이 있습니다.
<Button
android:layout_width="22dip"
android:layout_height="23dip"
android:background="@drawable/triangle" />
드로어 블은 배경이 투명한 삼각형입니다.
|\
| \
|__\
이 버튼을 누르기가 어렵습니다. 첫째, 상대적으로 작습니다. 둘째, 투명 픽셀은 탭할 수 없습니다. 드로어 블을 같은 크기로 유지하고 싶지만 히트 영역을 삼각형 크기의 두 배로 정사각형 모양으로 만듭니다.
_____________
| |
| |\ |
| | \ |
| |__\ |
|____________|
TouchDelegate API를 사용할 수 있습니다.
final View parent = (View) button.getParent(); // button: the view you want to enlarge hit area
parent.post( new Runnable() {
public void run() {
final Rect rect = new Rect();
button.getHitRect(rect);
rect.top -= 100; // increase top hit area
rect.left -= 100; // increase left hit area
rect.bottom += 100; // increase bottom hit area
rect.right += 100; // increase right hit area
parent.setTouchDelegate( new TouchDelegate( rect , button));
}
});
당신은 "패딩"을 원합니다. 그것은 뷰 내부에 공간을 둘 것입니다. 여백은 공간을 외부에 두어 히트 영역을 늘리지 않습니다.
<Button
android:layout_width="22dip"
android:layout_height="23dip"
android:background="@drawable/triangle"
android:padding="10dp" />
당신은 사용할 필요가 TouchDelegate
"실제 뷰 범위보다 더 큰 터치 영역을 가지고 당신이보기를 원하는 핸들 상황에 도우미 클래스"로 API 문서에 정의 된을,
http://developer.android.com/reference/android/view/TouchDelegate.html
이 솔루션을 선호합니다.
레이아웃 리소스 파일에 양수 여백과 음수 여백을 추가하기 만하면됩니다.
<some.View
..
android:padding="12dp"
android:margin="-12dp"
.. />
이것은 TouchDelegates 사용에 비해 매우 작은 변화입니다. 또한 Java 코드 내부에 클릭 가능한 영역을 추가하기 위해 Runnable을 실행하고 싶지 않습니다.
뷰가 픽셀 완벽해야하는 경우 고려할 수있는 한 가지 : 패딩 이 항상 margin 과 같을 수는 없습니다 . 패딩 지정된 항상 정확히이 있어야합니다. 마진 주변 뷰에 의존하여 오프셋 될 마진 다른보기의 값.
버튼에 패딩을 추가하기 만하면
<Button
android:layout_width="wrap_contant"
android:layout_height="wrap_contant"
android:background="@drawable/triangle"
android:padding="20dp" />
이렇게하면 버튼이 삼각형 이미지의 높이와 너비를 가져 와서 이미지 자체를 늘리지 않고 버튼에 20dp 패딩을 추가합니다. 최소 너비 또는 최소 높이를 원하면 minWidth
및 minHeight
태그를 사용할 수 있습니다.
답변을 바탕으로 kotlin 확장 기능을 만들었습니다.
/**
* Increase the click area of this view
*/
fun View.increaseHitArea(dp: Float) {
// increase the hit area
val increasedArea = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dp, Resources.getSystem().displayMetrics).toInt()
val parent = parent as View
parent.post {
val rect = Rect()
getHitRect(rect)
rect.top -= increasedArea
rect.left -= increasedArea
rect.bottom += increasedArea
rect.right += increasedArea
parent.touchDelegate = TouchDelegate(rect, this)
}
}
"배경 드로어 블을 늘리지 않고"의 의미를 잘 모르겠습니다. 드로어 블이 늘어나는 것을 원하지 않는 경우, 한 가지 옵션은 배경 png를 가져와 여기에 투명 픽셀 테두리를 추가하는 것입니다. 그러면 히트 영역이 증가하지만 이미지가 늘어나지는 않습니다.
그러나 드로어 블을 전혀 변경하지 않으려는 경우 유일한 옵션은 높이와 너비에 더 큰 하드 코드 값을 사용하는 것입니다.
이것으로 시도
<Button
android:id="@+id/btn_profile"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_alignParentLeft="true"
android:background="@android:color/transparent"
android:drawableBottom="@drawable/moreoptionicon"
android:onClick="click"
android:paddingBottom="15dp"
android:visibility="visible" />
프로그래밍 방식으로 클릭 영역의 버튼을 늘릴 수 있습니까?를 참조하십시오 . . 이것은 확실히 나에게 가장 쉬운 방법처럼 보입니다. 배경이 클릭을받을 수 있도록 허용하면서 실제 클릭 가능한 개체 만 애니메이션하는 방법도 포함합니다. 곧 내 코드에 적용 할 것입니다.
이것은 나를 위해 일했습니다.
public void getHitRect(Rect outRect) {
outRect.set(getLeft(), getTop(), getRight(), getBottom() + 30);
}
실제로 30을 딥으로 변환하거나 버튼 높이의 백분율을 수행해야합니다.
버튼 이미지보다 더 큰 클릭 가능한 영역이 필요했습니다. 배경 드로어 블보다 큰 FrameLayout으로 감싸고 내부 Button 태그를 TextView로 변경했습니다. 클릭 핸들러가 내부 TextView가 아닌이 FrameLayout과 함께 작동하도록 지시 한 것보다. 모두 잘 작동합니다!
이렇게 투명한 버튼을 사용할 수 있습니다.
<Button
android:layout_width="50dp"
android:layout_height="50dp"
android:background="@android:color/transparent" />
필요에 따라 버튼 크기를 늘리거나 줄일 수 있으며 버튼 enter code here
위로 ImageView를 사용할 수 있습니다 ....
<ImageView
android:layout_width="22dip"
android:layout_height="23dip"
android:background="@drawable/triangle" />
이를 위해 ImageButton을 사용했습니다. xml 방어에서 다음 두 가지 속성을 볼 수 있습니다.
- android : background-배경 으로 사용할 드로어 블입니다.
- android : scr- 드로어 블을이 ImageView의 콘텐츠로 설정합니다.
그래서 우리는 두 개의 드로어 블을 가지고 있습니다 : 배경 1과 소스. 예제 소스는 triagle (drawable / trianlge)입니다.
|\
| \
|__\
그리고 배경은 정사각형 (드로어 블 / 정사각형)입니다.
_____________
| |
| |
| |
| |
|____________|
다음은 ImageButton xml의 예입니다.
<ImageButton
...
android:src="@drawable/triangle"
android:background="@drawable/square">
결과:
_____________
| |
| |\ |
| | \ |
| |__\ |
|____________|
또한 사각형 드로어 블은 여러 다른 상태 (눌림, 초점)를 가질 수 있습니다. 패딩을 사용하여 배경 드로어 블 크기를 확장 할 수 있습니다.
경우에 따라 Android Compat Actionbar에서 배경 드로어 블의 예는 다음과 같습니다.
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<!-- Even though these two point to the same resource, have two states so the drawable will invalidate itself when coming out of pressed state. -->
<item android:state_focused="true" android:state_enabled="false" android:state_pressed="true" android:drawable="@drawable/abc_list_selector_disabled_holo_dark" />
<item android:state_focused="true" android:state_enabled="false" android:drawable="@drawable/abc_list_selector_disabled_holo_dark" />
<item android:state_focused="true" android:state_pressed="true" android:drawable="@drawable/abc_list_selector_background_transition_holo_dark" />
<item android:state_focused="false" android:state_pressed="true" android:drawable="@drawable/abc_list_selector_background_transition_holo_dark" />
<item android:state_focused="true" android:drawable="@drawable/abc_list_focused_holo" />
<item android:drawable="@android:color/transparent" />
</selector>
패딩을 뷰 즉 버튼으로 설정할 수 있습니다.
<Button
android:layout_width="50dp"
android:layout_height="50dp"
android:background="@android:color/transparent"
android:padding="15dp" />
이것이 당신을 위해 작동하기를 바랍니다.
따라서 정답 은 터치 가능한 영역 에 패딩 을 추가 하면 커지고 사진을 배경에서 srcCompact로 변경합니다 .
<Button
android:layout_width="22dip"
android:layout_height="23dip"
android:padding="6dp"
app:srcCompat="@drawable/triangle"/>
app : scrCompat를 사용하려면 xmlns:app="http://schemas.android.com/apk/res-auto"
xml의 기본 / 상위 요소에 추가 해야합니다.
예제 완료 :
<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="@dimen/height_btn_bottom_touch_area"
android:background="@color/bg_white"
android:clipToPadding="false"
android:elevation="7dp">
<android.support.constraint.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:stateListAnimator="@animator/selected_raise"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent" >
<ImageView
android:id="@+id/bottom_button_bg"
android:layout_width="0dp"
android:layout_height="0dp"
android:contentDescription=
"@string/service_request_background_contentDescription"
android:elevation="1dp"
android:padding="6dp"
app:srcCompat="@drawable/btn_round_blue"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent" >
</ImageView>
<TextView
android:id="@+id/bottom_button_text"
android:layout_width="0dp"
android:layout_height="0dp"
android:elevation="1dp"
android:gravity="center"
android:text="@string/str_continue_save"
android:textColor="@color/text_white"
android:textSize="@dimen/size_text_title"
android:textStyle="bold"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</android.support.constraint.ConstraintLayout>
</android.support.constraint.ConstraintLayout>
Just adding padding was causing my checkbox to not be centered. The following worked for me, however I specified a fixed size for the checkbox (as per my UI spec). The idea was to add padding to the left and not to the right. I added padding to the top and bottom too making the touch target larger and still keeping the checkbox centered.
<CheckBox
android:id="@+id/checkbox"
android:layout_width="30dp"
android:layout_height="45dp"
android:paddingLeft="15dp"
android:paddingTop="15dp"
android:paddingBottom="15dp"
android:button="@drawable/checkbox"
android:checked="false"
android:gravity="center"
/>
I think the correct answer should be using ImageButton instead of Button. Set the triangle drawable as the "src" of the ImageButton, and set the size (layout_width & layout_height) as you want for easier touch and set the ScaleType to center to retain the triangle size.
I created the top-level function for this in kotlin:
fun increaseTouchArea(view: View, increaseBy: Int) {
val rect = Rect()
view.getHitRect(rect)
rect.top -= increaseBy // increase top hit area
rect.left -= increaseBy // increase left hit area
rect.bottom += increaseBy // increase bottom hit area
rect.right += increaseBy // increase right hit area
view.touchDelegate = TouchDelegate(rect, view)
}
I honestly think the easiest way is this:-
Say your image size is 26dp*26dp and you want a hit area of 30dp*30dp, just add a padding of 2dp to your ImageButton/Button AND set the dimension to 30dp*30dp
Original
<ImageButton
android:layout_width="26dp"
android:layout_height="26dp"
android:src="@drawable/icon"/>
Bigger hit area
<ImageButton
android:layout_width="30dp"
android:layout_height="30dp"
android:padding="2dp"
android:src="@drawable/icon_transcript"/>
<Button
android:layout_width="32dp"
android:layout_height="36dp"
android:layout_margin="5dp"
android:background="@drawable/foo"
/>
The size of the background is still 22x26dp. Just add margin.
'IT TIP' 카테고리의 다른 글
REST 리소스 URL의 쿼리 문자열 (0) | 2020.10.31 |
---|---|
마우스 오버시 캔버스에서 픽셀 색상 가져 오기 (0) | 2020.10.31 |
Java 리플렉션은 모든 개인 필드를 가져옵니다. (0) | 2020.10.31 |
선택 쿼리에서 자동 증가 필드를 생성하는 방법 (0) | 2020.10.31 |
Unix / Linux 플랫폼에서 OS 이름과 버전을 찾는 가장 좋은 방법 (0) | 2020.10.31 |