Ongelma on 3D-mallien käytössä OpenGL:n kanssa. Malliformaatti on tuttu ja turvallinen Wavefront OBJ. Olenkin tässä yrittänyt tehdä koodia niiden lataamiseen ja epäonnistunut surkeasti. En oikeastaan edes tiedä missä virhe piilee kun noita verteksejä on perin monta.
Filu jota yritän saada malliksi
Hakemistossa on myös filun MTL-kirjasto
Mallin pitäisi näyttää tältä (Blenderin mielipide)
Mutta sen pinta näyttääkin tältä
Luokat ovat tässä
struct Verteksi { float x,y,z; }; struct PintaNelio { int kulma1, kulma2, kulma3, kulma4; }; class object3D { public: int kahva; PintaNelio pinnat[10000]; Verteksi VertexPoints [10000]; Verteksi VertexNormals[10000]; }; int vapaakahva = 0; object3D Objektit[1]; Verteksi VertexPoints[1]; int pointteja=0; int tasoja=0;
Latausfunktio:
int LataaObjekti(char *polku) { FILE *filu; // Määritellään tiedostopointteri char rivi[100] ="\0"; // Rivin merkkijono char tyyppi; // Tiedoston rivin tyyppi char tyyppi2; // Tuplatietoriveille float temppiste_x = 0; // Väliaikainen piste X float temppiste_y = 0; // Väliaikainen piste Y float temppiste_z = 0; // Väliaikainen piste Z bool kauttaviiva = 0; // Sisältääkö face-definitiot kauttaviivan int i = 0; // Indeksi for-looppia varten int kahva = 0; // Mallin kahva int temptaso_1 = 0; // Väliaikainen taso 1 int temptaso_2 = 0; // Väliaikainen taso 2 int temptaso_3 = 0; // Väliaikainen taso 3 int temptaso_4 = 0; // Väliaikainen taso 4 int peelo = 0; // Peelo int vapaapiste = 0; // Vapaa piste int vapaapinta = 0; // Vapaa pinta filu = fopen(polku, "r"); // Avataan filu if (filu == NULL) { // Tsekataan että filun avaus onnistui return 0; // Jos ei, palautetaan nolla } // Tämä on tärkeää ettei avata filua osoitteesta nolla -> kaataa systeemin while(!feof(filu)) { fgets(rivi, 99, filu); sscanf(rivi, "%c%c", &tyyppi, &tyyppi2); if (tyyppi == '#') { tyyppi = '\0'; tyyppi2 = '\0'; } else if (tyyppi == 'v' && tyyppi2 == ' ') { // Pointti sscanf(rivi, "%c%c %f %f %f\n", &tyyppi, &tyyppi2, &temppiste_x, &temppiste_y, &temppiste_z); Objektit[vapaakahva].VertexPoints[vapaapiste].x = temppiste_x / 3; Objektit[vapaakahva].VertexPoints[vapaapiste].y = temppiste_y / 3; Objektit[vapaakahva].VertexPoints[vapaapiste].z = temppiste_z / 3; temppiste_x = 0; temppiste_y = 0; temppiste_z = 0; vapaapiste++; pointteja++; } else if (tyyppi == 'f' && tyyppi2 == ' ') { // Face for (i=0;i<100;i++) { // Replasoidaan kauttaviivat välillä if (rivi[i] == '/') { rivi[i] = ' '; kauttaviiva = true; } } if (kauttaviiva) { sscanf(rivi, "%c %i %i %i %i %i %i %i %i\n", &tyyppi, &temptaso_1, &temppiste_x, &temptaso_2, &temppiste_y, &temptaso_3, &temppiste_z, &temptaso_4); } else { sscanf(rivi, "%c %i %i %i %i\n", &tyyppi, &temptaso_1, &temptaso_2, &temptaso_3, &temptaso_4); } Objektit[vapaakahva].pinnat[vapaapinta].kulma1 = temptaso_1; Objektit[vapaakahva].pinnat[vapaapinta].kulma2 = temptaso_2; Objektit[vapaakahva].pinnat[vapaapinta].kulma3 = temptaso_3; Objektit[vapaakahva].pinnat[vapaapinta].kulma4 = temptaso_4; temptaso_1 = 0; temptaso_2 = 0; temptaso_3 = 0; temptaso_4 = 0; temppiste_x = 0; temppiste_y = 0; temppiste_z = 0; vapaapinta++; tasoja++; kauttaviiva = false; tyyppi = '\0'; } for (i=0; i<100; i++) rivi[i] = '\0'; } fclose(filu); filu = 0; Objektit[vapaakahva].kahva = vapaakahva; vapaakahva++; return Objektit[vapaakahva].kahva; }
Ja sitten piirto-osio jossa luulisin ainakin olevan jotain häikkää
for(int i=0; i < tasoja; i++) { glBegin(GL_POLYGON); glVertex3f(Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma1].x, Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma1].y, Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma1].z); glVertex3f(Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma2].x, Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma2].y, Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma2].z); glVertex3f(Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma3].x, Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma3].y, Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma3].z); glVertex3f(Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma4].x, Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma4].y, Objektit[0].VertexPoints[Objektit[0].pinnat[i].kulma4].z); glEnd(); }
Mitenköhän saisin pallon näkymään oikein siellä kuvassa?
EDIT: Noi kommentit saattaa jossain näyttää vähän hassuilta, mutta tää menee yhteen kirjastoon mitä kaverin pitäisi ymmärtää ja se ei oo kovin guru C++:ssa.
Vikana on se, että formaatin speksin mukaan tiedoston ensimmäinen verteksi on indeksiltään 1 eikä 0, kuten tässä virheellisesti oletetaan. Eli jossakin kohti pitäisi tämä huomioida.
Aihe on jo aika vanha, joten et voi enää vastata siihen.