2011-09-02 10 views
12


Questo è il mio primo post qui, quindi scusarsi per eventuali errori.
Sto sviluppando un semplice gioco d'azione con l'utilizzo di OpenGL ES 2.0 e Android 2.3. La mia struttura di gioco su cui sto lavorando al momento si basa su sprite bidimensionali che esistono nel mondo tridimensionale. Ovviamente le mie entità del mondo possiedono informazioni come la posizione all'interno del mondo immaginario, il valore rotazionale sotto forma di matrice float [], handle di texture OpenGL e handle di Bitmap di Android (non sono sicuro che quest'ultimo sia necessario come sto facendo la rasterizzazione con l'uso della macchina OpenGl, ma per il momento è solo lì, per mia comodità). Questo è brevemente lo sfondo, ora alla questione problematica.
Attualmente sono bloccato con il rilevamento delle collisioni basato sui pixel perché non sono sicuro di quale oggetto (qui trama OGL o bitmap di Android) ho bisogno di campionare. Voglio dire, ho già provato ad assaggiare la Bitmap di Android, ma non ha funzionato completamente per me - molti crash in fase di esecuzione in relazione alla lettura al di fuori della bitmap. Ovviamente per poter leggere i pixel dalla bitmap, ho usato il metodo Bitmap.create per ottenere sprite ruotate correttamente. Ecco il frammento di codice:
Problema di rilevamento collisione basato su pixel con OpenGLES 2.0 su Android

android.graphics.Matrix m = new android.graphics.Matrix(); 
if(o1.angle != 0.0f) {   
    m.setRotate(o1.angle); 
    b1 = Bitmap.createBitmap(b1, 0, 0, b1.getWidth(), b1.getHeight(), m, false); 
} 

Un altro problema, che potrebbe aggiungere al problema, o addirittura essere il problema principale, è che il mio rettangolo di intersezione (rettangolo che indica spazio bidimensionale reciproco per entrambi gli oggetti) è costruire da parti di due scatole di delimitazione che sono state calcolate con l'uso delle matrici OpenGL Matrix.multiplyMV funzionalità (codice di seguito). Potrebbe essere, che quei due metodi di calcolo delle matrici Android e OpenGL non sono uguali?

Matrix.rotateM(mtxRotate, 0, -angle, 0, 0, 1); 

// original bitmap size, equal to sprite size in it's model space, 
// as well as in world's space 
float[] rect = new float[] { 
    origRect.left, origRect.top, 0.0f, 1.0f, 
    origRect.right, origRect.top, 0.0f, 1.0f, 
    origRect.left, origRect.bottom, 0.0f, 1.0f, 
    origRect.right, origRect.bottom, 0.0f, 1.0f 
}; 

android.opengl.Matrix.multiplyMV(rect, 0, mtxRotate, 0, rect, 0); 
android.opengl.Matrix.multiplyMV(rect, 4, mtxRotate, 0, rect, 4); 
android.opengl.Matrix.multiplyMV(rect, 8, mtxRotate, 0, rect, 8); 
android.opengl.Matrix.multiplyMV(rect, 12, mtxRotate, 0, rect, 12); 

// computation of object's bounding box (it is necessary as object has been 
// rotated second ago and now it's bounding rectangle doesn't match it's host 
float left = rect[0]; 
float top = rect[1]; 
float right = rect[0]; 
float bottom = rect[1]; 
for(int i = 4; i < 16; i += 4) { 
    left = Math.min(left, rect[i]); 
    top = Math.max(top, rect[i+1]); 
    right = Math.max(right, rect[i]); 
    bottom = Math.min(bottom, rect[i+1]); 
}; 
+0

generale OpenGL è solo * * per la grafica. Non dovresti lasciare che tocchi le coordinate del tuo gioco/mondo eccetto per fare una * copia * trasformata di loro per la presentazione sullo schermo. Questo significa che qualsiasi casella di delimitazione che hai deve essere calcolata usando il tuo codice. E fai attenzione ai sistemi di fisica basati sui pixel :) Sembra una buona idea per tutto, finché non lo provi e scopri che è solo una buona idea per gli oggetti che non interagiscono fisicamente (qualsiasi oggetto che scompare quando lo tocchi, come un proiettile o un oggetto preso, o se muori istantaneamente quando viene toccato). –

+0

Grazie per questa risposta. Il risultato che volevo ottenere era quello di avere una collisione migliore di quella basata su cerchi e scatole.Questo è probabilmente vero che le collisioni tra pixel non sono abbastanza buone in quanto sono computazionalmente costose. Di recente ho letto qualcosa chiamato "forme convesse" e probabilmente le userò per aumentare il comportamento del mio sistema di collisione. – cplusogl

+1

L'avvertimento su per-pixel è stato principalmente perché ho giocato con esso, implementato una funzione di ducking per un vecchio -strumentario di stile di scuola, e capito che non sembrava giusto. La complessità computazionale può essere notevolmente ridotta con le giuste tecniche (inizialmente solo la collisione con AABB, eventualmente ridotta dalle informazioni di partizionamento spaziale come un sistema di griglia o quad-tree dinamico, quindi utilizzare speciali maschere di collisione solo in bianco e nero e testare solo le sovrapposizione). Le forme convesse sono sicuramente un buon modo per andare anche tu e ti permetteranno di sostituire l'arte 3d in un gioco con solo 2d interazioni. –

risposta

0

Cheers,

prima nota che c'è un bug nel codice. Non è possibile utilizzare Matrix.multiplyMV() con il vettore di origine e di destinazione che è lo stesso (la funzione calcolerà correttamente una coordinata x che sovrascriverà nel vettore sorgente. Tuttavia, ha bisogno della x originale per calcolare y, z e w coordinate - che sono a loro volta imperfette). Si noti inoltre che sarebbe più facile per voi utilizzare le sfere di delimitazione per la prima fase di collisione di rilevamento, poiché non richiedono un codice così complicato per eseguire la trasformazione della matrice.

Quindi, il rilevamento di collisione. Non si dovrebbe leggere da bitmap o texture. Quello che dovresti fare è costruire una silhouette per il tuo oggetto (che è piuttosto facile, silhouette è solo una lista di posizioni). Dopodiché hai bisogno di costruire oggetti convessi che riempiano la silhouette (non convessa). Può essere raggiunto da es. algoritmo di clipping dell'orecchio. Potrebbe non essere il più veloce, ma è molto facile da implementare e verrà eseguito una sola volta. Una volta che hai gli oggetti convessi, puoi trasformare le loro coordinate usando una matrice e rilevare le collisioni con il tuo mondo (ci sono molti bei articoli sulle intersezioni raggio-triangolo che puoi usare), e ottieni la stessa precisione come se dovessi usare pixel rilevamento delle collisioni basato su

Spero che aiuta ...

+0

Oh, dovrò controllare le mie altre chiamate multipleMV, grazie per averlo indicato. Tuttavia, stranamente il comportamento dell'applicazione non ha mai presentato alcun problema a causa dell'uso improprio di multiplyMV ... Per quanto riguarda le forme convesse, dovrò approfondire l'argomento. Grazie molto! – cplusogl

Problemi correlati