2015-06-10 16 views
5

Làm thế nào để bạn bấm vào một menuItem trong một NavigationView từ thư viện thiết kế bằng cách sử dụng Espresso? Nó hoạt động tốt trên một thiết bị lớn hơn, nơi toàn bộ menu có thể nhìn thấy nhưng trong cảnh quan hoặc thiết bị nhỏ hơn dưới cùng của trình đơn của tôi là tắt màn hình và tôi không thể tìm ra một cách để di chuyển/swipe để các menuItems vì vậy tôi có thể nhấp vào chúng.Làm thế nào để bạn bấm vào một menuItem trong NavigationView trên Android khi thử nghiệm với Espresso?

Calling:

onView(withText(R.string.contact_us)).perform(scrollTo()).check(matches(isDisplayed())).perform(click()); 

Tạo điều sau đây:

Nguyên nhân: java.lang.RuntimeException: Hành động sẽ không được thực hiện vì xem mục tiêu không phù hợp với một hoặc nhiều sau ràng buộc: (chế độ xem có khả năng hiển thị hiệu quả = VISIBLE và là hậu duệ của: (được gán từ class: class android.widget.ScrollView hoặc là có thể gán từ class: class android.widget.Horizon talScrollView)) Chế độ xem mục tiêu: "NavigationMenuItemView {id = -1, mức hiển thị = VISIBLE, chiều rộng = 888, chiều cao = 144, có tiêu điểm = sai, có tiêu điểm = false, has-window-focus = true, là -clickable = false, được kích hoạt = true, is-focus = false, is-focusable = false, is-layout-requested = false, được chọn = false, root-is-layout-requested = false, có-input-kết nối = false, x = 0,0, y = 1653,0, text = Liên hệ, đầu vào-type = 0, ime-target = false, có-liên kết = false}"

NavigationView thừa hưởng từ FrameLayout và đang thực hiện thay đổi canvas để cuộn. https://developer.android.com/reference/android/support/design/widget/NavigationView.html

Tôi đã cố gắng viết customViewAction để từ từ cuộn màn hình bằng cách sử dụng tác vụ bên dưới và kiểm tra xem menuItem có hiển thị và không tiếp tục cuộn, nhưng tôi không thể làm việc đó.

CoordinatesProvider coordinatesProvider = new CoordinatesProvider() { 
     public float[] calculateCoordinates(View view) { 
      float[] xy = GeneralLocation.BOTTOM_CENTER.calculateCoordinates(view); 
      xy[0] += 0.0F * (float)view.getWidth(); 
      xy[1] += -0.083F * (float)view.getHeight(); 
      return xy; 
     } 
    }; 

onView(withId(R.id.navigation_view)).perform(new GeneralSwipeAction(Swipe.SLOW, 
          coordinatesProvider, GeneralLocation.TOP_CENTER, Press.FINGER)); 

onView(withText(R.string.contact_us)).check(matches(isDisplayed())).perform(click()); 

Có ai đã tìm ra cách kiểm tra điều hướngXem trên Espresso chưa? Tôi khá chắc chắn logic của tôi đằng sau customViewAction sẽ làm việc nhưng tôi không thể làm cho nó hoạt động.

Trả lời

3

I figured it out, tôi sử dụng một viewAction tùy chỉnh

public static ViewAction swipeForTextToBeVisible(final String text, final long millis, final View navigationView) { 
     return new ViewAction() { 
      @Override 
      public Matcher<View> getConstraints() { 
       return isRoot(); 
      } 

      @Override 
      public String getDescription() { 
       return "swipe for a specific view with text <" + text + "> during " + millis + " millis."; 
      } 

      @Override 
      public void perform(final UiController uiController, final View view) { 
       uiController.loopMainThreadUntilIdle(); 
       final long startTime = System.currentTimeMillis(); 
       final long endTime = startTime + millis; 
       final Matcher<View> viewMatcher = withText(text); 

       do { 
        boolean returnAfterOneMoreSwipe = false; //not sure why I have to do one more swipe but it works 

        for (View child : TreeIterables.breadthFirstViewTraversal(view)) { 
         // found view with required ID 
         if (viewMatcher.matches(child) && child.getVisibility() == View.VISIBLE) { 
          returnAfterOneMoreSwipe = true; 
         } 
        } 

        CoordinatesProvider coordinatesProvider = new CoordinatesProvider() { 
         public float[] calculateCoordinates(View view) { 
          float[] xy = GeneralLocation.BOTTOM_CENTER.calculateCoordinates(view); 
          xy[0] += 0.0F * (float)view.getWidth(); 
          xy[1] += -0.083F * (float)view.getHeight(); 
          return xy; 
         } 
        }; 

        //Below code is c/p from perform in android/support/test/espresso/action/GeneralSwipeAction.class 
        float[] startCoordinates = coordinatesProvider.calculateCoordinates(navigationView); 
        float[] endCoordinates = GeneralLocation.TOP_CENTER.calculateCoordinates(navigationView); 
        float[] precision = Press.FINGER.describePrecision(); 
        Swiper.Status status = Swiper.Status.FAILURE; 

        for(int tries = 0; tries < 3 && status != Swiper.Status.SUCCESS; ++tries) { 
         try { 
          status = Swipe.SLOW.sendSwipe(uiController, startCoordinates, endCoordinates, precision); 
         } catch (RuntimeException var9) { 
          throw (new PerformException.Builder()).withActionDescription(this.getDescription()).withViewDescription(HumanReadables.describe(navigationView)).withCause(var9).build(); 
         } 

         int duration = ViewConfiguration.getPressedStateDuration(); 
         if(duration > 0) { 
          uiController.loopMainThreadForAtLeast((long)duration); 
         } 
        } 
        //End c/p from android/support/test/espresso/action/GeneralSwipeAction.class 

        if (returnAfterOneMoreSwipe) { 
         return; 
        } 

        uiController.loopMainThreadForAtLeast(50); 
       } 
       while (System.currentTimeMillis() < endTime); 

       // timeout happens 
       throw new PerformException.Builder() 
         .withActionDescription(this.getDescription()) 
         .withViewDescription(HumanReadables.describe(view)) 
         .withCause(new TimeoutException()) 
         .build(); 
      } 
     }; 
    } 

tôi không yêu giải pháp này, nó không phải là sạch nhất vì đối với một số lý do tôi phải swipe một lần nữa sau khi nó nói có thể nhìn thấy nó nhưng nó hoạt động .

Để sử dụng nó, bạn gọi nó với những điều sau đây:

onView(isRoot()).perform(CustomViewActions.swipeForTextToBeVisible(getActivity().getString(R.string.contact_us),2000, getActivity().findViewById(R.id.navigation_view))); 
0

Bạn cần phải sử dụng espresso-contrib:

import android.support.test.espresso.contrib.DrawerActions; 

Để mở menu, bạn có thể làm điều này:

onView(withId(R.id.drawer_layout)).perform(DrawerActions.open()); 

Bạn có thể cuộn xuống mục menu và kiểm tra xem nó có được hiển thị hay không:

onView(withId(R.id.my_menu_item)).perform(scrollTo()).check(matches(isDisplayed())); 

Và bấm vào mục menu:

onView(withId(R.id.my_menu_item)).perform(click()); 
1

này làm việc cho tôi ngay cả khi mục trình đơn là không nhìn thấy được (ở đâu đó xuống trong danh sách)

OnView (withId (R.id. nav_view)) thực hiện (NavigationViewActions.navigateTo (R.id.nav_login));

Các vấn đề liên quan