Mam ViewPager, a pod nim mam 10 przycisków. Kliknięcie przycisku, na przykład # 4, powoduje natychmiastowe przejście do strony nr 4 przez mPager.setCurrentItem(3);
. Chcę jednak wyłączyć stronicowanie, przesuwając palcem poziomo. Tak więc stronicowanie odbywa się WYŁĄCZNIE poprzez kliknięcie przycisków. Jak mogę wyłączyć przesuwanie palcem?
android
android-viewpager
teista
źródło
źródło
Odpowiedzi:
Musisz podklasę
ViewPager
.onTouchEvent
zawiera wiele dobrych rzeczy, których nie chcesz zmieniać, na przykład pozwalając, aby widoki dziecka były poprawiane.onInterceptTouchEvent
jest tym, co chcesz zmienić. Jeśli spojrzysz na kodViewPager
, zobaczysz komentarz:Oto kompletne rozwiązanie:
Najpierw dodaj tę klasę do swojego
src
folderu:Następnie upewnij się, że używasz tej klasy zamiast zwykłej
ViewPager
, którą prawdopodobnie określiłeś jakoandroid.support.v4.view.ViewPager
. W pliku układu będziesz chciał określić go za pomocą czegoś takiego:Ten konkretny przykład znajduje się w punkcie a
LinearLayout
i ma zajmować cały ekran, dlategolayout_weight
jest to 1, alayout_height
0dp.I
setMyScroller();
sposób jest płynne przejścieźródło
0dp
wzrost /1
waga zamiastmatch_parent
wzrostu, aby uzyskać efekt pełnoekranowy? Czy zyskujesz dzięki temu poprawę wydajności?executeKeyEvent()
. Jest to metoda, która następnie wywołujeallowScroll()
.// Never allow swiping by keyboard LEFT, RIGHT, TAB and SHIFT+TAB keys
@Override public boolean executeKeyEvent(KeyEvent event) { return false; }
Bardziej ogólnym rozszerzeniem
ViewPager
byłoby stworzenieSetPagingEnabled
metody umożliwiającej włączanie i wyłączanie stronicowania w locie. Aby włączyć / wyłączyć przesuwanie, po prostu pomiń dwie metody:onTouchEvent
ionInterceptTouchEvent
. Oba zwrócą „fałsz”, jeśli stronicowanie zostało wyłączone.Następnie wybierz to zamiast wbudowanego podglądu w XML
Wystarczy wywołać
setPagingEnabled
metodę,false
a użytkownicy nie będą mogli przesunąć palcem do strony.źródło
onTouchEvent
ionInterceptTouchEvent
metody za pomocąreturn enabled && super.onTouchEvent(event);
Najprostszym sposobem jest
setOnTouchListener
i powrotutrue
doViewPager
.źródło
pager.setCurrentItem(pager.getCurrentItem());
przed powrotemtrue
.public int getItemPosition(Object object) { return POSITION_NONE; }
w moim adapterze, co wymusza odtwarzanie stron i może również rozwiązywanie innych problemów.Lepiej zadeklarować stylowość, aby można było zmienić jego właściwość z xml:
A w twoich wartościach / attr.xml:
abyś mógł go używać w swoim układzie xml:
Oczywiście nadal możesz mieć właściwość get / set.
źródło
Przesłanianie tylko
onTouchEvent
ionInterceptTouchEvent
nie jest wystarczające, jeśli masz ViewPager w innym ViewPager. Dziecko ViewPager kradnie zdarzenia dotyku przewijania w poziomie od nadrzędnego ViewPager, chyba że zostanie umieszczony na pierwszej / ostatniej stronie.Aby ta konfiguracja działała poprawnie, musisz zastąpić również
canScrollHorizontally
metodę.Zobacz
LockableViewPager
implementację poniżej.źródło
Teraz nie musimy tworzyć niestandardowych
ViewPager
Nowa
ViewPager2
nazwa Zobacz dostępna w AndroidzieViewPager2
obsługuje tradycyjne stronicowanie oprócz tradycyjnego poziomego stronicowania. Możesz włączyć stronicowanie pionowe dlaViewPager2
elementu, ustawiając jegoandroid:orientation
atrybutAby wyłączyć przeciąganie w
viewpager2
użyciuAby włączyć przesuwanie w
viewpager2
użyciuAby uzyskać więcej informacji, sprawdź to
AKTUALIZACJA
Sprawdź: migruj z ViewPager do ViewPager2
Aby uzyskać pełny przykład, sprawdź to korzystanie z ViewPager2 w systemie Android
źródło
viewpager2
zRecyclerView.Adapter
Jeśli korzystasz z ViewPager, musisz również zastąpić,
executeKeyEvent
jak wskazano wcześniej przez @araksPonieważ niektóre urządzenia, takie jak Galaxy Tab 4 10 ', pokazują te przyciski, w których większość urządzeń nigdy ich nie pokazuje:
źródło
Aby wyłączyć przeciąganie
Aby włączyć przesuwanie
źródło
Musiałem wyłączyć przesuwanie po jednej określonej stronie i nadać mu ładną animację z gumką, oto jak:
źródło
onPageSelected
zostanie wykonany. Przełącza się nawet następna strona. Więc ten kod nie jest potrzebny.Wiem, że jest bardzo późno, aby to opublikować, ale oto mały hack, aby osiągnąć swój wynik;)
Po prostu dodaj fikcyjny widok poniżej przeglądarki:
Następnie dodaj a
OnClickListener
do swojegoRelativeLayout
.Zachowaj kreatywność dzięki układom, ich rozmieszczeniu i zachowaniu, a nauczysz się znaleźć sposób na zrobienie absolutnie wszystkiego, co sobie wyobrażasz :)
Powodzenia!
źródło
setClickable
zamiastsetOnClickListener
, jeśli nie trzeba obsługiwaćonClick
zdarzenia.Napisałem
CustomViewPager
z kontrolką przeciągania:Jeśli ustawisz
canScroll
dotrue
tegoViewPager
można przesuwając palcem,false
a wręcz przeciwnie.Używam tego w moim projekcie i do tej pory działa świetnie.
źródło
Z powodzeniem wykorzystałem tę klasę. Przesłonięcie executeKeyEvent jest wymagane, aby uniknąć przesuwania za pomocą strzałek w niektórych urządzeniach lub w celu ułatwienia dostępu:
A w xml nazwij to tak:
źródło
performClick()
metoda nie jest przesłonięta.W Kotlinie moje rozwiązanie, łączące powyższe odpowiedzi.
źródło
onInterceptTouchEvent()
uniemożliwi otrzymanie danych wejściowych przez widoki potomne. W większości przypadków nie jest to zamierzone zachowanie.W kotlin możemy to rozwiązać, tworząc niestandardowy widget dziedziczący klasę ViewPager i dodając wartość flagi do kontrolowania zachowania podczas przeciągania.
NoSwipePager.kt
W xml
Wyłącz przesuwanie programowo. Jeśli
kotlin-android-extensions
wtyczka zostanie zastosowana w build.gradle , przesuwanie można wyłączyć, pisząc poniżej kodu.W przeciwnym razie możemy wyłączyć przesuwanie za pomocą kodu poniżej:
źródło
onInterceptTouchEvent()
uniemożliwi otrzymanie danych wejściowych przez widoki potomne. W większości przypadków nie jest to zamierzone zachowanie.super.onInterceptTouchEvent(event)
powoduje, że te widoki nie otrzymują żadnych danych wejściowych (co jest udokumentowanym celemonInterceptTouchEvent
metody).onInterceptTouchEvent()
metoda przesłonięcia zapobiega otrzymywaniu danych wejściowych przez (treść).Spróbuj przesłonić i zwrócić wartość true z onInterceptTouchEvent () i / lub onTouchEvent () , które zużyją zdarzenia dotykowe na pagerze.
źródło
true
by sugerować, że zdarzenie dotykowe zostało obsłużone?Kolejne łatwe rozwiązanie, aby wyłączyć przesuwanie na określonej stronie (w tym przykładzie strona 2):
źródło
źródło
Jeśli napiszesz galerię zdjęć za pomocą
ImageView
siViewPager
, która obsługuje powiększanie i przesuwanie, zapoznaj się z prostym rozwiązaniem opisanym tutaj: Implementowanie powiększalnego ImageView poprzez rozszerzenie domyślnego ViewPager w Phimpme Android (i próbka Github - PhotoView ). To rozwiązanie nie działaViewPager
samodzielnie.źródło
Jeśli chcesz zaimplementować to samo dla Androida w Xamarin, oto tłumaczenie na C #
Zdecydowałem się nazwać atrybut „ ScrollEnabled ”. Ponieważ iOS używa właśnie tego samego nazewnictwa. Tak więc masz taką samą nazwę na obu platformach, co ułatwia programistom.
W pliku .axml:
źródło
Żaden z powyższych kodów nie działa płynnie. Próbowałem tego
źródło
oto moja implementacja,
że jeśli chcesz wyłączyć animację przesuwania, możesz użyć swipeListener w lewo i prawo i nadal chcesz przewijać palcem, ale bez animacji
Viewpager
Metoda 1-ZastąponInterceptTouchEvent
ionTouchEvent
2- stwórz swój własny
GestureDetector
3- wykryj gest machnięcia i użyj
setCurrentItem(item, false)
ViewPager
podczas konfigurowania ViewPager ustaw swipeListener
źródło
Właśnie dostosowałem trochę przeglądarkę i łatwo wyłączam przesuwanie.
źródło
Jeśli używasz ViewPager2, musisz po prostu użyć:
viewpager.setUserInputEnabled(false);
Z dokumentów :
Dzięki: https://stackoverflow.com/a/61685871/9026710
źródło
źródło