Wielowątkowe rysowanie w OpenGL

0

Problem polega mianowicie na tym, że mam spory kod, który wyświetla w oknie mnóstwo elementów takie jak kilka warstw mapy, okna (ekwipunek itp.), postaci, itd. - wszystko umieszczone jest w jednym wątku, więc boję się o spadki FPSów, w szczególności na starszych komputerach.

Sporo czytałem o wielowątkowości w OpenGLu i jedynym sposobem, który na chwilę obecną zadziałał, chociaż w minimalnym stopniu - mianowicie - nie zwraca błędu - jest SharedDrawable
Nie jestem pewien co źle robię, bo mimo iż błędu nie zwraca (co było okropne w wypadku GLContext, gdyż nonstop występowały błędy), to nie rysuje nic z drugiego wątku...
Wątek główny:

SharedDrawable drawable = new SharedDrawable(Display.getDrawable());
new WatekDrugi();

Wątek drugi:

Thread watek;
public WatekDrugi(){
    watek = new Thread(this);
    watek.start();

public void run(){
    try{ WatekPierwszy.drawable.makeCurrent(); }catch(Exception e) e.printStackTrace(); }
    while( watek.isAlive() ){
        // Tutaj rysuję kwadrat za pomocą glBegin(GL_QUADS), glVertex2f() oraz glEnd();
        try{ watek.sleep(100); }catch(Exception e){ e.printStackTrace(); }
    } 
}

Jak temu zaradzić, aby rysowało "kwadrat" z drugiego wątku?

0

Obliczenia na procesorze jeśli masz jakieś możesz zrobić na wielu wątkach, ale rysowanie to nie wiem czy ma sens.
Daj karcie graficznej rysować to w spokoju.

0

Jeśli chcesz zachować swój obecny kod (stare wersje OpenGL), a jednocześnie znacznie zwiększyć wydajność, to spróbuj skorzystać z display list. Ich tworzenie i używanie jest bardzo proste, drobny przykład jak utworzyć i wykorzystać je (JOGL):

private int list;
    
    private void prepareDraw(GL2 g) {
        list = g.glGenLists(1); //tworzymy 1 nową listę - w przypadku Javy nie ma większego sensu robić inaczej. Należy ją gdzieś zapisać
        g.glNewList(list, GL2.GL_COMPILE);
            //kod renderowania, w środku może być wszystko poza funkcjami zwracającymi wartości
        g.glEndList();
    }
    
    public void draw(GL2 g) {
        if (list==0) {
            prepareDraw(g);
        }
        //jakikolwiek dodatkowy kod, który może zmieniać się z klatki na klatkę
        g.glCallList(list);
    }
    
    public void destroy(GL2 g) {
        g.glDeleteLists(list, 1); //usuwanie listy jeśli nie ma być już używana - to ważne, bo OpenGL NIE usunie jej sam z siebie
        list = 0;
    }

Display listy można porównać do funkcji - można je w sumie nazwać takimi "funkcjami dla karty graficznej" - po ich wywołaniu karta graficzna wykona dokładnie to, co znajdowało się pomiędzy glNewList a glEndList. Co ważne, listy można nadpisać, ale jest to niezbyt wydajne jeśli trzeba robić to często, więc transformacje warto wsadzić poza listę. Nie należy tylko zapomnieć o usuwaniu list jako, że w OpenGL pamięcią trzeba zarządzać manualnie (da się to zautomatyzować, ale to już nie dotyczy tematu tego wątku - jeśli jesteś zainteresowany, poszukaj informacji o java.lang.ref.Reference).

Karta graficzna w porównaniu z procesorem to demon prędkości - w przypadku gier 2d oraz części 3d wydajność będzie wysoka nawet przed wprowadzeniem jakichkolwiek optymalizacji. :)

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