Kirjautuminen

Haku

Tehtävät

Keskustelu: Ohjelmointikysymykset: C: Koordinaatit OpenGL-maailmassa

Burton [11.11.2012 01:03:25]

#

Tervehdys.

Olen eksynyt jälleen OpenGL:n maailmaan. En ole koskaan oikein ymmärtänyt ko. grafiikkakirjastoa, mutta nyt olen päättänyt korjata tuon vian. Olen vasta alussa, mutta mieleeni on jo juolahtanut kysymys, johon en itse keksinyt vastausta, eikä Googlekaan tarjonnut kelvollista ratkaisua.

Miten koordinaatit toimivat OpenGL:ssä? Miten esimerkiksi voi tietää piirtävänsä ruudun vasempaan yläkulmaan neliön? Jos siirrän kameran omassa ikkunassani ruudun keskelle, syvyyteen kuusi (0, 0, -6), niin -1.65f vastaa ruudun vasenta laitaa. Mitä 1.65f tarkoittaa, ja onko olemassa tapaa, jolla nämä voisi siirtää helpommin ymmärrettävään muotoon? Jouduin vähentämään arvosta 0.01 joka kääntökerralla ja tutkin ruutua silmä kovana, kunnes huomasin, että kyllä -1.65f on oikea arvo. SDL:n kanssa voi helposti asettaa vaikkapa putpixel(0, 0, rgb(255, 255, 255)), jolloin valkoinen pikseli piirtyy kohtaan (0, 0) (eli ruudun ylävasen kulma).

Harjoitusohjelma, jota kirjoitan heikosti edistyen, on siniaaltoa pitkin kulkeva pyörivä neliö. Neliön keskipiste on siniaallon pisteessä (x, sin(x)) ja se pyörii ympäri. Osaan piirtää pyörivän neliön ja liikuttaa sitä, mutta oikeiden koordinaattien löytämisen kanssa menee sormi suuhun.

Onko olemassa keinoa muuntaa OpenGL-piirtoalustaa kaksiulotteiseksi tasoksi, jonka koordinaatit ovat (0, 0) -> (w, h) - (0, 0):n ollessa ylävasen, (w, h):n ollessa alaoikea? Tämä helpottaisi huomattavasti, sillä voisin suoraan avata vanhan SDL-ohjelmani, joka piirtää em. ohjelman, ja muuntaa sen OpenGL-funktioiksi.

User137 [11.11.2012 01:26:31]

#

Tuolla on joku opas ainakin:
http://content.gpwiki.org/index.php/OpenGL:Tutorials:Tutorial_Framework:Ortho_and_Alpha
Googlella löytyy lisää "opengl ortho".

Siis lähinnä tuo pätkä:

glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(0,800,0,600,-100,100);
glMatrixMode(GL_MODELVIEW);

Metabolix [11.11.2012 01:41:34]

#

OpenGL on lähtökohtaisesti 3D-kirjasto, ja koordinaatisto toimii sen mukaan, yksinkertaistetusti näin: Kun esim. funktiolle glVertex3 annetaan jokin sijainti, sitä liikutetaan ensin modelview-matriisin mukaisesti, jotta saadaan pisteen sijainti suhteessa katsojaan. Sitten piste projisoidaan tasoon projektiomatriisin avulla.

Jos haluat piirtää ruudulla tiettyyn kohtaan, aseta projektiomatriisi funktiolla glOrtho (tai gluOrtho2D, jolle ei tarvitse itse syöttää z-rajoja -1 ja 1), niin saat suorakulmaisen projektion, jossa z-koordinaatti ei vaikuta objektin kokoon ja ruudun reunat on helppo hahmottaa. Pikselintarkassa piirrossa pitää kuitenkin olla tarkkana kaikkien koordinaattien ja tekstuurien asetusten kanssa.

Muunlaisella projektiolla ei yleensä ole tarkoituskaan piirtää juuri tiettyyn kohtaan ruudulla, vaan tavoitteena on, että katsoja ja kohde ovat kolmiulotteisessa avaruudessa ja näkymä sitten on suunnilleen sellainen, kuin se realistisesti olisi. Silti myös funktiolle glFrustum annetaan ihan selvässä muodossa tietyllä etäisyydellä (z) näkyvän alueen koko (x, y), jolloin ainakin tuolla syvyydellä on hyvin helppo hallita myös 2D-piirtoa. Jostain syystä useimmat (?) eivät käytä tätä funktiota vaan "oikaisevat" käyttämällä funktiota gluPerspective, jonka kanssa sitten ei olekaan enää yhtä selvää, mitä koordinaatteja on missäkin päin ruutua.

Oman 2D-ohjelman muunto suoraan OpenGL:n päälle ei ole minusta kovin mielekäs projekti, vaan kannattaa vain käyttää jotain valmista kirjastoa, joka keskustelee OpenGL:n kanssa (SDL 1.3, SFML 2.0, muita).

User137 [11.11.2012 01:55:53]

#

OpenGL:n ja 2D:n kanssa on jännä huomata mitä pikselintarkka grafiikka tarkoittaa. Jos haluaa yhden pikselin piirtää kohtaan (40, 50), niin se tarkoittaa neliötä (40, 50)-(41, 51). Eli siis kokonaiset koordinaatit sijaitsee pikseleiden välissä, ei niiden keskellä. Mutta kyllä OpenGL:llä saa ihan tarkkaa 2D:tä aikaseks, ehkei ihan samaa luokkaa kun SDL, mutta tarpeeksi tarkasti, nopeammin ja efektein. Pyöritys, skaalaus, blendaus jne on SDL:llä paljon hitaampaa. Mm. pikseli-shadereitä voi käyttää yhtä hyvin 2D- kuin 3D-grafiikan kanssa.

Vastaus

Aihe on jo aika vanha, joten et voi enää vastata siihen.

Tietoa sivustosta