PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : Quake1 Model File Format (MDL)


Kennung Eins
2003-06-23, 12:18:06
Hi Leute,

Ich will ein Q1 Model File nutzen um es in einem Programm anzuzeigen - aber irgendwie funzt das nicht so wie ich es will.

Und zwar:
Ich habe mir die MDL-Datei in OpenGL-Code wandeln lassen (mittels 3DWin4) - das sieht dann so aus:

/*
Copyright by Thomas Baier (thomas.baier@stmuc.com)
Created by OpenGL Export Plugin 1.0 at Mon Jun 23 10:46:53 2003
OpenGL-Structure
*/


(...)


/* Object: BOSS0*/
/* Vertices */
#define MAX_VERTICES_0 325
float verticies_0[MAX_VERTICES_0 * 3] =
{
161.310800f, -14.673797f, 38.908226f ,
182.330075f, -21.328125f, 59.500694f ,
165.514655f, -19.110016f, 33.760109f ,
171.820437f, -12.455688f, 31.186050f ,
167.616582f, -8.019469f, 36.334167f ,
163.412727f, 11.943516f, 38.908226f ,
184.432002f, 23.034062f, 59.500694f ,
169.718510f, 5.289187f, 36.334167f ,
173.922365f, 11.943516f, 31.186050f ,

(...)Wenn ich nun aber diese Dreiecke anzeigen lassen will, kommt da nur Salat dabei raus :(

Kann mir jemand helfen?

Einfachkrank
2003-06-23, 15:10:25
Hi,

mhh... ich weiß nicht direkt, wie das MDL Format gerendert wird - vielleicht probierst du mal verschiedene Primitives aus ??? Oder poste doch mal deinen Quellcode mit dem du den Salat rendern willst -vielleicht stimmt da was nicht.

MFG Einfachkrank

Kennung Eins
2003-06-23, 15:55:32
Jo oki ..

ich kenne das genaue Format der MDLs auch nicht, das einzige was ich finden konnte war auf http://www.wotsit.org/ ("MD2") in das Suchen-Feld eingeben, die erlauben keine direkten links) - und in diesem File steht leider auch nur drin, was ich schon weiß.

Nämlich, daß da drin Vertices, Faces, Normalen und Texturdaten stecken.

Es gibt einige Konverter, wie z.B. 3dwin4 oder "3D Object Converter", die machen aus diesen (für mich unlesbaren) Daten brauchbare Daten.

Das sieht dann (mit meinen Anzeige-Methoden) so aus:

/*
Copyright by Thomas Baier (thomas.baier@stmuc.com)
Created by OpenGL Export Plugin 1.0 at Mon Jun 23 14:09:37 2003
OpenGL-Structure
*/

#include "scene.h"
#include <GL\glut.h>

float WorldBoundMin[3] = {14.175873f, -176.595781f, -161.868340f};
float WorldBoundMax[3] = {302.139943f, 169.429281f, 77.519104f};

/* BackGround */
float background[3] = { 0.000000f, 0.000000f, 0.000000f};
/* Lights */
Light_Def lights[MAX_LIGHTS] =
{
/* PointLight: def_light1*/
{{0.800000f, 0.800000f, 0.800000f},{654.752773f, 856.544287f, 604.279887f},0,{0.000000f, 0.000000f, 0.000000f},0.000000f,0.000000f},
/* PointLight: def_light2*/
{{0.700000f, 0.700000f, 0.700000f},{-835.031821f, -3.583250f, 604.279887f},0,{0.000000f, 0.000000f, 0.000000f},0.000000f,0.000000f},
/* PointLight: def_light3*/
{{0.600000f, 0.600000f, 0.600000f},{654.752773f, -863.710787f, 604.279887f},0,{0.000000f, 0.000000f, 0.000000f},0.000000f,0.000000f}
};
/* Materials */
Material_Def materials[MAX_MATERIALS] =
{
/* Material: DEFAULT*/
{{0.300000f, 0.300000f, 0.300000f},{0.600000f, 0.600000f, 0.600000f},{0.900000f, 0.900000f, 0.900000f},{0.000000f, 0.000000f, 0.000000f},1.000000f,-1},
/* Material: skin_mat*/
{{0.300000f, 0.300000f, 0.300000f},{0.600000f, 0.600000f, 0.600000f},{0.900000f, 0.900000f, 0.900000f},{0.000000f, 0.000000f, 0.000000f},1.000000f,-1}
};
/* Texture Maps*/
Map_Def texture_maps[1] =
{
0
};
/* Object: BOSS0*/
/* Vertices */
#define MAX_VERTICES_0 (325)
float verticies_0[MAX_VERTICES_0 * 3] =
{
161.310800f, -14.673797f, 38.908226f ,
182.330075f, -21.328125f, 59.500694f ,
165.514655f, -19.110016f, 33.760109f ,
171.820437f, -12.455688f, 31.186050f ,
167.616582f, -8.019469f, 36.334167f ,
163.412727f, 11.943516f, 38.908226f ,
184.432002f, 23.034062f, 59.500694f ,
169.718510f, 5.289187f, 36.334167f ,
173.922365f, 11.943516f, 31.186050f ,
167.616582f, 18.597844f, 33.760109f ,
123.476104f, -127.797375f, -17.721062f ,
112.966467f, -161.069015f, -4.850769f ,
129.781887f, -130.015484f, -9.998886f ,
123.476104f, -125.579265f, -2.276711f ,
117.170322f, -125.579265f, -9.998886f ,
106.660684f, 122.848984f, -20.295120f ,

(..)

45.704786f, -74.562750f, -161.868340f ,
58.316351f, 71.832469f, -123.257462f ,
24.685511f, -1.365141f, -120.683403f ,
39.399004f, -1.365141f, -84.646584f ,
37.297076f, -47.945437f, -84.646584f ,
68.825989f, -74.562750f, -71.776291f
};
/* Normals */
#define MAX_NORMALS_0 (671)
float normals_0[MAX_NORMALS_0 * 3] =
{
0.029245f, -0.994067f, -0.104765f ,
-0.521672f, -0.808933f, 0.271083f ,
-0.605804f, 0.287036f, -0.742032f ,
-0.605804f, 0.287036f, -0.742032f ,
0.566152f, -0.702997f, -0.430426f ,
0.187036f, 0.898414f, 0.397329f ,
-0.420565f, 0.645250f, 0.637791f ,
0.702785f, 0.710373f, -0.038259f ,
-0.362359f, -0.614467f, 0.700804f ,
-0.709653f, 0.038765f, 0.703484f ,
-0.574521f, -0.241968f, -0.781906f ,
-0.574521f, -0.241968f, -0.781906f ,
0.923367f, 0.082349f, -0.374984f ,
0.814779f, -0.574587f, -0.077364f ,
-0.668531f, 0.670780f, 0.321124f ,
0.540785f, 0.695480f, -0.473137f ,

(..)

-0.898386f, -0.234636f, 0.371280f ,
-0.943303f, 0.007364f, 0.331852f ,
-0.150389f, -0.957042f, 0.247900f ,
-0.087506f, -0.897901f, -0.431412f ,
0.062144f, 0.011217f, -0.998004f ,
-0.118005f, 0.808953f, 0.575908f ,
-0.056873f, 0.666179f, -0.743620f ,
-0.951730f, -0.156303f, 0.264158f ,
-0.465496f, -0.883218f, -0.056912f
};
/* Textures */
#define MAX_TEXTURES_0 (325)
float textures_0[MAX_TEXTURES_0 * 3] =
{
0.700000f, 0.061856f, 0.000000f ,
0.183333f, 0.139175f, 0.000000f ,
0.190000f, 0.051546f, 0.000000f ,
0.200000f, 0.056701f, 0.000000f ,
0.210000f, 0.061856f, 0.000000f ,
0.820000f, 0.896907f, 0.000000f ,
0.336667f, 0.974227f, 0.000000f ,

(..)

0.376667f, 0.268041f, 0.000000f ,
0.753333f, 0.262887f, 0.000000f ,
0.753333f, 0.350515f, 0.000000f ,
0.676667f, 0.345361f, 0.000000f ,
0.130000f, 0.391753f, 0.000000f
};
/* Faces */
#define MAX_FACE_INDICES_0 (555)
int face_indicies_0[MAX_FACE_INDICES_0 * 9] =
{
2, 1, 0 ,0, 0, 1 ,2, 1, 0 ,
0, 3, 2 ,2, 2, 3 ,0, 3, 2 ,
3, 1, 2 ,4, 0, 0 ,3, 1, 2 ,
1, 4, 0 ,5, 5, 6 ,1, 4, 0 ,
4, 3, 0 ,3, 2, 2 ,4, 3, 0 ,
1, 3, 4 ,5, 7, 5 ,1, 3, 4 ,
7, 6, 5 ,8, 9, 9 ,7, 6, 5 ,
5, 8, 7 ,10, 10, 11 ,5, 8, 7 ,
8, 6, 7 ,12, 12, 13 ,8, 6, 7 ,
6, 9, 5 ,9, 14, 9 ,6, 9, 5 ,
9, 8, 5 ,11, 10, 10 ,9, 8, 5 ,
6, 8, 9 ,12, 12, 15 ,6, 8, 9 ,
12, 11, 10 ,16, 16, 17 ,12, 11, 10 ,
10, 13, 12 ,18, 18, 19 ,10, 13, 12 ,
13, 11, 12 ,20, 16, 16 ,13, 11, 12 ,
11, 14, 10 ,21, 21, 22 ,11, 14, 10 ,
14, 13, 10 ,23, 18, 18 ,14, 13, 10 ,
11, 13, 14 ,21, 24, 21 ,11, 13, 14 ,
17, 16, 15 ,25, 26, 26 ,17, 16, 15 ,
15, 18, 17 ,27, 27, 28 ,15, 18, 17 ,
18, 16, 17 ,29, 29, 30 ,18, 16, 17 ,
16, 19, 15 ,31, 32, 26 ,16, 19, 15 ,

(..)

323, 314, 224 ,662, 627, 452 ,323, 314, 224 ,
322, 224, 225 ,663, 452, 451 ,322, 224, 225 ,
221, 321, 230 ,449, 659, 669 ,221, 321, 230 ,
221, 319, 250 ,449, 670, 484 ,221, 319, 250
};
#define DEF_MAT_REF_0 (1)

/* Objects */
Object_Def objects[MAX_OBJECTS] =
{
{"BOSS0", face_indicies_0, MAX_FACE_INDICES_0, verticies_0, MAX_VERTICES_0, normals_0, MAX_NORMALS_0, textures_0, MAX_TEXTURES_0, DEF_MAT_REF_0 }
};

void keyboardFunc(unsigned char key, int x, int y)
{
switch(key)
{
case 27:
exit(0);
}
}

void display(void){
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
float m = 0;
for (int i = 0; i < (MAX_VERTICES_0);i++) {
if (verticies_0[i]>m) m=verticies_0[i];
}
glBegin(GL_TRIANGLES);
for (i = 0; i < (MAX_VERTICES_0);i+=3) {
glVertex3f(verticies_0[i]/m,verticies_0[i+1]/m,verticies_0[i+2]/m);
}
glEnd();
glutSwapBuffers();
}


int main(int argc, char **argv)
{
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH);
glutCreateWindow("Spaß");
glutFullScreen();
glutKeyboardFunc(keyboardFunc);
glutDisplayFunc(display);
glutMainLoop();
return 0;
}Ich habe inzwischen gelesen, daß der 3dwin4 in der Shareware "eventuell jeden 5. Vertex weglassen kann" (frei übersetzt von der Homepage des Progs), aber die Vertices von dem anderen Programm (3D Object Converter) bringens auch nicht wirklich.

Das Ganze sieht dann z.B. so aus:

Kennung Eins
2003-06-23, 15:59:58
Rauskommen sollte allerdings (hier schon geshadet):

zeckensack
2003-06-23, 16:03:54
Du mußt die indices benutzen.

StattglBegin(GL_TRIANGLES);
for (i = 0; i < (MAX_VERTICES_0);i+=3) {
glVertex3f(verticies_0[i]/m,verticies_0[i+1]/m,verticies_0[i+2]/m);
}
glEnd();
Versuch's mal so:glBegin(GL_TRIANGLES);
for (i = 0; i < (3*MAX_FACES???);++i) {
glVertex3f(verticies_0[3*indices_0[ i]]/m,verticies_0[3*indices_0[ i]+1]/m,verticies_0[3*indices_0[ i]+2]/m);
}
glEnd();

*nicht getestet*

Xmas
2003-06-23, 16:12:16
Die Indices sind offensichtlich in der Ordnung:
Vertex1, Vertex2, Vertex3, Normale1, Normale2, Normale3, TexCoord1, TexCoord2, TexCoord3


glBegin(GL_TRIANGLES);
for(i = 0; i < MAX_FACE_INDICES_0; ++i)
{
for(j = 0; j < 3; ++j)
{
glTexCoord3fv(&textures_0[indices_0[9 * i + 6 + j] * 3]);
glNormal3fv(&normals_0[indices_0[9 * i + 3 + j] * 3]);
glVertex3fv(&verticies_0[indices_0[9 * i + j] * 3);
}
}
glEnd();

Kennung Eins
2003-06-23, 16:21:47
hmm leider bringt Zeckis Vorschlag auch nur wilde Dreiecke auf den Schirm, und Xmas' Lösung zeigt gar nichts an ...

Kennung Eins
2003-06-23, 16:41:08
Ich hab mal das file komplett hochgeladen - vielleicht erkennt ja jemand, ob an den vertices irgendwas falsch ist?

Das kommt mir alles echt spanisch vor...

Xmas
2003-06-23, 16:56:50
Original geschrieben von Kennung Eins
Ich hab mal das file komplett hochgeladen - vielleicht erkennt ja jemand, ob an den vertices irgendwas falsch ist?

Das kommt mir alles echt spanisch vor...

http://www.uni-magdeburg.de/tuemler/scene.cpp
Fehlt nur noch die scene.h...

btw: "The matrix generated by gluLookAt postmultiplies the current matrix."

Kennung Eins
2003-06-23, 17:05:33
Original geschrieben von Xmas
Fehlt nur noch die scene.h...

btw: "The matrix generated by gluLookAt postmultiplies the current matrix." Oh äh .h (http://www.uni-magdeburg.de/tuemler/scene.h) ist jetzt auch da.

Xmas
2003-06-23, 17:23:41
Hauptsächlich ein Matrizenproblem.

Der folgende Code gibt ein halbwegs erkennbares Bild, allerdings stimmt mit den Dreiecken noch etwas nicht.

Edit: Jetzt gehts, der Z-Test fehlte.


void display(void){
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(90.0, 1.33, 0.2, 5000);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
gluLookAt(copx, copy - 50, copz - 400, atx, aty, atz, 0.0, 1.0, 0.0);
glEnable(GL_LIGHTING);
glEnable(GL_LIGHT0);
glEnable(GL_DEPTH_TEST);
glDepthFunc(GL_LEQUAL);
glBegin(GL_TRIANGLES);
for(i = 0; i < MAX_FACE_INDICES_0; ++i)
{
for(int j = 0; j < 3; ++j)
{
glTexCoord3fv(&textures_0[face_indicies_0[9 * i + 6 + j] * 3]);
glNormal3fv(&normals_0[face_indicies_0[9 * i + 3 + j] * 3]);
glVertex3fv(&verticies_0[face_indicies_0[9 * i + j] * 3]);
}
}
glEnd();

glutSwapBuffers();
}

Xmas
2003-06-23, 17:30:23
Übrigens solltest du auf jeden Fall eine Initialisierungsfunktion schreiben die solche Dinge wie Depth Test, Lighting, Perspektivprojektion, Clear Color/Depth u.ä. gleich am Anfang einstellt.

Kennung Eins
2003-06-23, 17:37:06
Hey krass, das funktioniert! ^^
Ich dank dir ganz sehr doll!!


Die InitFunc steht bereits im Hauptprojekt :)

thx again

Einfachkrank
2003-06-24, 17:11:35
Hi,

wenn wir das schon mal kurz in Erwähnung hatten - was sind denn Indizes genau?

MFG Einfachkrank

Kennung Eins
2003-06-24, 18:20:57
"Indizes" ist einfach nur der Plural von Index (also sozusagen "Indexe" :) ).
Also die "face_indicies_0" geben hier einfach nur an, wie aus welchem Vertex + Texturdaten + Normalen ein Dreieck gebildet wird.

Am Beispiel für das erste Dreieck (Alle Werte aus vorher gepostetem Code):int face_indicies_0[MAX_FACE_INDICES_0 * 9] =
{
2, 1, 0 ,0, 0, 1 ,2, 1, 0 ,
(...)
}Nimm für das erste Vertex die Koordinaten 2 und 1 und 0 (welches 38.908226f, -14.673797f und 161.310800f wären), für dessen Normalen die Werte 0.029245f, 0.029245f, -0.994067f (= 0, 0, 1) und für die Texturkoordinaten die Werte 0.000000f , 0.061856f, 0.700000f (= 2, 1, 0).

Ich hoffe ich hab das verständlich beschrieben :)

Xmas
2003-06-24, 18:50:25
Original geschrieben von Einfachkrank
Hi,

wenn wir das schon mal kurz in Erwähnung hatten - was sind denn Indizes genau?

MFG Einfachkrank
Indizes sind in diesem Kontext Verweise auf ein Element eines Arrays/einer Tabelle.

Bei array[x] wird x als Index in das Array verwendet.