2010-07-02 11 views
7

Mam obrazy 2 png, używane jako tekstury w aplikacji OpenGL Qt/C++ 2D. Pierwszy jest używany jako rodzaj "środkowego" gruntu, a drugi jest używany jako "obiekt" renderowany "ontop" (uwaga: wszystkie mają tę samą wartość atm, otrzymuję pożądane zachowanie, renderując je w zdefiniowana kolejność). Tekstura "obiektu" jest częściowo przeświecająca. Tekstura "middleground" jest w większości solidna. Problem polega na tym, że półprzezroczysta część mojej tekstury "obiektu" ma kolor tła, a nie teksturę "middleground".Przezroczysta tekstura OpenGL nad inną teksturą

Jakieś wskazówki, jak to osiągnąć?

Obserwuje OpenGL falgs służą do moich faktur świadczących

glEnable (GL_TEXTURE_2D); 
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); 
glEnable (GL_BLEND); 
glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); 

Dzięki za pomoc.

Edit:

więcej Kod:

glColor4f(1.0f, 1.0f, 1.0f, 1.0f); 

glEnable(GL_DEPTH_TEST); 
glDepthMask(GL_TRUE); 

glEnable(GL_ALPHA_TEST); 
glAlphaFunc(GL_GREATER, 0.1f); 

glEnable(GL_TEXTURE_2D); 
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); 
glBindTexture(GL_TEXTURE_2D, c->_texture); 

glEnable(GL_BLEND); 
glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA); 

glBegin(GL_QUADS); 
{ 
    glTexCoord2i(0,0); 
    glVertex2i(-128,-128); 

    glTexCoord2i(0,1); 
    glVertex2i(-128,128); 

    glTexCoord2i(1,1); 
    glVertex2i(128,128); 

    glTexCoord2i(1,0); 
    glVertex2i(128,-128); 

} 
glEnd(); 

glDisable(GL_TEXTURE_2D); 

glDisable(GL_ALPHA_TEST); 
glDisable(GL_DEPTH_TEST); 

Edit: Jak mogę przenieść moją teksturę i ile mogę powiedzieć, że ładuje go z kanałem alfa

QImage img("./images/dummycar.png","PNG"); 
QImage t(QGLWidget::convertToGLFormat(img)); 
glGenTextures(1, &_texture); 
glBindTexture(GL_TEXTURE_2D, _texture); 
glTexImage2D(GL_TEXTURE_2D, 0, 3, t.width(), t.height(), 0, GL_RGBA, GL_UNSIGNED_BYTE, t.bits()); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); 

Screenshot : http://img824.imageshack.us/img824/1912/blackbox.png

Skyimage to "środkowe pole", tło jest solidnie czarne.

+0

Zrzuty ekranu z objaśnieniami byłyby miłe. – SigTerm

Odpowiedz

7
glTexImage2D(GL_TEXTURE_2D, 0, 3, t.width(), t.height(), 0, GL_RGBA, GL_UNSIGNED_BYTE, t.bits()); 

Ty określając 3 kanały dla internalFormat, więc to RGB, a nie RGBA. Zamiast tego spróbuj użyć GL_RGBA w tej pozycji.

+1

Wiedziałem, że to było coś głupiego. Wielkie dzięki, które uratowały mój dzień :) – drahnr

4

Czy próbowałeś manipulować przy pomocy glAlphaFunc? Możesz go użyć do odrzucenia rysowania półprzezroczystych części tekstury obiektu na podstawie wartości alfa.

co bądź

glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_BLEND)

lub

glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE)?

Mam nadzieję, że to pomaga.

+0

To nie zadziałało. Próbowałem glEnable (GL_ALPHA_TEST); glAlphaFunc (GL_GREATER, 0.1f); ale bez zmian. GL_MODULATE nic nie zmieniło, GL_BLEND zmienił kolor, ale "pudełko" wokół mojego obiektu wciąż tam było – drahnr

+1

To było naprawdę pomocne dla mnie. Używając BB, gdy włączyłem test alfa i użyłem GL_GREATER, zadziałało to jak czar. – bobobobo

3

Jeśli renderujesz jedną teksturę na obiekt, musisz użyć glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE).

Jeśli tekstura nadal zawiera "pole", nawet po tym, to została załadowana bez kanału alfa.

To doskonale działa na mnie:

glEnable(GL_BLEND); 
    glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); 
    glBindTexture(GL_TEXTURE_2D, texture2->tex); 
    glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); 
    glColor4f(0.5f, 1.0f, 0.5f, 0.5f); 
    glBegin(GL_TRIANGLE_FAN); 
    glTexCoord2f(0, 0); 
    glVertex2f(x, y); 
    glTexCoord2f(1, 0); 
    glVertex2f(x + texture2->width, y); 
    glTexCoord2f(1, 1); 
    glVertex2f(x + texture2->width, y+ texture2->height); 
    glTexCoord2f(0, 1); 
    glVertex2f(x, y + texture2->height); 
    glEnd(); 
    glDisable(GL_BLEND); 

Półprzezroczyste tekstury, barwione przez ostatniego koloru.

Jeśli "mając pole wokół tekstury" nie opisuje twojego problemu, musisz opublikować zrzuty ekranu.

--EDIT--

Zaktualizowane dane na podstawie your screenshot.

Najpierw trzeba wyrenderować tło, a następnie wyrenderować samochód. Widzisz kolor tła, ponieważ nawet jeśli powierzchnia jest przezroczysta, wypełnia wartościami z bufora Z, a ponieważ tło jest poniżej samochodu, staje się niewidoczne.

Podczas renderowania obiektów półprzezroczystych należy przestrzegać tych zasad.

  1. Wszystkie nieprzejrzyste obiekty należy renderować przed półprzezroczystymi obiektami. Zawsze.

  2. Wszystkie przezroczyste obiekty powinny być renderowane z powrotem do przedniego obiektu. Najpierw powinny być renderowane najdalsze obiekty, najbliższe obiekty powinny być renderowane jako drugie.

  3. Jeśli renderowanie w kolejności odwrotnej nie jest możliwe (nieposortowane cząstki z mieszaniem GL_ADD), zapis w buforze głębi powinien być wyłączony za pomocą glDepthMask (GL_FALSE). Jeśli tego nie zrobisz, dostaniesz brzydkie artefakty. (jak ten na zrzucie ekranu).

+0

Czy to pokazuje teksturę leżącą u podstaw? Jak na razie działa to również dla mnie, ale moim problemem jest to, że chcę zobaczyć inny obiekt tekstury _beyond_ ten, który rysuję. Ale w bankomacie dostaję kolor tła (czarny). Zrzut ekranu: http://img824.imageshack.us/img824/1912/blackbox.png – drahnr

+0

@ soxs060389: Zaktualizowałem swoją odpowiedź. Powinieneś PIERWSZY wylądować, a PO TYM renderować samochód. Nie zadziała, jeśli zrobisz to w odwrotnej kolejności. – SigTerm

+0

Robiłem to od godziny zer0. Samochód jest i zawsze był ostatnim przedmiotem do wykonania. – drahnr

Powiązane problemy