Animacje

0

Witam!

  1. Jakie są sposoby wyświetlania animacji? Chodzi mi np. o coś w rodzaju pływającego udekorowanego tekstu, niekoniecznie przez podmienianie plików obrazków korzystając z wątków.
  2. Jak wczytywać do aplikacji pliki gif, aby animacja wyświetlana była cały czas, a nie tylko jedna klatka?
0

Jeżeli tekst ma się nie zmieniać, to renderujesz go całego do jakiegoś bardzo długiego obrazka (najlepiej w formacie kompatybilnym z trybem ekranu) mieszczącego go całego (nazwijmy to "taśmą"). Następnie co określony okres czasu wyrzucasz repaint, a w paint rysujesz na ekranie za pomocą drawImage pobierając odpowiedni fragment taśmy do wyplucia w odpowiednim obszarze. Zmieniając zakres kopiowanego fragmentu uzyskasz efekt przesuwania się napisu w wybranym miejscu panela/ekranu.
Można to zoptymalizować jeżeli, jest aktywne przyspieszenie sprzętowe (dla trybu obrazka zgodnego z trybem ekranu), kopiując (przenosząc) na buforze ekranu/panela ten fragment, który tylko się przesunie i doklejając z prawej lub lewej (zależnie od kierunku przesuwania) brakujący fragment z "taśmy". To chyba najszybsza (najbardziej płynna) metoda generowania przesuwającego się napisu. W przypadku przesuwania o jeden piksel z taśmy będzie kopiowane tylko bitów kolejnych linii ile pikseli ma wysokość "taśmy"

Jeżeli sam napis na taśmie się zmienia, to taśma musi stać się buforem, który też będzie się przesuwał, gdy kolejne fragmenty napisu będą renderowane (trzeba będzie uwzględnić jej przesunięcie w kolejnych zrzutach na ekran/panel). Buforowanie ma tę zaletę, że można w różnych momentach i różnymi procedurami doklejać, modyfikować zawartość taśmy, więc na takim napisie może sobie latać motylek, mogą pojawiać się kleksy i co tylko przyjdzie do głowy. Grunt, żeby przy przerzucaniu na ekran obszar do skopiowania miał już postać finalną.
Można też spróbować renderować taki zmieniający się tekst bezpośrednio na buforze ekranu/panela, ale wtedy może być problem z płynną animacją ponieważ nie będzie można łatwo zrobić przełączania stron, a także trzeba będzie anulować przesuwanie i renderowanie fragmentu obrazu jeżeli zabraknie czasu procesora ponieważ trzeba pamiętać, że paint może być bez żadnej kontroli łączone/olewane przez Swinga z kilku kolejnych zleceń repaint.

To pewnie nie jest zbyt jasne, ale prościej chyba się nie da. Trzeba poczytać dokumentację metod graficznych AWT/Swinga aby załapać o co chodzi.

A co odtwarzania gif-a, to musisz sobie taki playerek sam napisać, albo zaciągnąć gdzieś z sieci gotową klasę, która to robi (tzn. wyrzuca kolejne klatki do jakiegoś bufora).

0

Dzięki serdeczne za uwagę.
Mam jeszcze jedno pytanie:
czy mógłby mi ktoś wytłumaczyć pokrótce tzw podwójne buforowanie, ew. podać link do jakiegoś przystępnego tutorialu?

PS. to tak żeby nie zakładać nowego tematu, zapytam:
W pochodnej klasy JFrame mam dwie funkcje: runMenu() i runApp() . Pierwsza jest odpalana w konstruktorze, tworzy JPanel a na nim rysuje menu, dodaje obsługę strzałek itp.
Druga natomiast powinna być odpalana po wybraniu pierwszej opcji z menu. Jak zatem zgrabnie opuścić runMenu() i wywołać runApp() ? Dodam że to żądane "przejście" dzieje się to po wciśnięciu klawisza ENTER, czyli w zasadzie to w metodzie addKeyListener(...);

0

Idea jest bardzo prosta. http://pl.wikipedia.org/wiki/Podw%C3%B3jne_buforowanie
W przypadku obiektów Swinga nie trzeba nic robić ponieważ tam takie buforowanie jest już obecne i jest przezroczyste dla programisty (paintComponent dostaje kontekst graficzny do właściwego bufora).
Co do tutoriala, to aż się prosi o google. ;)

Co do drugiego pytania, to nie za bardzo go rozumiem. runMenu zakończy się jak skonstruuje wszystko co miał zrobić, wtedy wróci do kodu kontruktora, który też się zakończy. Okno po utworzeniu zacznie być zarządzane przez kolejkę zdarzeń Swinga. Jeżeli w runMenu zostaną zarejestrowane jakieś listenery, to odpowiednie procedury obsługi zostaną wywołane gdy nadejdą obsługiwane przez nie zdarzenia. Co do runApp, to powinna być ona procedurą obsługi zdarzenia dla wybrania z menu pierwszej pozycji (zaimplementowaną metodą interfejsu). Aby ją zarejestrować należy użyć w np. runMenu jakiegoś listenera, który utworzy obiekt np. klasy anonimowej, implementującego konkretny interfejs listenera (najczęściej jest to tylko jedna metoda do zaimplementowania).

ps. Metoda addKeyListener służy do dodania procedury obsługi wciśnięcia klawisza. Po wciśnięciu Enter wywoływana jest metoda obiektu, który podano jako argument w addKeyListener, a nie "w metodzie addKeyListener".

Listenery tworzy się najczęściej jako anonimowe klasy wewnętrzne w klasie reprezentującej element GUI, który generuje konkretne zdarzenia. Dzięki temu zarówno konstrukcja jak i obsługa działania konkretnego obiektu są w tym samym miejscu.

Pytania i nazwy metod sugerują, że nie załapałeś jeszcze, że to nie ty wywołujesz kod GUI, ale kod GUI (obiektów Swinga) wywołuje Twój kod. Twoim zadaniem jest jedynie podawanie mu obiektów, którymi będzie zarządzał (przez metody takie jak createGUI wywołujące metody add oraz setVisible) oraz obiektów, których metody będą reagowały na zdarzenia z tych obiektów (przez dodawanie/usuwanie listenerów).

1 użytkowników online, w tym zalogowanych: 0, gości: 1