2012-08-25 11 views
11

Mam problemy z uszkodzeniem tekstury na emulatorze Androida (działa dobrze na większości urządzeń z Androidem).Android korupcja tekstury OpenGL

Android 4.1 reference rendering

Na zdjęciu powyżej jest produkowany przez odniesienie renderowania emulatorze z systemem Android 4.1 Jelly Bean, wszystko wygląda tak jak powinno.

Android 1.6

Drugie zdjęcie jest zrobione w emulatorze z systemem Android 1.6. Uwaga korupcji niektórych niepełnosprawnych przycisków paska narzędzi (są one wykonane z kolorowego 1f, 1f, 1f, 0.5f)

Android 1.6

Trzecie zdjęcie jest zrobione w tym samym emulatorze. Różnica polega na tym, że wynik jest renderowany w prawym górnym rogu. Wynik to czcionka bitmapowa, a tekstura to maska ​​alfa. Wszystko wyrenderowane po wyniku traci swoją fakturę. Zauważ, że poprzedni zrzut ekranu zawierał również czcionkę bitmapową renderowaną w ten sam sposób (ale z użyciem innej tekstury).

Podobny problem był obecny na jednym z urządzeń Samsung (nie pamiętam modelu). Po wyrenderowaniu tekstury podłogowej wszystko wyrenderowane po utraconej teksturze. Problem nie pojawił się, gdy albo: a) nie związałem tekstury, b) związałem teksturę, ale nie narysowałem trójkątów, c) odtworzyłem png od zera.

OpenGL ustawienia:

gl.glDisable(GL10.GL_LIGHTING); 
gl.glDisable(GL10.GL_CULL_FACE); 
gl.glDisable(GL10.GL_DEPTH_TEST); 
gl.glDisable(GL10.GL_DITHER); 
gl.glDepthMask(false); 
gl.glEnable(GL10.GL_TEXTURE_2D); 
gl.glBlendFunc(GL10.GL_ONE,GL10.GL_ONE_MINUS_SRC_ALPHA); 
gl.glShadeModel(GL10.GL_FLAT); 
gl.glTexEnvf(GL10.GL_TEXTURE_ENV, GL10.GL_TEXTURE_ENV_MODE, GL10.GL_MODULATE); 

Jak tekstury są ładowane:

public void doGLLoading(Engine renderer) { 
     GL10 gl=renderer.getGl(); 
     int[] ids=new int[1]; 
     gl.glGenTextures(1, ids,0); 
     id=ids[0]; 
     gl.glBindTexture(GL10.GL_TEXTURE_2D, id); 
     Log.d("SpriteDraw", String.format("Texture %s has format %s",getPath(),bitmap.getConfig().toString())); 
     buildMipmap(gl, bitmap); 
     gl.glTexParameterf(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MIN_FILTER, minFilter); 
     gl.glTexParameterf(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MAG_FILTER, magFilter); 
     gl.glTexParameterf(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_WRAP_S, textureWrapS); 
     gl.glTexParameterf(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_WRAP_T, textureWrapT); 
    } 
private void buildMipmap(GL10 gl, Bitmap bitmap) { 
    int level = 0; 
    int height = bitmap.getHeight(); 
    int width = bitmap.getWidth(); 

    while (height >= 1 || width >= 1) { 
     // First of all, generate the texture from our bitmap and set it to 
     // the according level 
        //TextureUtils.texImage2D(gl, GL10.GL_TEXTURE_2D, level, -1, bitmap, -1, 0); 
     GLUtils.texImage2D(GL10.GL_TEXTURE_2D, level, bitmap, 0); 
     if (height == 1 || width == 1) { 
      break; 
     } 
     // Increase the mipmap level 
     level++; 
     height /= 2; 
     width /= 2; 
     Bitmap bitmap2 = Bitmap.createScaledBitmap(bitmap, width, height, 
       true); 

     // Clean up 
     bitmap.recycle(); 
     bitmap = bitmap2; 
    } 
} 

Uwagi: czcionka jest renderowane za pomocą gl.glBlendFunc(GL10.GL_SRC_ALPHA, GL10.GL_ONE_MINUS_SRC_ALPHA); i GL10.glDrawArrays. Zepsucie dotyczy nie tylko emulatora 1.6, ale także serii androidów 2.x, choć nie jest tak widoczne (masek alfa nadal są renderowane niepoprawnie). Wszystkie zasoby są poprawnie ładowane jako potęga dwóch bitmap.

+0

Czy tekstury mają wartość Moc dwóch? i czy używasz superPng lub Png? normalne pliki png nie rezerwują alfa poprawnie jako maski. ale superPng może to zarezerwować. Wtyczka do photoshopa jest eksportowana jako superPng – Behnam

+0

Tak, wszystkie są potęgą dwójki (wymienione na końcu postu). Bitmapy są zapisywane w postaci bitmap w skali szarości, ładowane jako ARGB_8888 przez Androida i konwertowane na maskę alfa za pomocą mojego kodu. – rkapl

Odpowiedz

2
  1. Proponuję za pomocą tekstur 32-bitowych, a nie w skali szarości, a nie „alphamasks” (co to jest?)
  2. Sprawdź rozmiar swojej fakturze, nie powinno przekraczać maksymalnego rozmiaru (glGetInteger (GL_MAX_TEXTURE_SIZE). Ponadto należy shure swoje tekstury są potęgą 2. Tak, wspomniałeś wcześniej, ale jeśli są w skalowalnych zasobach (foldery drawable_x_dpi), zostaną przeskalowane przez androida Aby uniknąć skalowania, umieść je w folderze "raw"
  3. Tylko dla test, spróbuj wyłączyć wszystkie filtry, w tym mipmapy - ustaw GL_TEXTURE_WRAP_S i GL_TEXTURE_WRAP_T na GL_NEAREST
+0

Maska alfa to tekstura z tylko kanałem alfa. Powinny działać poprawnie. Wszystkie tekstury są naprawdę załadowane jako potęga dwóch bitmap (są ładowane za pomocą 'InputStream', a nie identyfikatora zasobu, więc nie są skalowane). Jeśli chodzi o filtrowanie, przypuszczam, że miałeś na myśli 'GL_TEXTURE_MIN_FILTER'. Ustawienie go na "GL_NEAREST" nie rozwiązuje problemu. – rkapl

+0

Tak, miałem na myśli GL_TEXTURE_MIN_FILTER. Następną rzeczą, którą można wypróbować, jest zastąpienie plików tekstur, które ulegają uszkodzeniu z teksturami, które działają normalnie. Będziesz więc wiedział, czy problem polega na ładowaniu tekstury, czy na sposobie ich używania. – Dave

Powiązane problemy