2017-03-04 60 views
0

我使用动画根据用户操作移动视图(视图1,视图2)。 在特定情况下,两个视图重叠。安卓咖啡测试更高:视图1高于视图2

我想确保查看1高于查看2。 问题是,查看1不在查看2(他们重叠),所以我不能使用断言isAbove

我该如何测试该场景?

回答

0

我找到了解决办法,并在这里张贴是否有人会需要它:

我创建了一个CustomViewAssertions类和PositionAssertions复制的相关部分类:

relativePositionOf - 不已更改

findView - 完全不同,因为它使用内部类

getTopViewGroup - 没有改变

isRelativePosition - 更改比较逻辑

位置 - 新枚举值

最终结果:

public class CustomViewAssertions { 
    public static ViewAssertion isHigher(Matcher<View> matcher) { 
     return relativePositionOf(matcher, Position.HIGHER); 
    } 

    public static ViewAssertion isHigherOrSame(Matcher<View> matcher) { 
     return relativePositionOf(matcher, Position.HIGHER_OR_SAME); 
    } 

    private static ViewAssertion relativePositionOf(final Matcher<View> viewMatcher, 
                final Position position) { 
     return new ViewAssertion(){ 
      @Override 
      public void check(final View foundView, NoMatchingViewException noViewException) { 
       StringDescription description = new StringDescription(); 
       if (noViewException != null) { 
        description.appendText(String.format(
          "' check could not be performed because view '%s' was not found.\n", 
          noViewException.getViewMatcherDescription())); 
        throw noViewException; 
       } else { 
        description.appendText("View:").appendText(HumanReadables.describe(foundView)) 
           .appendText(" is not ") 
           .appendText(position.toString()) 
           .appendText(" view ") 
           .appendText(viewMatcher.toString()); 
        assertThat(description.toString(), isRelativePosition(foundView, findView(viewMatcher, getTopViewGroup(foundView)), position), is(true)); 
       } 
      } 
     }; 
    } 

    private static View findView(Matcher<View> viewMatcher, View topViewGroup) { 
     Iterable<View> views = breadthFirstViewTraversal(topViewGroup); 
     LinkedList<View> matchedViews = new LinkedList<>(); 
     for (View view : views) { 
      if (viewMatcher.matches(view)) { 
       matchedViews.add(view); 
      } 
     } 
     if (matchedViews.isEmpty()) { 
      throw new NoMatchingViewException.Builder() 
        .withViewMatcher(viewMatcher) 
        .withRootView(topViewGroup) 
        .build(); 
     } 
     if (matchedViews.size() == 1) { 
      return matchedViews.get(0); 
     } 

     // Ambiguous! 
     throw new AmbiguousViewMatcherException.Builder() 
       .withRootView(topViewGroup) 
       .withViewMatcher(viewMatcher) 
       .withView1(matchedViews.remove(0)) 
       .withView2(matchedViews.remove(0)) 
       .withOtherAmbiguousViews(matchedViews.toArray(new View[matchedViews.size()])) 
       .build(); 
    } 

    private static ViewGroup getTopViewGroup(View view) { 
     ViewParent currentParent = view.getParent(); 
     ViewGroup topView = null; 
     while (currentParent != null) { 
      if (currentParent instanceof ViewGroup) { 
       topView = (ViewGroup) currentParent; 
      } 
      currentParent = currentParent.getParent(); 
     } 
     return topView; 
    } 

    private static boolean isRelativePosition(View view1, View view2, Position position) { 
     int[] location1 = new int[2]; 
     int[] location2 = new int[2]; 
     view1.getLocationOnScreen(location1); 
     view2.getLocationOnScreen(location2); 

     switch (position) { 
      case HIGHER: 
       return location1[1] < location2[1]; 
      case HIGHER_OR_SAME: 
       return location1[1] <= location2[1]; 
      default: 
       return false; 
     } 
    } 

    private enum Position { 
     HIGHER("higher"), 
     HIGHER_OR_SAME("higher or same"); 

     private final String positionValue; 

     Position(String value) { 
      positionValue = value; 
     } 

     @Override 
     public String toString() { 
      return positionValue; 
     } 
    } 
}