9

Я хочу реализовать recyclerview в вертикальном viewpager. Мой текущий макет выглядит следующим образом:Android: RecyclerView в вертикальном viewpager

VerticalViewpager 
- Fragment1 
    - ImageView 
- Fragment2 
    - RecyclerView 

Если я провёл от фрагмента 1 до фрагмента 2, все будет хорошо. Я могу прокручивать в recyclerview вверх и вниз. Проблема возникает, если я пытаюсь прокручивать/прокручивать назад до Fragment1.

Если пользователь прокрутил до верхней части recyclerview, я хотел бы переслать следующее событие «Вверх» -Scroll на вертикальный просмотрщик. Я пробовал переопределить метод onInterceptTouchEvent, но, к сожалению, до сих пор нет успеха. Есть идеи? Спасибо за помощь :)

+0

Привет! Мне нужно сделать то же самое, какую-нибудь удачу? – Caique

+0

Привет @Caique, к сожалению, нет решения, которое работает во всех наших случаях. Предложение от г-на Индии было полезным для нас, но, как я уже упоминал в своем комментарии ниже его предложения, это решение не работает каждый раз. – jennymo

+0

Thys для ответа. Я сделал это: я перезаписал onTouch для recycliewiew, получил скорость от ACTION_DOWN, ACTION_MOVE и ACTION_UP, и если скорость> 500 (идет вверх с некоторой скоростью), я возвращаюсь на одну позицию на viewpager. Он работает очень хорошо. Я отправлю в качестве ответа с кодом, может быть, может помочь вам – Caique

ответ

2

Вам необходимо отключить scroll. Попробуйте использовать recyclerView.setNestedScrollingEnabled(false);

+1

Привет, за ваш ответ.Я пробовал это, и это работает ... иногда: D Если я достиг вершины recycliewiew, я должен прокручивать по крайней мере четыре или пять раз, пока VerticalViewpager не получит событие и не прокрутится до Fragment1. Любая идея, что вызывает такое поведение? – jennymo

2

1) Вам нужно использовать библиотеку поддержки 23.2.0 (или) выше 2), а высота recyclerView будет wrap_content. 3) recyclerView.setNestedScrollingEnabled (false)

Но при этом шаблон recycler не работает. (т. е. все представления будут загружены сразу, потому что wrap_content требуется высота полного recyclerView, чтобы он сразу рисовал все виды ресайклеров. Никакое представление не будет переработано). Старайтесь не использовать этот шаблон, если это действительно не требуется.

1
recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() { 
       @Override 
       public void onScrolled (RecyclerView recyclerView,int dx, int dy) { 
       int topRowVerticalPosition = (recyclerView == null || recyclerView.getChildCount() == 0) ? 0 : recyclerView.getChildAt(0).getTop(); 
       if (topRowVerticalPosition >= 0) { 
        //top position 
       } 
      } 
       @Override 
       public void onScrollStateChanged (RecyclerView recyclerView,int newState) { 
       super.onScrollStateChanged(recyclerView, newState); 
      } 
      }); 

С помощью этого кода вы можете найти пользователя в верхнем положении. В положении вы можете заставить пейджер представления перейти в нужное положение.

+0

Обнаружение не работает, если пользователь уже находится в верхнем положении в представлении ресайклера и пытается прокрутить вверх еще выше, чтобы вызвать просмотрщик. –

+0

@AlexanderHoffmann :: Попробуйте объявить ** int topRowVerticalPosition = 0; ** как общедоступный. – Jeevanandhan

+0

Я не могу установить переменную в public внутри метода onScroll. Это все равно будет иметь смысл, не так ли? –

1

Если у вас есть доступ VerticalViewPager от RecyclerView, вы можете расширить RecyclerView и проверить canScrollVertically(-1) вперед и сенсорного событие ViewPager

0

У меня была та же проблема. Ответ от Mr.India был полезен, но, как вы прокомментировали, он работал только иногда.

Что я сделал

recyclerView.setOnTouchListener(new View.OnTouchListener() { 
      public float speed; 
      public VelocityTracker mVelocityTracker; 

      @Override 
      public boolean onTouch(View v, MotionEvent event) { 
       int index = event.getActionIndex(); 
       int action = event.getActionMasked(); 
       int pointerId = event.getPointerId(index); 

       switch (action) { 

        case MotionEvent.ACTION_DOWN: 
         if(mVelocityTracker == null) { 
          mVelocityTracker = VelocityTracker.obtain(); 
         } 
         else { 
          mVelocityTracker.clear(); 
         } 
         mVelocityTracker.addMovement(event); 
         break; 
        case MotionEvent.ACTION_MOVE: 
         if(mVelocityTracker != null) { 
          mVelocityTracker.addMovement(event); 
          mVelocityTracker.computeCurrentVelocity(1000); 
          speed = VelocityTrackerCompat.getYVelocity(mVelocityTracker, pointerId); 
         } 
         break; 
        case MotionEvent.ACTION_UP: 
         int topRowVerticalPosition = (recyclerView == null || recyclerView.getChildCount() == 0) ? 0 : recyclerView.getChildAt(0).getTop(); 
         if(speed > 500 && topRowVerticalPosition >= 0) { 
          ReaderFragmentParent parent = (ReaderFragmentParent) getActivity(); 
          ReaderPager pager = parent.getPager(); 
          if(pager != null) { 
           pager.setCurrentItem(pager.getCurrentItem()-1); 
          } 

         } 
         return false; 
        case MotionEvent.ACTION_CANCEL: 
         mVelocityTracker.recycle(); 
         break; 
       } 


       return false; 
      } 
     }); 

На ACTION_UP я проверить, если скорость> 500, это означает, что происходит на рассматриваемой скорости и topRowVerticalPosition означает, что он находится на вершине recyclerview. Затем я получаю ViewPager и setCurrentItem для предыдущего элемента.

это немного грязный хак, но это был единственный способ, которым я нашел, чтобы выглядеть хорошей прокрутке между страницами на вертикальной ViewPager

0
mRecyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() { 
      @Override 
      public void onScrolled (RecyclerView recyclerView,int dx, int dy) { 

      } 
      @Override 
      public void onScrollStateChanged (RecyclerView recyclerView,int newState) { 
       super.onScrollStateChanged(recyclerView, newState); 

       if (!mRecyclerView.canScrollVertically(-1) && newState == 0) { 

        Log.e("canScrollVertically", mRecyclerView.canScrollVertically(-1)+""); 

        verticalViewPager.setCurrentItem(0, true); 
       } 
      } 
     });