Shader di relatività speciale in GLSL


11

Sto cercando di implementare uno shader GLSL che aiuta a capire la relatività speciale Trasformazione di Lorentz.

Prendiamo due osservatori inerziali allineati ad asse Oe O'. L'osservatore O'è in movimento Ocon velocità v=(v_x,0,0).

Se descritto in termini di O'coordinate, un evento P' = (x',y',z',ct')ha trasformato le coordinate(x,y,z,ct)= L (x',y',z',ct')

dove L è una matrice 4x4 chiamata trasformazione di Lorentz che ci aiuta a scrivere le coordinate dell'evento P 'in Ocoordinate.

(per dettagli guarda http://en.wikipedia.org/wiki/Lorentz_transformation#Boost_in_the_x-direction )

Ho scritto un primo shader di vertice preliminare che applica la trasformazione di Lorentz data la velocità a ogni vertice, ma non riesco a far funzionare correttamente la trasformazione.

vec3 beta= vec3(0.5,0.0,0.0);
float b2 = (beta.x*beta.x + beta.y*beta.y + beta.z*beta.z )+1E-12; 
float g=1.0/(sqrt(abs(1.0-b2))+1E-12); // Lorentz factor (boost)
float q=(g-1.0)/b2;

//http://en.wikipedia.org/wiki/Lorentz_transformation#Matrix_forms
vec3 tmpVertex = (gl_ModelViewMatrix*gl_Vertex).xyz;
float w = gl_Vertex.w;

mat4  lorentzTransformation =
        mat4(
            1.0+beta.x*beta.x*q ,   beta.x*beta.y*q ,   beta.x*beta.z*q , beta.x*g ,
            beta.y*beta.x*q , 1.0+beta.y*beta.y*q ,   beta.y*beta.z*q , beta.y*g ,
            beta.z*beta.x*q ,   beta.z*beta.y*q , 1.0+beta.z*beta.z*q , beta.z*g ,
            beta.x*g , beta.y*g , beta.z*g , g
            );
vec4 vertex2 = (lorentzTransformation)*vec4(tmpVertex,1.0);


gl_Position = gl_ProjectionMatrix*(vec4(vertex2.xyz,1.0) );

Questo shader dovrebbe applicarsi a tutti i vertici ed eseguire la trasformazione non lineare di Lorentz, ma la trasformazione che esegue è chiaramente diversa da quella che mi aspetterei (in questo caso una contrazione della lunghezza sull'asse x).

Qualcuno ha già lavorato su uno shader di relatività speciale per il videogioco 3D?


In realtà è una trasformazione lineare, non non lineare, come afferma la wiki che hai collegato. Quindi, ciò che vedi suona bene, tuttavia, è difficile dirlo senza vederlo.
Maik Semder,

Puoi provare questo shader in ShaderMaker per vedere gli effetti, ma quello che vorrei ottenere è questo effetto: spacetimetravel.org/relaflug/relaflug.html Qui dovremmo vedere la contrazione della lunghezza sull'asse x ma vedo un ridimensionamento errato
Linello,

Sposti davvero la videocamera? Il collegamento spacetimetravle viene fornito con il codice sorgente, potrebbe valere la pena dare un'occhiata qui
Maik Semder,

anche la velocità di 0,5 c / s è un po 'piccola, prova a usare qualcosa di più grande di 0,9, l'esempio usa 0,93 c / s e sposta la fotocamera con quella velocità
Maik Semder,

No, suppongo che l'osservatore Osia (0,0,0) guardando l'asse z mentre l'osservatore O'è in movimento Ocon velocità v_xe gli oggetti descritti O'sono a riposo. So che in questo vertex shader la trasformazione viene applicata solo ai vertici, quindi la deformazione delle linee viene persa, ma voglio solo capire e far funzionare questo all'inizio. Sembra che il gioco Polynomial abbia già fatto trasformazioni di questo tipo, ma lo shader che ho trovato non ha nulla di interessante, perché ottengo gli stessi risultati! bit.ly/MueQqo
linello

Risposte:


4

Per implementare la contrazione di Lorentz, la soluzione migliore è probabilmente quella di ridimensionare esplicitamente l'oggetto di 1 / gamma lungo la direzione del movimento.

Il problema è che la trasformazione di Lorentz sposta i vertici nella direzione del tempo e nello spazio, quindi da sola non ti darà l'aspetto di un oggetto in movimento in un determinato momento. Per fare ciò, dovresti prima trasformare l'intero oggetto, quindi prendere una "fetta" attraverso di essa parallela agli assi dello spazio, come in questo diagramma:

Diagramma spazio-temporale della contrazione di Lorentz

Per calcolare questo per davvero, dovresti effettivamente effettuare il raytrace in 4D, intersecando la linea mondiale del vertice con l'iperpiano 3D del momento attuale nel frame di riferimento dell'osservatore. Credo che il risultato di questo sia lo stesso del semplice ridimensionamento di 1 / gamma.

(Per ulteriore credito, prendi in considerazione il fatto che un osservatore non vedrebbe effettivamente l'intero oggetto in un solo momento: lo vedrebbero usando i raggi di luce. Quindi dovresti intersecare la linea del mondo vertice con il cono di luce passato dell'osservatore, che in realtà modifica significativamente i risultati: un oggetto che si allontana da te sembrerà accorciato, ma un oggetto che si muove verso di te apparirà allungato e un oggetto che si sposta su un lato verrà ruotato - vedi rotazione di Penrose-Terrell per più.)


Ok, ma cosa succede se cambio l'ora all'interno della simulazione? Considero il tempo come un galleggiante uniforme da passare dall'esterno dello shader, questo dovrebbe deformare correttamente l'oggetto nel tempo?
Linello,

Se il tempo è una costante per ogni fotogramma, allora stai prendendo una fetta di tempo 3D del mondo 4D, quindi sì, ciò che ho detto sopra vale.
Nathan Reed

Non capisco anche se devo implementare l'aberrazione relativistica separatamente dalla trasformazione di Lorentz.
Linello,

@linello Se ti interessa l'aberrazione, sembra che tu abbia bisogno della versione più sofisticata di questo che ho descritto nell'ultimo paragrafo - cioè intersecare la linea del mondo del vertice con il cono di luce passato dell'osservatore e spostare il vertice sul punto di intersezione posizione spaziale. Questo dovrebbe essere fattibile nello shader di vertice, credo. La trasformazione di Lorentz sarebbe coinvolta solo nella creazione della linea mondiale del vertice. Si noti inoltre che se l'oggetto sta accelerando, ruotando, ecc., La linea del mondo è curva.
Nathan Reed
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.