W mojej funkcji:
public void getPointMarkerFromUrl(final String url, final OnBitmapDescriptorRetrievedListener listener) {
final int maxSize = context.getResources().getDimensionPixelSize(R.dimen.icon_max_size);
Target t = new Target() {
@Override
public void onBitmapLoaded(Bitmap bitmap, Picasso.LoadedFrom from) {
if (bitmap != null)
listener.bitmapRetrieved(getBitmapDescriptorInCache(url, bitmap));
else
loadDefaultMarker(listener);
}
@Override
public void onBitmapFailed(Drawable errorDrawable) {
loadDefaultMarker(listener);
}
@Override
public void onPrepareLoad(Drawable placeHolderDrawable) {
}
};
Picasso.with(context)
.load(url)
.resize(maxSize, maxSize)
.into(t);
}
Metoda onBitmapLoaded () nigdy nie jest wywoływana przy pierwszym ładowaniu zdjęć. Przeczytałem jakiś temat, taki jak https://github.com/square/picasso/issues/39, który zaleca użycie metody pobierania (Target t) (wydaje się, że jest to problem ze słabym odniesieniem ...), ale ta funkcja nie jest dostępny w ostatnim wydaniu Picassa (2.3.2). Mam tylko metodę fetch (), ale nie mogę używać metody into (mytarget) w tym samym czasie
Czy możesz mi wyjaśnić, jak używać funkcji fetch () z niestandardowym celem? Dziękuję Ci.
Doc: http://square.github.io/picasso/javadoc/com/squareup/picasso/RequestCreator.html#fetch--
Odpowiedzi:
Jak zauważyli inni respondenci (@lukas i @mradzinski), Picasso zachowuje jedynie słabe odniesienie do
Target
obiektu. Chociaż możesz przechowywać silne odniesienieTarget
w jednej ze swoich klas, nadal może to być problematyczne, jeśliTarget
odniesienia aView
w jakikolwiek sposób, ponieważ skutecznie zachowasz również silne odniesienie do tegoView
(co jest jedną z rzeczy, które Picasso wyraźnie pomaga uniknąć).Jeśli jesteś w takiej sytuacji, polecam otagowanie
Target
jakoView
:Takie podejście ma tę zaletę, że Picasso zajmie się wszystkim za Ciebie. Będzie zarządzać
WeakReference
obiektami dla każdego z twoich widoków - gdy tylko jeden nie będzie już potrzebny, wszelkieTarget
przetwarzanie obrazu również zostanie zwolnione, więc nie utkniesz z wyciekami pamięci z powodu długowiecznych celów, ale Twój Cel przetrwa dopóki jego widok jest żywy.źródło
Picasso nie ma silnego odniesienia do obiektu docelowego, dlatego jest on zbierany jako śmieci i
onBitmapLoaded
nie jest wywoływany.Rozwiązanie jest dość proste, wystarczy odnieść się do pliku
Target
.źródło
View
narzędzieTarget
.Object.equals(Object)
iObject.hashCode()
metody. czy masz działającą próbkę?Gdybym miał ImageView, zrobiłbym tak: imageView.setTag (target);
Używam kolejnego rozwiązania do ładowania map bitowych do powiadomień, więc potrzebuję tylko bitmapy.
Stwórz więc zestaw, który będzie przechowywać obiekty docelowe i usuwać je po zakończeniu ładowania.
źródło
źródło
Oto rozwiązanie dla tych, którzy nie używają widoku. Ta metoda pomocnicza używa listy do tymczasowego przechowywania obiektu docelowego, dopóki wynik nie zostanie zwrócony, aby nie był gc'd:
źródło
Jak powiedział @lukas (i cytując), Picasso nie ma silnego odniesienia do obiektu docelowego. Aby uniknąć wyrzucania elementów bezużytecznych, musisz mieć silne odwołanie do obiektu.
Informacje o metodzie fetch (). W dokumentacji jest całkiem jasne, że funkcja fetch () nie może być używana z ImageView ani Targetem, służy ona tylko do "rozgrzania" pamięci podręcznej i nic więcej, więc nie będziesz mógł jej używać w taki sposób chcieć.
Zalecam trzymanie silnego odniesienia, takiego jak wyjaśnił @lukas, powinno działać. Jeśli nie, otwórz nowy numer na stronie GitHub projektu.
źródło
Napotkałem podobny problem i trzymanie odniesienia do celu w ogóle nie pomogło, więc użyłem następującego kodu, który zwraca Bitmapę:
z drugiej strony -> nie ma wywołania zwrotnego i nie możesz wywołać tej funkcji w głównym wątku, musisz uruchomić tę funkcję w wątku w tle, jak w poniższym przykładzie:
Kolejną rzeczą, która działa o wiele lepiej, jest użycie Glide!
Musiałem użyć obu z nich, ponieważ celem mojego projektu było użycie 2 różnych interfejsów API do pobierania obrazów, aby wyświetlić galerię obrazów i dać użytkownikowi możliwość wyboru interfejsu API.
Muszę powiedzieć, że byłem zdumiony wynikami, api Glide'a działało bez zarzutu pod każdym względem (cel Glide'a nie ma słabych odniesień) wile Picasso dał mi piekło (to był mój pierwszy raz z Glide, zwykle używałem Picassa do tej pory, wygląda na to, że dzisiaj to się zmieni ^^).
źródło
Miałem ten sam problem, ale kiedy zmienię zależność, jak wspomniano poniżej, teraz działa poprawnie.
źródło