Android 使用Robotium在自定义视图组中测试拖放行为

Android 使用Robotium在自定义视图组中测试拖放行为,android,testing,drag-and-drop,tdd,robotium,Android,Testing,Drag And Drop,Tdd,Robotium,我正在尝试在自定义视图组中测试拖放行为。我试过用浓缩咖啡,但它没有那种功能。所以现在我正在尝试使用机器人。但我的测试给出了这个错误: java.lang.RuntimeException:无法从主应用程序线程调用此方法 代码: 编辑: 我已经看过了,有两种方法:长点击查看和拖动,当它们结合在一起时,似乎能完全满足我的需要。这是我对这两种方法的结合: public void longClickViewAndDrag(InstrumentationTestCase test,

我正在尝试在自定义视图组中测试拖放行为。我试过用浓缩咖啡,但它没有那种功能。所以现在我正在尝试使用机器人。但我的测试给出了这个错误:

java.lang.RuntimeException:无法从主应用程序线程调用此方法

代码:

编辑:

我已经看过了,有两种方法:长点击查看和拖动,当它们结合在一起时,似乎能完全满足我的需要。这是我对这两种方法的结合:

public void longClickViewAndDrag(InstrumentationTestCase test,
                          View v,
                          float toX, float toY,
                          int stepCount) {
    int[] xy = new int[2];
    v.getLocationOnScreen(xy);

    final int viewWidth = v.getWidth();
    final int viewHeight = v.getHeight();

    float x = xy[0] + (viewWidth / 2.0f);
    float y = xy[1] + (viewHeight / 2.0f);

    Instrumentation inst = test.getInstrumentation();

    long downTime = SystemClock.uptimeMillis();
    long eventTime = SystemClock.uptimeMillis();

    MotionEvent event = MotionEvent.obtain(downTime, eventTime,
                                           MotionEvent.ACTION_DOWN, x, y, 0);
    inst.sendPointerSync(event);
    inst.waitForIdleSync();

    eventTime = SystemClock.uptimeMillis();
    final int touchSlop = ViewConfiguration.get(v.getContext()).getScaledTouchSlop();
    event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE,
                               x + touchSlop / 2, y + touchSlop / 2, 0);
    inst.sendPointerSync(event);
    inst.waitForIdleSync();

    try {
        Thread.sleep((long)(ViewConfiguration.getLongPressTimeout() * 1.5f));
    } catch (InterruptedException e) {
        e.printStackTrace();
    }

    float yStep = (toY - y) / stepCount;
    float xStep = (toX - x) / stepCount;

    for (int i = 0; i < stepCount; ++i) {
        Log.d("STEP", "..." + i);
        y += yStep;
        x += xStep;
        eventTime = SystemClock.uptimeMillis();
        event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE, x, y, 0);
        inst.sendPointerSync(event);
    }

    eventTime = SystemClock.uptimeMillis();
    event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_UP, x, y, 0);
    inst.sendPointerSync(event);
    inst.waitForIdleSync();
}
出于某种原因,执行inst.sendPointerSyncevent后,测试停止

编辑:

我创建了一个新帖子,更好地描述了真正的问题:

具有以下特征:


谢谢你的建议!我正在尝试测试代码,我长时间单击一个视图,然后将它拖到一个位置,而不让它离开视图,直到它被放置到所需的位置。我尝试在指定的时间段内执行clickLongOnViewView v,int time,但此方法是同步的,因此拖动直到上一个方法结束才开始。请尝试将Robotium更新为5。我不确定这是否有效,但clickOnLongView在Robotium小于4.0时有问题。注意TouchUtils现在不推荐使用atedhttps://developer.android.com/reference/android/test/TouchUtils.html
public void longClickViewAndDrag(InstrumentationTestCase test,
                          View v,
                          float toX, float toY,
                          int stepCount) {
    int[] xy = new int[2];
    v.getLocationOnScreen(xy);

    final int viewWidth = v.getWidth();
    final int viewHeight = v.getHeight();

    float x = xy[0] + (viewWidth / 2.0f);
    float y = xy[1] + (viewHeight / 2.0f);

    Instrumentation inst = test.getInstrumentation();

    long downTime = SystemClock.uptimeMillis();
    long eventTime = SystemClock.uptimeMillis();

    MotionEvent event = MotionEvent.obtain(downTime, eventTime,
                                           MotionEvent.ACTION_DOWN, x, y, 0);
    inst.sendPointerSync(event);
    inst.waitForIdleSync();

    eventTime = SystemClock.uptimeMillis();
    final int touchSlop = ViewConfiguration.get(v.getContext()).getScaledTouchSlop();
    event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE,
                               x + touchSlop / 2, y + touchSlop / 2, 0);
    inst.sendPointerSync(event);
    inst.waitForIdleSync();

    try {
        Thread.sleep((long)(ViewConfiguration.getLongPressTimeout() * 1.5f));
    } catch (InterruptedException e) {
        e.printStackTrace();
    }

    float yStep = (toY - y) / stepCount;
    float xStep = (toX - x) / stepCount;

    for (int i = 0; i < stepCount; ++i) {
        Log.d("STEP", "..." + i);
        y += yStep;
        x += xStep;
        eventTime = SystemClock.uptimeMillis();
        event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE, x, y, 0);
        inst.sendPointerSync(event);
    }

    eventTime = SystemClock.uptimeMillis();
    event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_UP, x, y, 0);
    inst.sendPointerSync(event);
    inst.waitForIdleSync();
}
public void drag(
        float fromX,
        float toX,
        float fromY,
        float toY,
        int stepCount
)