仅为TextView复合drawable实现onClick

Gia*_*nzi 25 android onclick textview android-layout

我需要有一些文字与左边被拉伸,我想,当用户点击/触摸图像(仅图像,而不是文字)来执行一些代码,所以我用了一个LinearLayout中具有的TextViewImageView的是可点击并启动onClick事件.XML解析器建议我用带有复合drawableTextView替换它,这将用更少的XML行绘制相同的东西.我的问题是"我可以指定我只想在on drawable上处理onClick事件TextView而不是TextView本身?我见过一些解决方案,包括编写你自己的TextView扩展,但我只对能够在布局资源中做到这一点感兴趣,如果可能的话,我会保留以下内容XML代码:

<LinearLayout
        xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:gravity="center"
        android:orientation="horizontal" >

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:gravity="bottom"
            android:paddingTop="10dp"
            android:paddingLeft="10dp"
            android:paddingRight="10dp"
            android:text="@string/home_feedback_title"
            android:textColor="@android:color/primary_text_dark"
            android:textStyle="bold" 
            android:paddingBottom="4dp"/>


        <ImageView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:src="@drawable/action_feedback" 
            android:clickable="true"
            android:onClick="onClickFeedback"
            android:contentDescription="@string/action_feedback_description"/>
</LinearLayout>
Run Code Online (Sandbox Code Playgroud)

Vis*_*san 38

它非常简单.假设你在TextView的'txtview'的左侧有一个drawable.以下将做到这一点.

TextView txtview = (TextView) findViewById(R.id.txtview);
txtview.setOnTouchListener(new OnTouchListener() {
    @Override
    public boolean onTouch(View v, MotionEvent event) {
        if(event.getAction() == MotionEvent.ACTION_UP) {
            if(event.getRawX() <= txtview.getTotalPaddingLeft()) {
                // your action for drawable click event

             return true;
            }
        }
        return true;
    }
});
Run Code Online (Sandbox Code Playgroud)

如果你想要正确的drawable改变if语句:

if(event.getRawX() >= txtview.getRight() - txtview.getTotalPaddingRight())
Run Code Online (Sandbox Code Playgroud)

同样,您可以为所有复合drawables执行此操作.

txtview.getTotalPaddingTop();
txtview.getTotalPaddingBottom();
Run Code Online (Sandbox Code Playgroud)

此方法调用返回该侧的所有填充,包括任何drawable.您甚至可以将它用于TextView,Button等.

点击这里从android开发者网站获取参考.


Jer*_*rds 7

你可以去任何一个方向.使用复合drawable更快,因为它旨在进行优化.它使用较少的ram,因为你将3个视图减少为1,并且它的布局更快,因为你失去了1个深度.

如果我是你,我会考虑退一步看看文字和图像是否拦截触摸做任何动作都可能是一件好事.通常,具有更大的触摸区域使得更容易按压.有些用户实际上可能倾向于触摸文本而不是图像.

最后,如果你走合并2的路线,你可能要考虑使用a Button而不是a TextView.您可以设置按钮的样式,使其周围没有矩形.他们称之为无边框按钮.因为你得到你一个动作项,其中作为点击视觉反馈很高兴ImageViewTextView通常是不可诉的.

如何在Android中创建无边框按钮


Tak*_*ori 6

@Vishnuvathsan 的回答几乎是完美的,但会getRaw()返回接触点的绝对 x 位置。如果 textview 不在视图的左边缘,则应使用getLocationOnScreen. 下面的代码是一个检查左可绘制点击和右可绘制点击的示例。

textView.setOnTouchListener(new OnTouchListener() {
    @Override
    public boolean onTouch(View v, MotionEvent event) {
        if (event.getAction() == MotionEvent.ACTION_UP) {
            int[] textLocation = new int[2];
            textView.getLocationOnScreen(textLocation);

            if (event.getRawX() <=  textLocation[0] + textView.getTotalPaddingLeft()) {

                // Left drawable was tapped

                return true;
            }


            if (event.getRawX() >= textLocation[0] + textView.getWidth() - textView.getTotalPaddingRight()){

                // Right drawable was tapped

                return true;
            }
        }
        return true;
    }
});
Run Code Online (Sandbox Code Playgroud)