<?xml version="1.0"?>
<rss version="2.0">
	<channel>
		<title>glLoadIdentity vs glPushMatrix/glPopMatrix</title>
		<link>http://www.allegro.cc/forums/view/595000</link>
		<description>Allegro.cc Forum Thread</description>
		<webMaster>matthew@allegro.cc (Matthew Leverton)</webMaster>
		<lastBuildDate>Wed, 06 Feb 2008 03:02:37 +0000</lastBuildDate>
	</channel>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>ok so i&#39;m pretty new to opengl...<br />if i want to rotate two objects with different angles i have to call either glLoadIdentity after the first rotation or i have to call glPopMatrix, rotate and glPushMatrix for each object...<br />so wich one to use?
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Frank Drebin)</author>
		<pubDate>Sun, 03 Feb 2008 00:05:27 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>Push and pop.</p><p>That way, if you decide you want the whole rotation to be part of a more complicated system that&#39;s also moving around and rotating, you don&#39;t have to redo everything. <img src="http://www.allegro.cc/forums/smileys/smiley.gif" alt=":)" />
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (amber)</author>
		<pubDate>Sun, 03 Feb 2008 00:09:52 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>ok but both have basically the same effect - or is there anything i should take care of?
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Frank Drebin)</author>
		<pubDate>Sun, 03 Feb 2008 00:27:04 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>They don&#39;t have the same effect.</p><p>glLoadIdentity replaces the current matrix with the identity matrix.</p><p>glPushMatrix pushes the current matrix onto a stack. You can then pull the top matrix off the stack and make it the current one later using glPopMatrix.</p><p>Those are only the same if:
</p><ul><li><p> your camera is always fixed at (0, 0, 0) looking along z</p></li><li><p> all of your models are single, rigid shapes</p></li><li><p> you loaded your matrix stack with the identity in the first place</p></li></ul><p>
Or if you&#39;re doing lots of unnecessary arithmetic yourself on the CPU, making your code more complicated and your application less speedy.
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Thomas Harte)</author>
		<pubDate>Sun, 03 Feb 2008 01:05:44 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><div class="quote_container"><div class="title">Quote:</div><div class="quote"><p>
glPushMatrix pushes the current matrix onto a stack.
</p></div></div><p>
To make that more clear, the current matrix is not affected by this at all. glPushMatrix simply makes a copy that you can retrieve later on with glPopMatrix. You still will have your old transformation matrix as your current matrix that still has to be cleared to an identity matrix. Thus, you need to call glLoadIdentity regardless (at least once, as Thomas Harte&#39;s third bullet suggests).
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (SiegeLord)</author>
		<pubDate>Sun, 03 Feb 2008 01:20:35 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><div class="quote_container"><div class="title">Quote:</div><div class="quote"><p>
Thus, you need to call glLoadIdentity regardless (at least once, as Thomas Harte&#39;s third bullet suggests).
</p></div></div><p>
don&#39;t get it... i have to call glLoadIdentity() once at least?
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Frank Drebin)</author>
		<pubDate>Sun, 03 Feb 2008 18:00:08 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><div class="quote_container"><div class="title">Quote:</div><div class="quote"><p>
don&#39;t get it... i have to call glLoadIdentity() once at least?
</p></div></div><p>
I&#39;m sorry, I&#39;m probably about to repeat a whole bunch of information you already know. I don&#39;t mean to be patronising, I&#39;m just not sure exactly how to answer otherwise.</p><p>OpenGL has two matrix stacks that affect how geometry is mapped from 3d space to your screen — PROJECTION and MODELVIEW.</p><p>When you tell OpenGL to process geometry (through glVertex3f, vertex arrays or any other method) it first applies the MODELVIEW matrix. That matrix acts to position your model relative to the camera. So changes to MODELVIEW are often used to move the camera, move the object or both.</p><p>It then applies PROJECTION as part of the process of projecting your geometry onto the 2d screen. Changes to PROJECTION are commonly used to do things such as change the aspect ratio or the centre of projection of the output image — e.g. if you have a view into your world occupying the entire screen then you probably want different settings than if you have two player split screen.</p><p>The OpenGL stack mechanisms don&#39;t really care about when you start or finish drawing your image. Their state only changes when you explicitly change it.</p><p>So, a common way of doing things for a game looks like this:
</p><div class="source-code"><div class="toolbar"></div><div class="inner"><table width="100%"><tbody><tr><td class="number">1</td><td><span class="k1">void</span> FunctionRunWhenProgramStarts<span class="k2">(</span><span class="k2">)</span></td></tr><tr><td class="number">2</td><td><span class="k2">{</span></td></tr><tr><td class="number">3</td><td>  glMatrixMode<span class="k2">(</span>GL_PROJECTION<span class="k2">)</span><span class="k2">;</span> <span class="c">// signal that I want to work with the projection stack</span></td></tr><tr><td class="number">4</td><td>  glLoadIdentity<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> <span class="c">// make sure that the projection stack doesn't already have anything on it</span></td></tr><tr><td class="number">5</td><td>  gluPerspective<span class="k2">(</span>whatever I want<span class="k2">)</span><span class="k2">;</span> <span class="c">// set up a normal perspective projection</span></td></tr><tr><td class="number">6</td><td>&#160;</td></tr><tr><td class="number">7</td><td>  glMatrixMode<span class="k2">(</span>GL_MODELVIEW<span class="k2">)</span><span class="k2">;</span> <span class="c">// the rest of my app will only change MODELVIEW </span></td></tr><tr><td class="number">8</td><td>  glLoadIdentity<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> <span class="c">// make sure that the modelview stack doesn't already have anything on it</span></td></tr><tr><td class="number">9</td><td><span class="k2">}</span></td></tr><tr><td class="number">10</td><td>&#160;</td></tr><tr><td class="number">11</td><td><span class="k1">void</span> FunctionToDrawAFrame<span class="k2">(</span><span class="k2">)</span></td></tr><tr><td class="number">12</td><td><span class="k2">{</span></td></tr><tr><td class="number">13</td><td>  <span class="c">// modelview is still the active stack, because I never that setting</span></td></tr><tr><td class="number">14</td><td>  glPushMatrix<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> <span class="c">// push current matrix up one, because I'm about to do a bunch of stuff that shouldn't remain active after the end of this function</span></td></tr><tr><td class="number">15</td><td>&#160;</td></tr><tr><td class="number">16</td><td>  <span class="c">/* position camera - whatever code you want, this is just an example */</span></td></tr><tr><td class="number">17</td><td>  glTranslatef<span class="k2">(</span>cameraX, cameraY, cameraZ<span class="k2">)</span><span class="k2">;</span></td></tr><tr><td class="number">18</td><td>  glRotatef<span class="k2">(</span>cameraAngle, <span class="n">0</span>, <span class="n">1</span>, <span class="n">0</span><span class="k2">)</span><span class="k2">;</span></td></tr><tr><td class="number">19</td><td>&#160;</td></tr><tr><td class="number">20</td><td>  <span class="c">/* draw all objects */</span></td></tr><tr><td class="number">21</td><td>  <span class="k1">for</span><span class="k2">(</span>all objects<span class="k2">)</span></td></tr><tr><td class="number">22</td><td>  <span class="k2">{</span></td></tr><tr><td class="number">23</td><td>    glPushMatrix<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> <span class="c">//we don't want each object to move the camera...</span></td></tr><tr><td class="number">24</td><td>&#160;</td></tr><tr><td class="number">25</td><td>      glTranslatef<span class="k2">(</span>objectX, objectY, obectZ<span class="k2">)</span><span class="k2">;</span></td></tr><tr><td class="number">26</td><td>      glRotatef<span class="k2">(</span>objectAngle, <span class="n">0</span>, <span class="n">1</span>, <span class="n">0</span><span class="k2">)</span><span class="k2">;</span></td></tr><tr><td class="number">27</td><td>&#160;</td></tr><tr><td class="number">28</td><td>      DrawObject<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> <span class="c">// whatever method you use to draw your object</span></td></tr><tr><td class="number">29</td><td>&#160;</td></tr><tr><td class="number">30</td><td>    glPopMatrix<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> <span class="c">//restore unaffected camera for next object</span></td></tr><tr><td class="number">31</td><td>  <span class="k2">}</span></td></tr><tr><td class="number">32</td><td>&#160;</td></tr><tr><td class="number">33</td><td>  glPopMatrix<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> <span class="c">// restore view prior to movement by this camera</span></td></tr><tr><td class="number">34</td><td><span class="k2">}</span></td></tr></tbody></table></div></div><p>

The general rule people program to when using OpenGL is &quot;leave everything in the state it was before I did this operation&quot;. The way you do that is to backup the state (in this case, using glPushMatrix), do whatever you have to in order to achieve your operation, then restore the original state (using glPopMatrix).
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Thomas Harte)</author>
		<pubDate>Sun, 03 Feb 2008 19:16:56 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p><a href="http://www.opengl.org/resources/faq/technical/transformations.htm">http://www.opengl.org/resources/faq/technical/transformations.htm</a></p><p>They said:<br />9.020 How do I transform only one object in my scene or give each object its own transform?</p><p>    OpenGL provides matrix stacks specifically for this purpose. In this case, use the ModelView matrix stack.</p><p>    A typical OpenGL application first sets the matrix mode with a call to glMatrixMode(GL_MODELVIEW) and loads a viewing transform, perhaps with a call to gluLookAt().More information is available on gluLookAt().</p><p>    Then the code renders each object in the scene with its own transformation by wrapping the rendering with calls to glPushMatrix() and glPopMatrix(). For example:</p><p>        glPushMatrix(); glRotatef(90., 1., 0., 0.); gluCylinder(quad,1,1,2,36,12); glPopMatrix();</p><p>    The above code renders a cylinder rotated 90 degrees around the X-axis. The ModelView matrix is restored to its previous value after the glPopMatrix() call. Similar call sequences can render subsequent objects in the scene.
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Arthur Kalliokoski)</author>
		<pubDate>Sun, 03 Feb 2008 23:08:07 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>hmmm i still don&#39;t understand why i have to call something like glMatrixMode() or glLoadIdentity before using glPushMatrix/glPopMatrix. atm i only set up the screen coordinates to &quot;allegro-coordinates&quot; through glOrtho(0,640,480,0,-1,1) at the start of my programm and then everything works fine without these function mentioned before. do i really  need to call something like these before?
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Frank Drebin)</author>
		<pubDate>Tue, 05 Feb 2008 17:51:39 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>The clues are in the man pages:
</p><div class="quote_container"><div class="title">glOrtho man page said:</div><div class="quote"><p>
multiply the current matrix by an orthographic matrix
</p></div></div><p>
So, what will your matrix stack look like if you only call glOrtho? The answer is: you don&#39;t know. Because you don&#39;t know what was originally on the stack. It sounds like it&#39;s the identity on your particular, current OpenGL implementation. Is it on mine? Who knows. If you weren&#39;t too lazy to write the 17 extra characters &quot;glLoadIdentity();&quot; then I don&#39;t suppose it would matter much.</p><p>Similarly, what do you think happens next when you pass geometry to OpenGL? It goes through MODELVIEW and then PROJECTION. So what&#39;s the end result? Again - you couldn&#39;t quite be bothered to load the identity matrix to MODELVIEW, so you don&#39;t know. It could easily vary from driver to driver.</p><p>&quot;It works on my computer&quot; is the absolute worst justification for using a particular set of code. If you aren&#39;t willing to program according to the specifications of the API you&#39;re using then don&#39;t be surprised when your program doesn&#39;t work on other people&#39;s computers. Or even necessarily your own, unless you keep everything about your software installation exactly as it is now.
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Thomas Harte)</author>
		<pubDate>Tue, 05 Feb 2008 18:18:11 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>Camera - you&#39;re doing it wrong <img src="http://www.allegro.cc/forums/smileys/tongue.gif" alt=":P" /></p><p><span class="remote-thumbnail"><span class="json">{"name":"photo5av.jpg","src":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/b\/b\/bbee34fd8702e56e2ea7dff8f1cc0aae.jpg","w":500,"h":434,"tn":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/b\/b\/bbee34fd8702e56e2ea7dff8f1cc0aae"}</span><img src="http://www.allegro.cc//djungxnpq2nug.cloudfront.net/image/cache/b/b/bbee34fd8702e56e2ea7dff8f1cc0aae-240.jpg" alt="photo5av.jpg" width="240" height="208" /></span>
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Leniuch)</author>
		<pubDate>Tue, 05 Feb 2008 18:43:38 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>ah ok i think now i got it:<br />so i can&#39;t rely on that these both matrixes are &quot;initiallized&quot; automatically so i have to reset it on my own once through calling
</p><div class="source-code snippet"><div class="inner"><pre>glMatrixMode<span class="k2">(</span>GL_PROJECTION<span class="k2">)</span><span class="k2">;</span>
glLoadIdentity<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span> 
glMatrixMode<span class="k2">(</span>GL_MODELVIEW<span class="k2">)</span><span class="k2">;</span> 
glLoadIdentity<span class="k2">(</span><span class="k2">)</span><span class="k2">;</span>
</pre></div></div><p>
it&#39;s like initializing an integer cause i don&#39;t know what number it actually holds if uninitiallized, right?
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Frank Drebin)</author>
		<pubDate>Tue, 05 Feb 2008 18:48:53 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>I jumped in here a little late.</p><p>An easy way to remember the transformations: think of the Modelview matrix as the world, the Projection matrix as a kaleidoscope/glasses and the Viewport as your visual spectrum (2D screen).</p><div class="quote_container"><div class="title">Quote:</div><div class="quote"><p>
it&#39;s like initializing an integer cause i don&#39;t know what number it actually holds if uninitiallized, right?
</p></div></div><p>
I suppose that you could think of it like that. It adds certainty in the end.
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Archon)</author>
		<pubDate>Tue, 05 Feb 2008 19:50:30 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><p>The OpenGL standard specifies initial values for a number of its variables, specifically:</p><div class="quote_container"><div class="title">OpenGL 2.0 specs said:</div><div class="quote"><p>

MODELVIEW_MATRIX Identity<br />PROJECTION_MATRIX Identity
</p></div></div><p>

So as long as your drivers are not broken, you can rely on it. But since drivers usually are broken, and since you might change your code to modify the matrix elsewhere, I still would agree that calling glLoadIdentity() is a good idea <img src="http://www.allegro.cc/forums/smileys/smiley.gif" alt=":)" />
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Elias)</author>
		<pubDate>Tue, 05 Feb 2008 23:51:09 +0000</pubDate>
	</item>
	<item>
		<description><![CDATA[<div class="mockup v2"><div class="quote_container"><div class="title">Quote:</div><div class="quote"><p>
if i want to rotate two objects with different angles
</p></div></div><p>
and
</p><div class="quote_container"><div class="title">Quote:</div><div class="quote"><p>
hmmm i still don&#39;t understand why i have to call something like glMatrixMode() or glLoadIdentity before using glPushMatrix/glPopMatrix.
</p></div></div><p>
I understood the first quote to mean objects that were created in object space, i.e. you created them at 0,0,0 in your modeler (so you didn&#39;t have to &quot;move&quot; maybe a hundred virtual meters in your 3d modeler to get to it upon file load).  So when you need to &quot;move&quot; that object to the appropriate position in your world you don&#39;t want to move everything else along with it.  Thus, glPushMatrix() and glPopMatrix().</p><p>as for the second quote...<br />Unless you keep very good track of which matrix mode you&#39;re in when you move your objects, using glPushMatrix() will possibly push the wrong stack.  I messed up like this just last week rewriting my text code in glOrtho().  AFTER you&#39;ve pushed your matrix, THEN call glLoadIdentity(), just like you need to initialize local auto variables in C.
</p></div>]]>
		</description>
		<author>no-reply@allegro.cc (Arthur Kalliokoski)</author>
		<pubDate>Wed, 06 Feb 2008 03:02:37 +0000</pubDate>
	</item>
</rss>
