在 Android 上拖放按钮的问题

Issues with Drag and Drop of a Button on Android

我希望能够在用户拖动按钮时移动它。我正在使用在 API 级别 11 中介绍的拖放 API,它可以正常工作。这是代码:

    public class MainActivity extends Activity {

        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);

            setContentView(R.layout.activity_test);

            final Button button = (Button) findViewById(R.id.button);

            button.setOnLongClickListener(new View.OnLongClickListener() {

                @Override
                public boolean onLongClick(View v) {
                    v.startDrag(null, new View.DragShadowBuilder(v), null, 0);

                    return true;
                }
            });

            findViewById(R.id.test_main_layout).setOnDragListener(new View.OnDragListener() {

                @Override
                public boolean onDrag(View v, DragEvent event) {
                    switch (event.getAction()) {
                        case DragEvent.ACTION_DRAG_STARTED:
                            button.setVisibility(View.INVISIBLE);
                            break;

                        case DragEvent.ACTION_DROP:
                            button.setY(event.getY() - button.getHeight() / 2.F);
                            button.setX(event.getX() - button.getWidth() / 2.F);
                            break;

                        case DragEvent.ACTION_DRAG_ENDED:
                            button.setVisibility(View.VISIBLE);
                            break;
                    }

                    return true;
                }
            });
        }
    }

    <?xml version="1.0" encoding="utf-8"?>
    <RelativeLayout
        android:id="@+id/test_main_layout"
        xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <TextView
            android:id="@+id/edit"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"/>

        <Button
            android:id="@+id/button"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_below="@+id/edit"
            android:text="Some text"/>

    </RelativeLayout>

目前的行为是,当用户按住按钮时,按钮消失,'shadow' 出现并被拖来拖去。然后,当拖动完成时,阴影将替换为真正的按钮。

它的工作方式有两个问题:

  1. 当用户停止拖动时有一个难看的闪烁?看起来好像有一小会儿阴影消失了,真正的按钮还没有显示出来。有没有可能以某种方式摆脱它?

  2. 当 EditText 获得焦点时,行为会发生变化。只需将 XML 中的 TextView 更改为 EditText 即可重现它。通过此更改,拖动阴影时原始按钮不会消失,两者都可见!为什么会这样以及如何解决这个问题?

我正在两台设备上测试它,一台是 5.0.1,另一台是 5.1,行为是一致的(两个问题)。

原来问题#2(按钮没有消失)是由这个引起的:https://code.google.com/p/android/issues/detail?id=25073。简而言之,由于某种原因,具有 ACTION_DRAG_STARTED 的 mu onDrag() 永远不会被称为 EditText(或实际上是 TextView)#onDragEvent returns true 当它具有焦点时:

case DragEvent.ACTION_DRAG_STARTED:
            return mEditor != null && mEditor.hasInsertionController();

mEditor 在这种情况下不为空。对于我,我更改了逻辑以不依赖于调用的开始,将代码移到其他地方并且它工作正常。