Android 如何模拟活动单元测试的自定义ImageView

Android 如何模拟活动单元测试的自定义ImageView,android,unit-testing,android-animation,android-imageview,android-espresso,Android,Unit Testing,Android Animation,Android Imageview,Android Espresso,我有一个LoginActivity,它在onResume()中加载SplashFragment splash片段的布局XML包含一个名为RotatingImageView的自定义ImageView,顾名思义,它会在源图像连接到窗口后立即开始旋转源图像 现在,当我尝试使用ActivityInstrumentationTestCase2为LoginActivity编写单元测试时,这会导致问题。我试图在真实的设备(无根设备)上运行测试,而不是在模拟器上 getActivity()调用启动活动,但由于旋

我有一个
LoginActivity
,它在
onResume()中加载
SplashFragment

splash片段的布局XML包含一个名为
RotatingImageView
的自定义
ImageView
,顾名思义,它会在源图像连接到窗口后立即开始旋转源图像

现在,当我尝试使用
ActivityInstrumentationTestCase2
LoginActivity
编写单元测试时,这会导致问题。我试图在真实的设备(无根设备)上运行测试,而不是在模拟器上

getActivity()
调用启动活动,但由于旋转图像视图(这是一个动画窗口),浓缩咖啡被卡住了。我知道浓缩咖啡不喜欢那里的动画。我有例外

“浓缩咖啡无法在45秒内启动intent。可能是主咖啡 线程没有在合理的时间内空闲?有吗 可能是一个动画或是不断重新绘制屏幕的东西。 或者该活动正在创建时进行网络调用?请参阅线程转储 日志。供您参考上次事件队列空闲的时间 您的活动启动请求是1487296262885,现在是最后一次 队列闲置的时间是:1487296262885。如果这些数字相同 您的活动可能占用了事件队列…”

现在很明显,问题是如何停止/模拟动画

  • 我已经从设备->设置->开发人员选项中禁用了所有动画选项,但当活动启动时,我仍然看到图像旋转,因此这没有帮助

  • 我也调查过,但这对我也没什么帮助。我可能做错了,但不管怎样,这没有用

  • 另一个选项是使用特殊意图启动
    LoginActivity
    ,该意图告诉活动这是在测试下启动的,因此当加载片段时,它将禁用动画。此方法可以工作,但并不理想,因为它涉及在主类中添加代码,而主类纯粹用于测试

  • 另一种解决方案是模拟
    旋转ImageView
    ,并在开始加载之前将其注入
    SplashFragment
    。我会模拟出对
    startspininganimation
    的调用,这样当它加载到窗口时就不会启动动画


    我的问题是:可能吗?在调用
    getActivity()
    之前,我可以模拟并将这个自定义的
    imageView
    注入到我的片段中吗?

    是的,您可以创建一个名为
    AnimationUtil
    的类,将动画方法放在该类中,并在测试期间模拟它们

    public Animation getWhateverAnimation(int duration){
        RotateAnimation anim = new RotateAnimation(0f, 350f, 15f, 15f);
        anim.setInterpolator(new LinearInterpolator());
        anim.setRepeatCount(Animation.INFINITE);
        anim.setDuration(duration);
        return anim;
    }
    
    并在
    androidTest
    包(非
    main
    包)中创建一个
    MockAnimationUtil
    扩展
    AnimationUtil
    ,并重写和方法

    public Animation getWhateverAnimation(int duration){
        return super.getWhateverAnimation(0);
    }
    

    谢谢这很有效。我将动画逻辑从
    CustomImageView
    中取出,放到一个单独的类中。该片段将从
    MyApplication
    获取此实例。在测试中,我可以在启动测试活动之前在
    MyApplication
    实例中注入一个模拟实例。作品