2009-07-25 18 views
43

Kiedy i jak jest używana layoutIfNeeded? Wiem, że zmieniając układ widoku, możemy zadzwonić pod numer setNeedsLayout, aby zaktualizować układ, ale nie jest pewny, kiedy należy użyć layoutIfNeeded.W jaki sposób używa się layoutIfNeeded?

UWAGA: Mam layoutIfNeeded użyte w aktualnym kodzie, ale zapomniałem w jakim kontekście zostało użyte.

Odpowiedz

57

layoutIfNeeded zmusza odbiornik do natychmiastowego układu swoich widoków w razie potrzeby.

Załóżmy, że nadpisałeś layoutSubviews, a UIKit uważa, że ​​Twój widok wymaga układu z dowolnego powodu (np. Zadzwoniłeś pod numer setNeedsLayout podczas obsługi niektórych działań użytkownika). Wtedy twoja niestandardowa metoda layoutSubviews będzie wywoływana natychmiast, zamiast wtedy, gdy normalnie będzie wywoływana w zwykłej sekwencji zdarzeń pętli UIKit (po obsłudze zdarzeń, ale przed drawRect:).

Przykładem dlaczego może trzeba zadzwonić layoutIfNeeded obrębie jednej pętli biegu:

  1. zmienić rozmiar widoku niestandardowego zawierający widok tabeli z niestandardowego układu. setNeedsLayout jest ustawiony tak, że layoutSubviews zostanie wywołany później.
  2. Obiekt kontrolera prosi o widok tabeli, aby przewinąć do określonej komórki podczas obsługi zdarzenia użytkownika.
  3. Twój niestandardowy widok wykonuje niestandardowy rozmiar widoku tabeli w layoutSubviews, który zmienia rozmiar widoku tabeli.

Problem polegał na tym, że kontroler poprosił o widok tabeli, aby przewinąć (krok 2), widok tabeli miał nieaktualne granice. Zaktualizowane granice zostaną ustawione później w widoku tabeli (krok 3). To, czego kontroler chciał, aby widok tabeli mógł przewinąć, może nie być widoczny po wykonaniu layoutSubviews. Rozwiązaniem byłoby wówczas, gdyby kontroler zadzwonił pod numer layoutIfNeeded w sytuacjach, gdy wie, że może to nastąpić.

-9

setNeedsLayout faktycznie wywołuje layoutIfNeeded, więc jeśli twój zestaw wywoławczyNeedsDisplay nie ma powodu, aby wywołać layoutIfNeeded. W ten sposób setNeedsLayout jest wygodną metodą wywoływania layoutIfNeeded, która wykonuje podnoszenie ciężkie.

+14

To nie jest prawda. setNeedsLayout będzie oznaczać widok dla układu, co spowoduje wywołanie layoutSubviews w innym cyklu runloop. Wywołanie layoutIfNeeded spowoduje wywołanie layoutSubviews w tym samym cyklu runloop. Aby przetestować, ustaw punkt przerwania w layoutSubviews, a następnie punkt przerwania w wywołaniu setNeedsLayout. Jeśli przejdziesz do jednej linii, zauważysz, że nie włamujesz się do layoutSubviews. Jednakże, jeśli złamiesz layoutIfNeeded i prześlesz linię, zauważysz, że ZROBISZ rozkładekSubviews przed awansem. – tyler

+1

dang, co za poważny głos –

Powiązane problemy