Jak mogę zmienić pozycję widoku za pomocą kodu? Jak zmiana jego pozycji X, Y. Czy to możliwe?
102
W przypadku wszystkiego poniżej Honeycomb (poziom API 11) będziesz musiał użyć setLayoutParams(...)
.
Jeśli można ograniczyć wsparcie Honeycomb i nawet można użyć setX(...)
, setY(...)
, setLeft(...)
, setTop(...)
, itd.
sets the top position of this view relative to its parent. This method is meant to be called by the layout system and should not generally be called otherwise, because the property may be changed at any time by the layout.
- więc może to nie taki dobry pomysł;)Tak, możesz dynamicznie ustawiać pozycję widoku w systemie Android. Podobnie masz
ImageView
inLinearLayout
w pliku xml, więc możesz ustawić jego pozycję za pomocąLayoutParams
.Ale upewnij się, że robisz toLayoutParams
zgodnie z układem wykonanym w pliku xml. Są różne wLayoutParams
zależności od przyjętego układu.Oto kod do ustawienia:
Mam nadzieję, że ustawienie pozycji będzie pomocne.
źródło
Istnieją już różne prawidłowe odpowiedzi, ale żadna z nich nie wydaje się właściwie sugerować, której metody należy użyć w danym przypadku, z wyjątkiem odpowiednich ograniczeń na poziomie interfejsu API:
Jeśli możesz poczekać na cykl układu, a nadrzędna grupa widoków obsługuje
MarginLayoutParams
(lub podklasę), ustawmarginLeft
/marginTop
odpowiednio.Jeśli potrzebujesz natychmiast i trwale zmienić pozycję (np. Dla kotwicy PopupMenu), dodatkowo wywołaj
layout(l, t, r, b)
z tymi samymi współrzędnymi. To wyklucza to, co system układu potwierdzi później.W przypadku natychmiastowych (tymczasowych) zmian (takich jak animacje) użyj zamiast tego
setX()
/setY()
. W przypadkach, gdy rozmiar nadrzędny nie zależy od WRAP_CHILDREN, użyciesetX()
/setY()
wyłączność może być w porządku .Nigdy nie używaj
setLeft()
/setRight()
/setBottom()
/setTop()
, patrz poniżej.tło : pola
mLeft
/mTop
/mBottom
/mRight
są wypełniane z odpowiednich parametrów LayoutParams w układzie (). Układ jest wywoływany niejawnie i asynchronicznie przez system układu widoku systemu Android. Dlatego ustawienieMarginLayoutParams
wydaje się być najbezpieczniejszym i najczystszym sposobem na ustawienie pozycji na stałe. Jednak asynchroniczne opóźnienie układu może stanowić problem w niektórych przypadkach, np. Podczas korzystania z widoku do renderowania kursora, i powinno zostać ponownie umieszczone i służyć jako kotwica PopupMenu w tym samym czasie. W tym przypadku dzwonienielayout()
działało dobrze.Problemy z
setLeft()
isetTop()
to:Samo dzwonienie do nich nie wystarczy - trzeba też zadzwonić
setRight()
isetBottom()
unikać rozciągania lub zawężania widoku.Implementacja tych metod wygląda na stosunkowo złożoną (= wykonanie pewnej pracy w celu uwzględnienia zmian rozmiaru widoku spowodowanych przez każdą z nich)
Wydaje się, że powodują dziwne problemy z polami wejściowymi: miękka klawiatura numeryczna EditText czasami nie zezwala na cyfry
setX()
isetY()
działają poza układem układu, a odpowiednie wartości są traktowane jako dodatkowe odsunięcie do wartości w lewo / w górę / w dół / w prawo określonych przez system układu, odpowiednio przesuwając widok. Wydaje się, że zostały dodane do animacji (gdzie wymagany jest natychmiastowy efekt bez przechodzenia przez cykl układu).źródło
marginLeft
można ustawić za pomocąsetLayoutParams
a,new FrameLayout.LayoutParams(width, height)
na którym ustawionomarginLeft
Istnieje biblioteka o nazwie NineOldAndroids , która umożliwia korzystanie z biblioteki animacji Honeycomb aż do wersji pierwszej.
Oznacza to, że możesz zdefiniować left, right, translationX / Y z nieco innym interfejsem.
Oto jak to działa:
Wystarczy użyć statycznych metod z klasy ViewHelper, przekazać widok i jakąkolwiek wartość, na jaką chcesz go ustawić.
źródło
Polecam używanie
setTranslationX
isetTranslationY
. Sam dopiero zaczynam, ale wydaje mi się, że to najbezpieczniejszy i preferowany sposób przesuwania widoku. Myślę, że zależy to w dużej mierze od tego, co dokładnie próbujesz zrobić, ale to działa dobrze w przypadku animacji 2D.źródło
Jeśli używasz HoneyComb Sdk (poziom interfejsu API 11), możesz spróbować użyć następujących metod.
Parametr x to wizualna pozycja x tego widoku.
Parametr y jest wizualną pozycją y tego widoku.
Mam nadzieję, że okaże się pomocny. :)
źródło
Aby uzyskać obsługę wszystkich poziomów API, możesz go używać w następujący sposób:
źródło
Ustaw lewą pozycję tego widoku względem jego rodzica:
Ustaw właściwą pozycję tego widoku względem jego elementu nadrzędnego:
Ustaw najwyższą pozycję tego widoku względem jego elementu nadrzędnego:
Ustaw dolną pozycję tego widoku względem jego elementu nadrzędnego:
Powyższe metody służą do ustawiania pozycji widoku związanego z jego rodzicem.
źródło
Użyj LayoutParams. Jeśli używasz LinearLayout, musisz zaimportować android.widget.LinearLayout.LayoutParams, w przeciwnym razie zaimportuj odpowiednią wersję LayoutParams dla używanego układu lub spowoduje to wyjątek ClassCast , a następnie:
Uwaga: Zauważ, że możesz użyć również imageView.setLeft (int dim), ALE TO NIE BĘDZIE ustawiało pozycji komponentu, ustawi tylko pozycję lewej krawędzi komponentu, reszta pozostanie w tej samej pozycji .
źródło
Użyj
RelativeLayout
, umieść w nim swój widok, pobierzRelativeLayout.LayoutParams
obiekt ze swojego widoku i ustaw marginesy według potrzeb. Następnie poprośrequestLayout()
o swój punkt widzenia. To jedyny sposób, jaki znam.źródło
Odkryłem, że @Stefan Haustein jest bardzo blisko mojego doświadczenia, ale nie jestem pewien w 100%. Moja sugestia to:
setLeft()
/setRight()
/setBottom()
/setTop()
czasami nie działa.setX()
/setY()
zamiast. (Możesz chcieć wyszukiwać bardziej w różnicysetLeft()
isetX()
)źródło
Jedną rzeczą, o której należy pamiętać przy pozycjonowaniu, jest to, że każdy widok ma indeks względem swojego widoku nadrzędnego. Więc jeśli masz układ liniowy z trzema podglądami podrzędnymi, każdy z podglądów częściowych będzie miał indeks: 0, 1, 2 w powyższym przypadku.
Pozwala to na dodanie widoku do ostatniej pozycji (lub końca) w widoku nadrzędnym, wykonując coś takiego:
Alternatywnie możesz zastąpić widok, używając czegoś podobnego do następującego:
źródło