﻿<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>C++博客-OpenGL群23186719</title><link>http://www.cppblog.com/zmj/</link><description /><language>zh-cn</language><lastBuildDate>Sun, 12 Oct 2008 01:04:57 GMT</lastBuildDate><pubDate>Sun, 12 Oct 2008 01:04:57 GMT</pubDate><ttl>60</ttl><item><title>The Theory of Stencil Shadow Volumes </title><link>http://www.cppblog.com/zmj/archive/2008/10/11/63778.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Sat, 11 Oct 2008 15:08:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/10/11/63778.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/63778.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/10/11/63778.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/63778.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/63778.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: http://www.gamedev.net/reference/articles/article1873.aspIntroductionShadows used to be just a patch of darkened texture, usually round in shape, which is projected onto the floor below characters...&nbsp;&nbsp;<a href='http://www.cppblog.com/zmj/archive/2008/10/11/63778.html'>阅读全文</a><img src ="http://www.cppblog.com/zmj/aggbug/63778.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-10-11 23:08 <a href="http://www.cppblog.com/zmj/archive/2008/10/11/63778.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Silhouette edge</title><link>http://www.cppblog.com/zmj/archive/2008/09/26/62827.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Fri, 26 Sep 2008 09:27:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/09/26/62827.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/62827.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/09/26/62827.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/62827.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/62827.html</trackback:ping><description><![CDATA[<p>In computer graphics, a <strong>silhouette edge</strong> on a 3D body projected onto a 2D plane (display plane) is the collection of points whose outwards <em>surface normal is perpendicular to the view vector</em>. Due to discontinities in the surface normal, a silhouette edge is also an edge which separates a front facing face from a back facing face. Without loss of generality, this edge is usually chosen to be the closest one on a face, so that in parallel view this edge corresponds to the same one in a perspective view. Hence, if there is an edge between a front facing face and a side facing face, and another edge between a side facing face and back facing face, the closer one is chosen. The easy example is looking at a cube in the direction where the face normal is colinear with the view vector.</p>
<p>The first type of silhouette edge is sometimes troublesome to handle because it does not necessarily correspond to a physical edge in the CAD model. The reason that this can be an issue is that a programmer might corrupt the original model by introducing the new silhouette edge into the problem. Also, given that the edge strongly depends upon the orientation of the model and view vector, this can introduce numerical instablities into the algorithm (such as when a trick like <a title="Dilution of precision (computer graphics)" href="http://en.wikipedia.org/wiki/Dilution_of_precision_(computer_graphics)"><u><font color=#0000ff>dilution of precision</font></u></a> is considered).</p>
<p><a id=Computation name=Computation></a></p>
<h2><span class=editsection>[<a title="Edit section: Computation" href="http://en.wikipedia.org/w/index.php?title=Silhouette_edge&amp;action=edit&amp;section=1"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>Computation</span></h2>
<p>To determine the silhouette edge of an object, we first have to know the <a title="Plane (mathematics)" href="http://en.wikipedia.org/wiki/Plane_(mathematics)"><u><font color=#0000ff>plane equation</font></u></a> of all faces. Then, by examining the sign of the <em>point-plane distance</em> from the light-source to each face</p>
<dl>
<dd><span class=tex style="DISPLAY: inline-block; FONT-SIZE: 0px; BORDER-LEFT-COLOR: black; BACKGROUND-IMAGE: none; BORDER-BOTTOM-COLOR: black; VERTICAL-ALIGN: middle; BORDER-TOP-COLOR: black; BORDER-RIGHT-COLOR: black"><span style="DISPLAY: inline-block; FILTER: progid:DXImageTransform.Microsoft.AlphaImageLoader(src='http://upload.wikimedia.org/math/0/0/f/00f7c3077410a48d6f91e179734270be.png'); WIDTH: 1px; HEIGHT: 1px"></span></span></dd></dl>
<p>Using this result, we can determine if the face is front- or back facing.</p>
<p>The silhouette edge(s) consist of all <strong>edges separating a front facing face from a back facing face</strong>.</p>
<p><br>A convenient and practical implementation of front/back facing detection is to use the <a class=mw-redirect title="Unit normal" href="http://en.wikipedia.org/wiki/Unit_normal"><u><font color=#0000ff>unit normal</font></u></a> of the plane (which is commonly precomputed for lighting effects anyhow), then simply applying the <a title="Dot product" href="http://en.wikipedia.org/wiki/Dot_product"><u><font color=#0000ff>dot product</font></u></a> of the light position to the plane's unit normal:</p>
<p><br></p>
<dl>
<dd><span class=tex style="DISPLAY: inline-block; FONT-SIZE: 0px; BORDER-LEFT-COLOR: black; BACKGROUND-IMAGE: none; BORDER-BOTTOM-COLOR: black; VERTICAL-ALIGN: middle; BORDER-TOP-COLOR: black; BORDER-RIGHT-COLOR: black"><span style="DISPLAY: inline-block; FILTER: progid:DXImageTransform.Microsoft.AlphaImageLoader(src='http://upload.wikimedia.org/math/5/6/8/5689c91bc2b32ebc1b50626340aba079.png'); WIDTH: 1px; HEIGHT: 1px"></span></span></dd></dl>
<p><br>Note: The <a title="Homogeneous coordinates" href="http://en.wikipedia.org/wiki/Homogeneous_coordinates"><u><font color=#0000ff>homogeneous coordinates</font></u></a>, w and d, are not always needed for this computation.</p>
<p><br></p>
<dl>
<dd><span class=tex style="DISPLAY: inline-block; FONT-SIZE: 0px; BORDER-LEFT-COLOR: black; BACKGROUND-IMAGE: none; BORDER-BOTTOM-COLOR: black; VERTICAL-ALIGN: middle; BORDER-TOP-COLOR: black; BORDER-RIGHT-COLOR: black"><span style="DISPLAY: inline-block; FILTER: progid:DXImageTransform.Microsoft.AlphaImageLoader(src='http://upload.wikimedia.org/math/6/e/6/6e6a97cfe93e9faaad6c8f017b1a8ae4.png'); WIDTH: 1px; HEIGHT: 1px"></span></span></dd></dl>
<p><br>This is also the technique used in the 2002 <a title=SIGGRAPH href="http://en.wikipedia.org/wiki/SIGGRAPH"><u><font color=#0000ff>SIGGRAPH</font></u></a> paper, "Practical and Robust Stenciled Shadow Volumes for Hardware-Accelerated Rendering"</p>
<p><a id=External_links name=External_links></a></p>
<h2><span class=editsection>[<a title="Edit section: External links" href="http://en.wikipedia.org/w/index.php?title=Silhouette_edge&amp;action=edit&amp;section=2"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>External links</span></h2>
<ul>
    <li><a class="external free" title=http://wheger.tripod.com/vhl/vhl.htm href="http://wheger.tripod.com/vhl/vhl.htm" rel=nofollow><u><font color=#0000ff>http://wheger.tripod.com/vhl/vhl.htm</font></u></a> </li>
</ul>
<!--
NewPP limit report
Preprocessor node count: 12/1000000
Post-expand include size: 0/2048000 bytes
Template argument size: 0/2048000 bytes
Expensive parser function count: 0/500
--><!-- Saved in parser cache with key enwiki:pcache:idhash:1654070-0!1!0!default!!en!2 and timestamp 20080922060928 -->
<div class=printfooter>Retrieved from "<a href="http://en.wikipedia.org/wiki/Silhouette_edge"><u><font color=#800080>http://en.wikipedia.org/wiki/Silhouette_edge</font></u></a>"</div>
<img src ="http://www.cppblog.com/zmj/aggbug/62827.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-09-26 17:27 <a href="http://www.cppblog.com/zmj/archive/2008/09/26/62827.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Shadow volume</title><link>http://www.cppblog.com/zmj/archive/2008/09/26/62826.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Fri, 26 Sep 2008 09:24:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/09/26/62826.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/62826.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/09/26/62826.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/62826.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/62826.html</trackback:ping><description><![CDATA[<a href="http://en.wikipedia.org/wiki/Shadow_volume">http://en.wikipedia.org/wiki/Shadow_volume</a><br>
<p><strong>Shadow volumes</strong> are a technique used in <a title="3D computer graphics" href="http://en.wikipedia.org/wiki/3D_computer_graphics"><u><font color=#800080>3D computer graphics</font></u></a> to add shadows to a rendered scene. They were first proposed by <a title="Frank Crow" href="http://en.wikipedia.org/wiki/Frank_Crow"><u><font color=#0000ff>Frank Crow</font></u></a> in <a title=1977 href="http://en.wikipedia.org/wiki/1977"><font color=#0000ff><u>1977</u></font></a><sup class=reference id=cite_ref-0><a title="" href="http://en.wikipedia.org/wiki/Shadow_volume#cite_note-0"><u><font color=#800080>[1]</font></u></a></sup> as the geometry describing the 3D shape of the region occluded from a light source. A shadow volume divides the virtual world in two: areas that are in shadow and areas that are not.</p>
<p>The stencil buffer implementation of shadow volumes is generally considered among the most practical general purpose real-time shadowing techniques utilizing the capabilities of modern 3D graphics hardware. It has been popularized by the <a class=mw-redirect title="Computer game" href="http://en.wikipedia.org/wiki/Computer_game"><u><font color=#0000ff>computer game</font></u></a> <em><a title="Doom 3" href="http://en.wikipedia.org/wiki/Doom_3"><u><font color=#0000ff>Doom 3</font></u></a></em>, and a particular variation of the technique used in this game has become known as <strong>Carmack's Reverse</strong> (see <em><a title="" href="http://en.wikipedia.org/wiki/Shadow_volume#Depth_fail"><u><font color=#800080>depth fail</font></u></a></em> below).</p>
<p>This technique as well as <a title="Shadow mapping" href="http://en.wikipedia.org/wiki/Shadow_mapping"><u><font color=#0000ff>shadow mapping</font></u></a> has become popular real-time shadowing techniques. The main advantage of shadow volumes is that they are accurate to the pixel (though many implementations have a minor self-shadowing problem along the silhouette edge, see <em><a title="Shadow volume" href="http://en.wikipedia.org/wiki/Shadow_volume#Construction"><u><font color=#800080>construction</font></u></a></em> below), whereas the accuracy of a shadow map depends on the texture memory allotted to it as well as the angle at which the shadows are cast (at some angles, the accuracy of a shadow map unavoidably suffers). However, the shadow volume technique requires the creation of shadow geometry, which can be CPU intensive (depending on the implementation). The advantage of shadow mapping is that it is often faster, the reason for which is that shadow volume polygons are often very large in terms of screen space and require a lot of fill time (especially for convex objects), whereas shadow maps do not have this limitation.</p>
<table class=toc id=toc summary=Contents>
    <tbody>
        <tr>
            <td>
            <div id=toctitle>
            <h2>Contents</h2>
            <span class=toctoggle>[<a class=internal id=togglelink href="javascript:toggleToc()"><u><font color=#0000ff>hide</font></u></a>]</span></div>
            <ul>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Shadow_volume#Construction"><u><font color=#800080><span class=tocnumber>1</span> <span class=toctext>Construction</span></font></u></a>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Shadow_volume#Stencil_buffer_implementations"><u><font color=#800080><span class=tocnumber>2</span> <span class=toctext>Stencil buffer implementations</span></font></u></a>
                <ul>
                    <li class=toclevel-2><a href="http://en.wikipedia.org/wiki/Shadow_volume#Depth_pass"><u><font color=#800080><span class=tocnumber>2.1</span> <span class=toctext>Depth pass</span></font></u></a>
                    <li class=toclevel-2><a href="http://en.wikipedia.org/wiki/Shadow_volume#Depth_fail"><u><font color=#800080><span class=tocnumber>2.2</span> <span class=toctext>Depth fail</span></font></u></a>
                    <li class=toclevel-2><a href="http://en.wikipedia.org/wiki/Shadow_volume#Exclusive-Or"><u><font color=#800080><span class=tocnumber>2.3</span> <span class=toctext>Exclusive-Or</span></font></u></a> </li>
                </ul>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Shadow_volume#Optimization"><u><font color=#800080><span class=tocnumber>3</span> <span class=toctext>Optimization</span></font></u></a>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Shadow_volume#See_also"><u><font color=#800080><span class=tocnumber>4</span> <span class=toctext>See also</span></font></u></a>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Shadow_volume#External_links"><u><font color=#800080><span class=tocnumber>5</span> <span class=toctext>External links</span></font></u></a>
                <ul>
                    <li class=toclevel-2><a href="http://en.wikipedia.org/wiki/Shadow_volume#Regarding_depth-fail_patents"><u><font color=#800080><span class=tocnumber>5.1</span> <span class=toctext>Regarding depth-fail patents</span></font></u></a> </li>
                </ul>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Shadow_volume#References"><u><font color=#800080><span class=tocnumber>6</span> <span class=toctext>References</span></font></u></a> </li>
            </ul>
            </td>
        </tr>
    </tbody>
</table>
<script type=text/javascript>
//<![cdata[
if (window.showTocToggle) { var tocShowText = "show"; var tocHideText = "hide"; showTocToggle(); }
//]]&gt;
</script>
<p><a id=Construction name=Construction></a></p>
<h2><span class=editsection>[<a title="Edit section: Construction" href="http://en.wikipedia.org/w/index.php?title=Shadow_volume&amp;action=edit&amp;section=1"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>Construction</span></h2>
<p>In order to construct a shadow volume, project a ray from the light through each vertex in the shadow casting object to some point (generally at infinity). These projections will together form a volume; any point inside that volume is in shadow, everything outside is lit by the light.</p>
<p>For a polygonal model, the volume is usually formed by classifying each face in the model as either facing toward the light source or facing away from the light source. The set of all edges that connect a toward-face to an away-face form the <em>silhouette</em> with respect to the light source. The edges forming the silhouette are extruded away from the light to construct the faces of the shadow volume. This volume must extend over the range of the entire visible scene; often the dimensions of the shadow volume are extended to infinity to accomplish this (see <em><a title="Shadow volume" href="http://en.wikipedia.org/wiki/Shadow_volume#Optimization"><u><font color=#800080>optimization</font></u></a></em> below.) To form a closed volume, the front and back end of this extrusion must be covered. These coverings are called "caps". Depending on the method used for the shadow volume, the front end may be covered by the object itself, and the rear end may sometimes be omitted (see <em><a title="Shadow volume" href="http://en.wikipedia.org/wiki/Shadow_volume#depth_pass"><u><font color=#800080>depth pass</font></u></a></em> below).</p>
<p>There is also a problem with the shadow where the faces along the silhouette edge are relatively shallow. In this case, the shadow an object casts on itself will be sharp, revealing its polygonal facets, whereas the usual lighting model will have a gradual change in the lighting along the facet. This leaves a rough shadow artifact near the silhouette edge which is difficult to correct. Increasing the polygonal density will minimize the problem, but not eliminate it. If the front of the shadow volume is capped, the entire shadow volume may be offset slightly away from the light to remove any shadow self-intersections within the offset distance of the silhouette edge (this solution is more commonly used in <a title="Shadow mapping" href="http://en.wikipedia.org/wiki/Shadow_mapping"><u><font color=#0000ff>shadow mapping</font></u></a>).</p>
<p>The basic steps for forming a shadow volume are:</p>
<ol>
    <li>Find all <a title="Silhouette edge" href="http://en.wikipedia.org/wiki/Silhouette_edge"><u><font color=#0000ff>silhouette edges</font></u></a> (edges which separate front-facing faces from back-facing faces)
    <li>Extend all silhouette edges in the direction away from the light-source
    <li>Add a <em>front-cap</em> and/or <em>back-cap</em> to each surface to form a closed volume (may not be necessary, depending on the implementation used) </li>
</ol>
<div class=center>
<div class="thumb tnone">
<div class=thumbinner style="WIDTH: 502px"><a class=image title="Illustration of shadow volumes. The image above at left shows a scene shadowed using shadow volumes. At right, the shadow volumes are shown in wireframe. Note how the shadows form a large conical area pointing away from the light source (the bright white point)." href="http://en.wikipedia.org/wiki/Image:Shadow_volume_illustration.png"><span class=thumbimage style="BORDER-RIGHT: #ccc 1px solid; BORDER-TOP: #ccc 1px solid; DISPLAY: inline-block; FONT-SIZE: 0px; BACKGROUND-IMAGE: none; VERTICAL-ALIGN: middle; BORDER-LEFT: #ccc 1px solid; CURSOR: hand; BORDER-BOTTOM: #ccc 1px solid"><span style="DISPLAY: inline-block; FILTER: progid:DXImageTransform.Microsoft.AlphaImageLoader(src='http://upload.wikimedia.org/wikipedia/commons/thumb/a/af/Shadow_volume_illustration.png/500px-Shadow_volume_illustration.png'); WIDTH: 1px; HEIGHT: 1px"></span></span></a>
<div class=thumbcaption>
<div class=magnify><a class=internal title=Enlarge href="http://en.wikipedia.org/wiki/Image:Shadow_volume_illustration.png"><span class="" style="BORDER-TOP-WIDTH: 2px; DISPLAY: inline-block; BORDER-LEFT-WIDTH: 2px; FONT-SIZE: 0px; BORDER-LEFT-COLOR: #0000ff; BACKGROUND-IMAGE: none; BORDER-BOTTOM-WIDTH: 2px; BORDER-BOTTOM-COLOR: #0000ff; VERTICAL-ALIGN: middle; CURSOR: hand; BORDER-TOP-COLOR: #0000ff; BORDER-RIGHT-WIDTH: 2px; BORDER-RIGHT-COLOR: #0000ff"><span style="DISPLAY: inline-block; FILTER: progid:DXImageTransform.Microsoft.AlphaImageLoader(src='http://en.wikipedia.org/skins-1.5/common/images/magnify-clip.png'); WIDTH: 1px; HEIGHT: 1px"></span></span></a></div>
Illustration of shadow volumes. The image above at left shows a scene shadowed using shadow volumes. At right, the shadow volumes are shown in wireframe. Note how the shadows form a large conical area pointing away from the light source (the bright white point).</div>
</div>
</div>
</div>
<p><a id=Stencil_buffer_implementations name=Stencil_buffer_implementations></a></p>
<h2><span class=editsection>[<a title="Edit section: Stencil buffer implementations" href="http://en.wikipedia.org/w/index.php?title=Shadow_volume&amp;action=edit&amp;section=2"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>Stencil buffer implementations</span></h2>
<p>After Crow, <a class=new title="Tim Heidmann (page does not exist)" href="http://en.wikipedia.org/w/index.php?title=Tim_Heidmann&amp;action=edit&amp;redlink=1"><u><font color=#0000ff>Tim Heidmann</font></u></a> showed in <a title=1991 href="http://en.wikipedia.org/wiki/1991"><u><font color=#0000ff>1991</font></u></a> how to use the <a title="Stencil buffer" href="http://en.wikipedia.org/wiki/Stencil_buffer"><u><font color=#800080>stencil buffer</font></u></a> to render shadows with shadow volumes quickly enough for use in real time applications. There are three common variations to this technique, <strong>depth pass</strong>, <strong>depth fail</strong>, and <strong>exclusive-or</strong>, but all of them use the same process:</p>
<ol>
    <li>Render the scene as if it were completely in shadow.
    <li>For each light source:
    <ol>
        <li>Using the depth information from that scene, construct a mask in the stencil buffer that has holes only where the visible surface is not in shadow.
        <li>Render the scene again as if it were completely lit, using the stencil buffer to mask the shadowed areas. Use additive blending to add this render to the scene. </li>
    </ol>
    </li>
</ol>
<p>The difference between these three methods occurs in the generation of the mask in the second step. Some involve two passes, and some only one; some require less precision in the stencil buffer. (These algorithms function well in both <a title=OpenGL href="http://en.wikipedia.org/wiki/OpenGL"><u><font color=#0000ff>OpenGL</font></u></a> and <a title=Direct3D href="http://en.wikipedia.org/wiki/Direct3D"><u><font color=#0000ff>Direct3D</font></u></a>.)</p>
<p>Shadow volumes tend to cover large portions of the visible scene, and as a result consume valuable rasterization time (fill time) on 3D graphics hardware. This problem is compounded by the complexity of the shadow casting objects, as each object can cast its own shadow volume of any potential size onscreen. See <em><a title="Shadow volume" href="http://en.wikipedia.org/wiki/Shadow_volume#Optimization"><u><font color=#800080>optimization</font></u></a></em> below for a discussion of techniques used to combat the fill time problem.</p>
<p><a id=Depth_pass name=Depth_pass></a></p>
<h3><span class=editsection>[<a title="Edit section: Depth pass" href="http://en.wikipedia.org/w/index.php?title=Shadow_volume&amp;action=edit&amp;section=3"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>Depth pass</span></h3>
<p>Heidmann proposed that if the front surfaces and back surfaces of the shadows were rendered in separate passes, the number of front faces and back faces in front of an object can be counted using the stencil buffer. If an object's surface is in shadow, there will be more front facing shadow surfaces between it and the eye than back facing shadow surfaces. If their numbers are equal, however, the surface of the object is not in shadow. The generation of the stencil mask works as follows:</p>
<ol>
    <li>Disable writes to the <a title=Z-buffering href="http://en.wikipedia.org/wiki/Z-buffering"><u><font color=#0000ff>depth</font></u></a> and colour buffers.
    <li>Use back-face culling.
    <li>Set the stencil operation to increment on depth pass (only count shadows in front of the object).
    <li>Render the shadow volumes (because of culling, only their front faces are rendered).
    <li>Use front-face culling.
    <li>Set the stencil operation to decrement on depth pass.
    <li>Render the shadow volumes (only their back faces are rendered). </li>
</ol>
<p>After this is accomplished, all lit surfaces will correspond to a 0 in the stencil buffer, where the numbers of front and back surfaces of all shadow volumes between the eye and that surface are equal.</p>
<p>This approach has problems when the eye itself is inside a shadow volume (for example, when the light source moves behind an object). From this point of view, the eye sees the back face of this shadow volume before anything else, and this adds a &#8722;1 bias to the entire stencil buffer, effectively inverting the shadows. This can be remedied by adding a "cap" surface to the front of the shadow volume facing the eye, such as at the front <a class=mw-redirect title="Clipping plane" href="http://en.wikipedia.org/wiki/Clipping_plane"><u><font color=#0000ff>clipping plane</font></u></a>. There is another situation where the eye may be in the shadow of a volume cast by an object behind the camera, which also has to be capped somehow to prevent a similar problem. In most common implementations, because properly capping for depth-pass can be difficult to accomplish, the depth-fail method (see below) may be licensed for these special situations. Alternatively one can give the stencil buffer a +1 bias for every shadow volume the camera is inside, though doing the detection can be slow.</p>
<p>There is another potential problem if the stencil buffer does not have enough bits to accommodate the number of shadows visible between the eye and the object surface, because it uses <a title="Saturation arithmetic" href="http://en.wikipedia.org/wiki/Saturation_arithmetic"><u><font color=#0000ff>saturation arithmetic</font></u></a>. (If they used <a title="Arithmetic overflow" href="http://en.wikipedia.org/wiki/Arithmetic_overflow"><u><font color=#0000ff>arithmetic overflow</font></u></a> instead, the problem would be insignificant.)</p>
<p>Depth pass testing is also known as <strong>z-pass</strong> testing, as the depth buffer is often referred to as the z-buffer.</p>
<p><a id=Depth_fail name=Depth_fail></a></p>
<h3><span class=editsection>[<a title="Edit section: Depth fail" href="http://en.wikipedia.org/w/index.php?title=Shadow_volume&amp;action=edit&amp;section=4"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>Depth fail</span></h3>
<p>Around <a title=2000 href="http://en.wikipedia.org/wiki/2000"><u><font color=#0000ff>2000</font></u></a>, several people discovered that Heidmann's method can be made to work for all camera positions by reversing the depth. Instead of counting the shadow surfaces in front of the object's surface, the surfaces behind it can be counted just as easily, with the same end result. This solves the problem of the eye being in shadow, since shadow volumes between the eye and the object are not counted, but introduces the condition that the rear end of the shadow volume must be capped, or shadows will end up missing where the volume points backward to infinity.</p>
<ol>
    <li>Disable writes to the depth and colour buffers.
    <li>Use front-face culling.
    <li>Set the stencil operation to increment on depth fail (only count shadows behind the object).
    <li>Render the shadow volumes.
    <li>Use back-face culling.
    <li>Set the stencil operation to decrement on depth fail.
    <li>Render the shadow volumes. </li>
</ol>
<p>The depth fail method has the same considerations regarding the stencil buffer's precision as the depth pass method. Also, similar to depth pass, it is sometimes referred to as the <strong>z-fail</strong> method.</p>
<p>William Bilodeau and Michael Songy discovered this technique in October 1998, and presented the technique at Creativity, a Creative Labs developer's conference, in 1999<a class="external autonumber" title=http://www.gamedev.net/reference/articles/article1873.asp href="http://www.gamedev.net/reference/articles/article1873.asp" rel=nofollow><u><font color=#0000ff>[1]</font></u></a>. <a class=new title="Sim Dietrich (page does not exist)" href="http://en.wikipedia.org/w/index.php?title=Sim_Dietrich&amp;action=edit&amp;redlink=1"><u><font color=#0000ff>Sim Dietrich</font></u></a> presented this technique at a Creative Labs developer's forum in 1999 <a class="external autonumber" title=http://techreport.com/onearticle.x/7113 href="http://techreport.com/onearticle.x/7113" rel=nofollow><u><font color=#0000ff>[2]</font></u></a>. A few months later, William Bilodeau and Michael Songy filed a <a title="Software patent" href="http://en.wikipedia.org/wiki/Software_patent"><u><font color=#0000ff>US patent application</font></u></a> for the technique the same year, <a class="external text" title=http://v3.espacenet.com/textdoc?DB=EPODOC&amp;IDX=US6384822 href="http://v3.espacenet.com/textdoc?DB=EPODOC&amp;IDX=US6384822" rel=nofollow><u><font color=#0000ff>US&nbsp;patent&nbsp;6384822</font></u></a>, entitled "Method for rendering shadows using a shadow volume and a stencil buffer" issued in <a title=2002 href="http://en.wikipedia.org/wiki/2002"><u><font color=#0000ff>2002</font></u></a>. <a title="John D. Carmack" href="http://en.wikipedia.org/wiki/John_D._Carmack"><u><font color=#0000ff>John Carmack</font></u></a> of <a title="Id Software" href="http://en.wikipedia.org/wiki/Id_Software"><u><font color=#0000ff>id Software</font></u></a> independently discovered the algorithm in 2000 during the development of <em><a title="Doom 3" href="http://en.wikipedia.org/wiki/Doom_3"><u><font color=#0000ff>Doom 3</font></u></a></em> <a class="external autonumber" title=http://developer.nvidia.com/object/robust_shadow_volumes.html href="http://developer.nvidia.com/object/robust_shadow_volumes.html" rel=nofollow><u><font color=#0000ff>[3]</font></u></a>. Since he advertised the technique to the larger public, it is often known as <strong>Carmack's Reverse</strong>.</p>
<p>Bilodeau and Songy assigned their patent ownership rights to <a title="Creative Technology" href="http://en.wikipedia.org/wiki/Creative_Technology"><u><font color=#0000ff>Creative Labs</font></u></a>. Creative Labs, in turn, granted id Software a license to use the invention free of charge in exchange for future support of <a title="Environmental audio extensions" href="http://en.wikipedia.org/wiki/Environmental_audio_extensions"><u><font color=#0000ff>EAX</font></u></a> technology. <a class="external autonumber" title=http://www.theinquirer.net/default.aspx?article=17445 href="http://www.theinquirer.net/default.aspx?article=17445" rel=nofollow><u><font color=#0000ff>[4]</font></u></a></p>
<p><a id=Exclusive-Or name=Exclusive-Or><u><font color=#0000ff></font></u></a></p>
<h3><span class=editsection>[<a title="Edit section: Exclusive-Or" href="http://en.wikipedia.org/w/index.php?title=Shadow_volume&amp;action=edit&amp;section=5"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>Exclusive-Or</span></h3>
<p>Either of the above types may be approximated with an <a class=mw-redirect title="Exclusive disjunction" href="http://en.wikipedia.org/wiki/Exclusive_disjunction"><u><font color=#0000ff>Exclusive-Or</font></u></a> variation, which does not deal properly with intersecting shadow volumes, but saves one rendering pass (if not fill time), and only requires a 1-bit stencil buffer. The following steps are for the depth pass version:</p>
<ol>
    <li>Disable writes to the depth and colour buffers.
    <li>Set the stencil operation to XOR on depth pass (flip on any shadow surface).
    <li>Render the shadow volumes. </li>
</ol>
<p><a id=Optimization name=Optimization></a></p>
<h2><span class=editsection>[<a title="Edit section: Optimization" href="http://en.wikipedia.org/w/index.php?title=Shadow_volume&amp;action=edit&amp;section=6"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>Optimization</span></h2>
<ul>
    <li>One method of speeding up the shadow volume geometry calculations is to utilize existing parts of the rendering pipeline to do some of the calculation. For instance, by using <a title="Homogeneous coordinates" href="http://en.wikipedia.org/wiki/Homogeneous_coordinates"><u><font color=#0000ff>homogeneous coordinates</font></u></a>, the <em>w</em>-coordinate may be set to zero to extend a point to infinity. This should be accompanied by a <a title="Viewing frustum" href="http://en.wikipedia.org/wiki/Viewing_frustum"><u><font color=#0000ff>viewing frustum</font></u></a> that has a far clipping plane that extends to infinity in order to accommodate those points, accomplished by using a specialized projection matrix. This technique reduces the accuracy of the depth buffer slightly, but the difference is usually negligible. Please see SIGGRAPH 2002 paper <strong>Practical and Robust Stenciled Shadow Volumes for Hardware-Accelerated Rendering</strong>, C. Everitt and M. Kilgard, for a detailed implementation. </li>
</ul>
<ul>
    <li>Rasterization time of the shadow volumes can be reduced by using an in-hardware scissor test to limit the shadows to a specific onscreen rectangle. </li>
</ul>
<ul>
    <li><a class=mw-redirect title=NVIDIA href="http://en.wikipedia.org/wiki/NVIDIA"><u><font color=#0000ff>NVIDIA</font></u></a> has implemented a hardware capability called the <em>depth bounds test</em> that is designed to remove parts of shadow volumes that do not affect the visible scene. (This has been available since the <a title=GeForce href="http://en.wikipedia.org/wiki/GeForce"><u><font color=#0000ff>GeForce</font></u></a> FX 5900 model.) A discussion of this capability and its use with shadow volumes was presented at the <a title="Game Developers Conference" href="http://en.wikipedia.org/wiki/Game_Developers_Conference"><u><font color=#0000ff>Game Developers Conference</font></u></a> in 2005. <a class="external autonumber" title=http://www.terathon.com/gdc_lengyel.ppt href="http://www.terathon.com/gdc_lengyel.ppt" rel=nofollow><u><font color=#0000ff>[5]</font></u></a> </li>
</ul>
<ul>
    <li>Since the depth-fail method only offers an advantage over depth-pass in the special case where the eye is within a shadow volume, it is preferable to check for this case, and use depth-pass wherever possible. This avoids both the unnecessary back-capping (and the associated rasterization) for cases where depth-fail is unnecessary, as well as the problem of appropriately front-capping for special cases of depth-pass. </li>
</ul>
<p><a id=See_also name=See_also></a></p>
<h2><span class=editsection>[<a title="Edit section: See also" href="http://en.wikipedia.org/w/index.php?title=Shadow_volume&amp;action=edit&amp;section=7"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>See also</span></h2>
<ul>
    <li><a title="Silhouette edge" href="http://en.wikipedia.org/wiki/Silhouette_edge"><u><font color=#0000ff>Silhouette edge</font></u></a>
    <li><a title="Shadow mapping" href="http://en.wikipedia.org/wiki/Shadow_mapping"><u><font color=#0000ff>Shadow mapping</font></u></a>, an alternative shadowing algorithm
    <li><a title="Stencil buffer" href="http://en.wikipedia.org/wiki/Stencil_buffer"><u><font color=#800080>Stencil buffer</font></u></a>
    <li><a title=Z-buffering href="http://en.wikipedia.org/wiki/Z-buffering"><u><font color=#0000ff>Depth buffer</font></u></a>
    <li><a title="List of software patents" href="http://en.wikipedia.org/wiki/List_of_software_patents"><u><font color=#0000ff>List of software patents</font></u></a> </li>
</ul>
<p><a id=External_links name=External_links></a></p>
<h2><span class=editsection>[<a title="Edit section: External links" href="http://en.wikipedia.org/w/index.php?title=Shadow_volume&amp;action=edit&amp;section=8"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>External links</span></h2>
<ul>
    <li><a class="external text" title=http://www.gamedev.net/reference/articles/article1873.asp href="http://www.gamedev.net/reference/articles/article1873.asp" rel=nofollow><u><font color=#0000ff>The Theory of Stencil Shadow Volumes</font></u></a>
    <li><a class="external text" title=http://www.gamasutra.com/features/20021011/lengyel_01.htm href="http://www.gamasutra.com/features/20021011/lengyel_01.htm" rel=nofollow><u><font color=#0000ff>The Mechanics of Robust Stencil Shadows</font></u></a>
    <li><a class="external text" title=http://www.devmaster.net/articles/shadow_volumes href="http://www.devmaster.net/articles/shadow_volumes" rel=nofollow><u><font color=#0000ff>An Introduction to Stencil Shadow Volumes</font></u></a>
    <li><a class="external text" title=http://www.devmaster.net/articles/shadow_techniques href="http://www.devmaster.net/articles/shadow_techniques" rel=nofollow><u><font color=#0000ff>Shadow Mapping and Shadow Volumes</font></u></a>
    <li><a class="external text" title=http://www.3ddrome.com/articles/shadowvolumes.php href="http://www.3ddrome.com/articles/shadowvolumes.php" rel=nofollow><u><font color=#0000ff>Stenciled Shadow Volumes in OpenGL</font></u></a>
    <li><a class="external text" title=http://www.gamedev.net/reference/articles/article2036.asp href="http://www.gamedev.net/reference/articles/article2036.asp" rel=nofollow><u><font color=#0000ff>Volume shadow tutorial</font></u></a>
    <li><a class="external text" title=http://developer.nvidia.com/object/fast_shadow_volumes.html href="http://developer.nvidia.com/object/fast_shadow_volumes.html" rel=nofollow><u><font color=#0000ff>Fast shadow volumes</font></u></a> at NVIDIA
    <li><a class="external text" title=http://developer.nvidia.com/object/robust_shadow_volumes.html href="http://developer.nvidia.com/object/robust_shadow_volumes.html" rel=nofollow><u><font color=#0000ff>Robust shadow volumes</font></u></a> at NVIDIA
    <li><a class="external text" title=http://www.terathon.com/gdc_lengyel.ppt href="http://www.terathon.com/gdc_lengyel.ppt" rel=nofollow><u><font color=#0000ff>Advanced Stencil Shadow and Penumbral Wedge Rendering</font></u></a> </li>
</ul>
<p><a id=Regarding_depth-fail_patents name=Regarding_depth-fail_patents></a></p>
<h3><span class=editsection>[<a title="Edit section: Regarding depth-fail patents" href="http://en.wikipedia.org/w/index.php?title=Shadow_volume&amp;action=edit&amp;section=9"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>Regarding depth-fail patents</span></h3>
<ul>
    <li>"<a class="external text" title=http://games.slashdot.org/games/04/07/28/1529222.shtml href="http://games.slashdot.org/games/04/07/28/1529222.shtml" rel=nofollow><u><font color=#0000ff>Creative Pressures id Software With Patents</font></u></a>". <em><a title=Slashdot href="http://en.wikipedia.org/wiki/Slashdot"><u><font color=#0000ff>Slashdot</font></u></a></em> (<a title="July 28" href="http://en.wikipedia.org/wiki/July_28"><u><font color=#0000ff>July 28</font></u></a>, <a title=2004 href="http://en.wikipedia.org/wiki/2004"><u><font color=#0000ff>2004</font></u></a>). Retrieved on <a title=2006 href="http://en.wikipedia.org/wiki/2006"><u><font color=#0000ff>2006</font></u></a>-<a title="May 16" href="http://en.wikipedia.org/wiki/May_16"><u><font color=#0000ff>05-16</font></u></a>.
    <li>"<a class="external text" title=http://techreport.com/onearticle.x/7113 href="http://techreport.com/onearticle.x/7113" rel=nofollow><u><font color=#0000ff>Creative patents Carmack's reverse</font></u></a>". <em><a title="The Tech Report" href="http://en.wikipedia.org/wiki/The_Tech_Report"><u><font color=#0000ff>The Tech Report</font></u></a></em> (<a title="July 29" href="http://en.wikipedia.org/wiki/July_29"><u><font color=#0000ff>July 29</font></u></a>, <a title=2004 href="http://en.wikipedia.org/wiki/2004"><u><font color=#0000ff>2004</font></u></a>). Retrieved on <a title=2006 href="http://en.wikipedia.org/wiki/2006"><u><font color=#0000ff>2006</font></u></a>-<a title="May 16" href="http://en.wikipedia.org/wiki/May_16"><u><font color=#0000ff>05-16</font></u></a>.
    <li>"<a class="external text" title=http://www.theinquirer.net/?article=17525 href="http://www.theinquirer.net/?article=17525" rel=nofollow><u><font color=#0000ff>Creative gives background to Doom III shadow story</font></u></a>". <em><a title="The Inquirer" href="http://en.wikipedia.org/wiki/The_Inquirer"><u><font color=#0000ff>The Inquirer</font></u></a></em> (<a title="July 29" href="http://en.wikipedia.org/wiki/July_29"><u><font color=#0000ff>July 29</font></u></a>, <a title=2004 href="http://en.wikipedia.org/wiki/2004"><u><font color=#0000ff>2004</font></u></a>). Retrieved on <a title=2006 href="http://en.wikipedia.org/wiki/2006"><u><font color=#0000ff>2006</font></u></a>-<a title="May 16" href="http://en.wikipedia.org/wiki/May_16"><u><font color=#0000ff>05-16</font></u></a>. </li>
</ul>
<p><a id=References name=References></a></p>
<h2><span class=editsection>[<a title="Edit section: References" href="http://en.wikipedia.org/w/index.php?title=Shadow_volume&amp;action=edit&amp;section=10"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>References</span></h2>
<div class=references-small>
<ol class=references>
    <li id=cite_note-0><strong><a title="" href="http://en.wikipedia.org/wiki/Shadow_volume#cite_ref-0"><u><font color=#800080>^</font></u></a></strong> Crow, Franklin C: "Shadow Algorithms for Computer Graphics", <em>Computer Graphics (SIGGRAPH '77 Proceedings)</em>, vol. 11, no. 2, 242-248. </li>
</ol>
</div>
<!--
NewPP limit report
Preprocessor node count: 344/1000000
Post-expand include size: 2340/2048000 bytes
Template argument size: 1270/2048000 bytes
Expensive parser function count: 0/500
--><!-- Saved in parser cache with key enwiki:pcache:idhash:401494-0!1!0!default!!en!2 and timestamp 20080920181346 -->
<div class=printfooter>Retrieved from "<a href="http://en.wikipedia.org/wiki/Shadow_volume"><u><font color=#800080>http://en.wikipedia.org/wiki/Shadow_volume</font></u></a>"</div>
<img src ="http://www.cppblog.com/zmj/aggbug/62826.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-09-26 17:24 <a href="http://www.cppblog.com/zmj/archive/2008/09/26/62826.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>AutoCAD History Timeline</title><link>http://www.cppblog.com/zmj/archive/2008/09/19/62272.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Fri, 19 Sep 2008 06:04:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/09/19/62272.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/62272.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/09/19/62272.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/62272.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/62272.html</trackback:ping><description><![CDATA[<a href="http://betaprograms.autodesk.com/history/autocad_release_history.htm">http://betaprograms.autodesk.com/history/autocad_release_history.htm</a><br>
<p>This unofficial AutoCAD history site is a service to fellow users and trivia aficionados. <br><br>This site includes detailed command and system variables that have changed with each release and even some screen shots of old release material.</p>
<p><img height=205 alt="autocad timeline" src="http://betaprograms.autodesk.com/history/images/AutoCAD-Timeline%202008%20(Small).jpg" width=640></p>
<p>Regards,<br>Shaan Hurley<br>shaan.hurley@autodesk.com </p>
<p>AutoCAD DWG Version History by Release for the past 20+ years <br>The first six bytes of a DWG file identify its version. In a DXF file, the AutoCAD version number is specified in the header section. The DXF system variable is $ACADVER. </p>
<table width="50%" align=center border=0>
    <tbody>
        <tr>
            <td>AC1021</td>
            <td>AutoCAD 2007/2008</td>
        </tr>
        <tr>
            <td>AC1018</td>
            <td>AutoCAD 2004/2005/2006</td>
        </tr>
        <tr>
            <td>AC1015</td>
            <td>AutoCAD 2000/2000i/2002</td>
        </tr>
        <tr>
            <td>AC1014</td>
            <td>Release 14</td>
        </tr>
        <tr>
            <td>AC1012 </td>
            <td>Release 13</td>
        </tr>
        <tr>
            <td>AC1009</td>
            <td>Release 11/12</td>
        </tr>
        <tr>
            <td>AC1006 </td>
            <td>Release 10</td>
        </tr>
        <tr>
            <td>AC1004 </td>
            <td>Release 9</td>
        </tr>
        <tr>
            <td>AC1003 </td>
            <td>Version 2.60</td>
        </tr>
        <tr>
            <td>AC1002</td>
            <td>Version 2.50</td>
        </tr>
        <tr>
            <td>AC1001</td>
            <td>Version 2.22</td>
        </tr>
        <tr>
            <td>AC2.22 </td>
            <td>Version 2.22</td>
        </tr>
        <tr>
            <td>AC2.21</td>
            <td>Version 2.21</td>
        </tr>
        <tr>
            <td>AC2.10</td>
            <td>Version 2.10</td>
        </tr>
        <tr>
            <td>AC1.50</td>
            <td>Version 2.05</td>
        </tr>
        <tr>
            <td>AC1.40 </td>
            <td>Version 1.40</td>
        </tr>
        <tr>
            <td>AC1.2</td>
            <td>Version 1.2</td>
        </tr>
        <tr>
            <td>MC0.0</td>
            <td>Version 1.0 </td>
        </tr>
    </tbody>
</table>
<p>AutoCAD 2008 can read DWG files back from AutoCAD version 2.0 released in 1984. <br></p>
<img src ="http://www.cppblog.com/zmj/aggbug/62272.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-09-19 14:04 <a href="http://www.cppblog.com/zmj/archive/2008/09/19/62272.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>DXF:drawing interchange and file formats</title><link>http://www.cppblog.com/zmj/archive/2008/09/18/62204.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Thu, 18 Sep 2008 10:23:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/09/18/62204.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/62204.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/09/18/62204.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/62204.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/62204.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: http://www.moon-soft.com/program/FORMAT/graphics/dxf.htmdrawing interchange and fileformats                                    [ this file is an excerpt from the autocad release 10 r...&nbsp;&nbsp;<a href='http://www.cppblog.com/zmj/archive/2008/09/18/62204.html'>阅读全文</a><img src ="http://www.cppblog.com/zmj/aggbug/62204.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-09-18 18:23 <a href="http://www.cppblog.com/zmj/archive/2008/09/18/62204.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Quaternion 四元数</title><link>http://www.cppblog.com/zmj/archive/2008/09/18/62180.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Thu, 18 Sep 2008 07:56:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/09/18/62180.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/62180.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/09/18/62180.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/62180.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/62180.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: QuaternionFrom Wikipedia, the free encyclopediaJump to: navigation, searchThis page describes quaternions in mathematics. For other uses of this word, see quaternion (disambiguation)....&nbsp;&nbsp;<a href='http://www.cppblog.com/zmj/archive/2008/09/18/62180.html'>阅读全文</a><img src ="http://www.cppblog.com/zmj/aggbug/62180.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-09-18 15:56 <a href="http://www.cppblog.com/zmj/archive/2008/09/18/62180.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>OpenGL Vertex Buffer Object (VBO)</title><link>http://www.cppblog.com/zmj/archive/2008/09/09/61420.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Tue, 09 Sep 2008 13:59:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/09/09/61420.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/61420.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/09/09/61420.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/61420.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/61420.html</trackback:ping><description><![CDATA[<h1><a href="http://www.songho.ca/opengl/gl_vbo.html">http://www.songho.ca/opengl/gl_vbo.html</a></h1>
<h1>OpenGL Vertex Buffer Object (VBO)</h1>
<p><strong>Related Topics:</strong> <a href="http://www.songho.ca/opengl/gl_vertexarray.html">Vertex Array</a>, <a href="http://www.songho.ca/opengl/gl_displaylist.html">Display List</a>, <a href="http://www.songho.ca/opengl/gl_pbo.html">Pixel Buffer Object</a> <br><strong>Download:</strong> <a href="http://www.songho.ca/opengl/files/vbo.zip">vbo.zip</a>, <a href="http://www.songho.ca/opengl/files/vboSimple.zip">vboSimple.zip</a> </p>
<ul>
    <li><a href="http://www.songho.ca/opengl/gl_vbo.html#create">Creating VBO</a>
    <li><a href="http://www.songho.ca/opengl/gl_vbo.html#draw">Drawing VBO</a>
    <li><a href="http://www.songho.ca/opengl/gl_vbo.html#update">Updating VBO</a>
    <li><a href="http://www.songho.ca/opengl/gl_vbo.html#example">Example</a> </li>
</ul>
<p><strong>GL_ARB_vertex_buffer_object</strong> extension is intended to enhance the performance of OpenGL by providing the benefits of <a href="http://www.songho.ca/opengl/gl_vertexarray.html">vertex array</a> and <a href="http://www.songho.ca/opengl/gl_displaylist.html">display list</a>, while avoiding downsides of their implementations. Vertex buffer object (VBO) allows vertex array data to be stored in high-performance graphics memory on the server side and promotes efficient data transfer. If the buffer object is used to store pixel data, it is called <a href="http://www.songho.ca/opengl/gl_pbo.html">Pixel Buffer Object (PBO)</a>. </p>
<p>Using vertex array can reduce the number of function calls and redundant usage of the shared vertices. However, the disadvantage of vertex array is that vertex array functions are in the client state and the data in the arrays must be re-sent to the server each time when it is referenced. </p>
<p>On the other hand, display list is server side function, so it does not suffer from overhead of data transfer. But, once a display list is compiled, the data in the display list cannot be modified. </p>
<p>Vertex buffer object (VBO) creates <em>"buffer objects"</em> for vertex attributes in high-performance memory on the server side and provides same access functions to reference the arrays, which are used in vertex arrays, such as glVertexPointer(), glNormalPointer(), glTexCoordPointer(), etc. </p>
<p>The memory manager in vertex buffer object will put the buffer objects into the best place of memory based on user's hints: <em>"target"</em> and <em>"usage"</em> mode. Therefore, the memory manager can optimize the buffers by balancing between 3 kinds of memory: system, AGP and video memory. </p>
<p>Unlike display lists, the data in vertex buffer object can be read and updated by mapping the buffer into client's memory space. </p>
<p>Another important advantage of VBO is sharing the buffer objects with many clients, like display lists and textures. Since VBO is on the server's side, multiple clients will be able to access the same buffer with the corresponding identifier. </p>
<h3 id=create>Creating VBO</h3>
<p>Creating a VBO requires 3 steps; </p>
<ol>
    <li>Generate a new buffer object with <strong>glGenBuffersARB()</strong>.
    <li>Bind the buffer object with <strong>glBindBufferARB()</strong>.
    <li>Copy vertex data to the buffer object with <strong>glBufferDataARB()</strong>. </li>
</ol>
<h4>glGenBuffersARB()</h4>
<p style="MARGIN-LEFT: 30px">glGenBuffersARB() creates buffer objects and returns the identifiers of the buffer objects. It requires 2 parameters: the first one is the number of buffer objects to create, and the second parameter is the address of a GLuint variable or array to store a single ID or multiple IDs. </p>
<div class=code>void glGenBuffersARB(GLsizei n, GLuint* ids)</div>
<h4>glBindBufferARB()</h4>
<p style="MARGIN-LEFT: 30px">Once the buffer object has been created, we need to hook the buffer object with the corresponding ID before using the buffer object. glBindBufferARB() takes 2 parameters: <em>target</em> and <em>ID</em>. </p>
<div class=code>void glBindBufferARB(GLenum target, GLuint id)</div>
<p style="MARGIN-LEFT: 30px"><em>Target</em> is a hint to tell VBO whether this buffer object will store vertex array data or index array data: GL_ARRAY_BUFFER_ARB, or GL_ELEMENT_ARRAY_BUFFER_ARB. Any vertex attributes, such as vertex coordinates, texture coordinates, normals and color component arrays should use GL_ARRAY_BUFFER_ARB. Index array which is used for glDraw[Range]Elements() should be tied with GL_ELEMENT_ARRAY_BUFFER_ARB. Note that this <em>target</em> flag assists VBO to decide the most efficient locations of buffer objects, for example, some systems may prefer indices in AGP or system memory, and vertices in video memory. </p>
<p style="MARGIN-LEFT: 30px">Once glBindBufferARB() is first called, VBO initializes the buffer with a zero-sized memory buffer and set the initial VBO states, such as usage and access properties. </p>
<h4>glBufferDataARB()</h4>
<p style="MARGIN-LEFT: 30px">You can copy the data into the buffer object with glBufferDataARB() when the buffer has been initialized. </p>
<div class=code>void glBufferDataARB(GLenum target, GLsizei size, const void* data, GLenum usage)</div>
<p style="MARGIN-LEFT: 30px">Again, the first parameter, <em>target</em> would be GL_ARRAY_BUFFER_ARB or GL_ELEMENT_ARRAY_BUFFER_ARB. <em>Size</em> is the number of bytes of data to transfer. The third parameter is the pointer to the array of source data. If <em>data</em> is NULL pointer, then VBO reserves only memory space with the given data size. The last parameter, <em>"usage"</em> flag is another performance hint for VBO to provide how the buffer object is going to be used: <em>static</em>, <em>dynamic</em> or <em>stream</em>, and <em>read</em>, <em>copy</em> or <em>draw</em>. </p>
<p style="MARGIN-LEFT: 30px">VBO specifies 9 enumerated values for <em>usage</em> flags; </p>
<div class=code>
<pre>GL_STATIC_DRAW_ARB
GL_STATIC_READ_ARB
GL_STATIC_COPY_ARB
GL_DYNAMIC_DRAW_ARB
GL_DYNAMIC_READ_ARB
GL_DYNAMIC_COPY_ARB
GL_STREAM_DRAW_ARB
GL_STREAM_READ_ARB
GL_STREAM_COPY_ARB
</pre>
</div>
<p style="MARGIN-LEFT: 30px"><em>"Static"</em> means the data in VBO will not be changed (specified once and used many times), <em>"dynamic"</em> means the data will be changed frequently (specified and used repeatedly), and <em>"stream"</em> means the data will be changed every frame (specified once and used once). <em>"Draw"</em> means the data will be sent to GPU in order to draw (application to GL), <em>"read"</em> means the data will be read by the client's application (GL to application), and <em>"copy"</em> means the data will be used both drawing and reading (GL to GL). </p>
<p style="MARGIN-LEFT: 30px">Note that only <em>draw</em> token is useful for VBO, and <em>copy</em> and <em>read</em> token will be become meaningful only for pixel/frame buffer object (<a href="http://www.songho.ca/opengl/gl_pbo.html">PBO</a> or <a href="http://www.songho.ca/opengl/gl_fbo.html">FBO</a>). </p>
<p style="MARGIN-LEFT: 30px">VBO memory manager will choose the best memory places for the buffer object based on these usage flags, for example, GL_STATIC_DRAW_ARB and GL_STREAM_DRAW_ARB may use video memory, and GL_DYNAMIC_DRAW_ARB may use AGP memory. Any _READ_ related buffers would be fine in system or AGP memory because the data should be easy to access. </p>
<h4>glBufferSubDataARB()</h4>
<div class=code>void glBufferSubDataARB(GLenum target, GLint offset, GLsizei size, void* data)</div>
<p style="MARGIN-LEFT: 30px">Like glBufferDataARB(), glBufferSubDataARB() is used to copy data into VBO, but it only replaces a range of data into <em>the existing buffer</em>, starting from the given offset. (The total size of the buffer must be set by glBufferDataARB() before using glBufferSubDataARB().) </p>
<h4>glDeleteBuffersARB()</h4>
<div class=code>void glDeleteBuffersARB(GLsizei n, const GLuint* ids)</div>
<p style="MARGIN-LEFT: 30px">You can delete a single VBO or multiple VBOs with glDeleteBuffersARB() if they are not used anymore. After a buffer object is deleted, its contents will be lost. </p>
<p>The following code is an example of creating a single VBO for vertex coordinates. Notice that you can delete the memory allocation for vertex array in your application after you copy data into VBO. </p>
<div class=code>
<pre>GLuint vboId;                              <span class=comment>// ID of VBO</span>
GLfloat* vertices = new GLfloat[vCount*3]; <span class=comment>// create vertex array</span>
...
<span class=comment>// generate a new VBO and get the associated ID</span>
glGenBuffersARB(1, &amp;vboId);
<span class=comment>// bind VBO in order to use</span>
glBindBufferARB(GL_ARRAY_BUFFER_ARB, vboId);
<span class=comment>// upload data to VBO</span>
glBufferDataARB(GL_ARRAY_BUFFER_ARB, dataSize, vertices, GL_STATIC_DRAW_ARB);
<span class=comment>// it is safe to delete after copying data to VBO</span>
delete [] vertices;
...
<span class=comment>// delete VBO when program terminated</span>
glDeleteBuffersARB(1, &amp;vboId);
</pre>
</div>
<h3 id=draw>Drawing VBO</h3>
<p>Because VBO sits on top of the existing vertex array implementation, rendering VBO is almost same as using <a href="http://www.songho.ca/opengl/gl_vertexarray.html">vertex array</a>. Only difference is that the pointer to the vertex array is now as an offset into a currently bound buffer object. Therefore, no additional APIs are required to draw a VBO except glBindBufferARB(). </p>
<div class=code>
<pre><span class=comment>// bind VBOs for vertex array and index array</span>
glBindBufferARB(GL_ARRAY_BUFFER_ARB, vboId1);         <span class=comment>// for vertex coordinates</span>
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, vboId2); <span class=comment>// for indices</span>
<span class=comment>// do same as vertex array except pointer</span>
glEnableClientState(GL_VERTEX_ARRAY);                 <span class=comment>// activate vertex coords array</span>
glVertexPointer(3, GL_FLOAT, 0, 0);                   <span class=comment>// last param is offset, not ptr</span>
<span class=comment>// draw 6 quads using offset of index array</span>
glDrawElements(GL_QUADS, 24, GL_UNSIGNED_BYTE, 0);
glDisableClientState(GL_VERTEX_ARRAY);                <span class=comment>// deactivate vertex array</span>
<span class=comment>// bind with 0, so, switch back to normal pointer operation</span>
glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0);
</pre>
</div>
<p>Binding the buffer object with 0 switchs off VBO operation. It is a good idea to turn VBO off after use, so normal vertex array operations with absolute pointers will be re-activated. </p>
<h3 id=update>Updating VBO</h3>
<p>The advantage of VBO over <a href="http://www.songho.ca/opengl/gl_displaylist.html">display list</a> is the client can read and modify the buffer object data, but display list cannot. The simplest method of updating VBO is copying again new data into the bound VBO with glBufferDataARB() or glBufferSubDataARB(). For this case, your application should have a valid vertex array all the time in your application. That means that you must always have 2 copies of vertex data: one in your application and the other in VBO. </p>
<p>The other way to modify buffer object is to map the buffer object into client's memory, and the client can update data with the pointer to the mapped buffer. The following describes how to map VBO into client's memory and how to access the mapped data. </p>
<h4>glMapBufferARB()</h4>
<p style="MARGIN-LEFT: 30px">VBO provides glMapBufferARB() in order to map the buffer object into client's memory. </p>
<div class=code>void* glMapBufferARB(GLenum target, GLenum access)</div>
<p style="MARGIN-LEFT: 30px">If OpenGL is able to map the buffer object into client's address space, glMapBufferARB() returns the pointer to the buffer. Otherwise it returns NULL. </p>
<p style="MARGIN-LEFT: 30px">The first parameter, <em>target</em> is mentioned earlier at glBindBufferARB() and the second parameter, <em>access</em> flag specifies what to do with the mapped data: read, write or both. </p>
<div class=code>
<pre>GL_READ_ONLY_ARB
GL_WRITE_ONLY_ARB
GL_READ_WRITE_ARB
</pre>
</div>
<p style="MARGIN-LEFT: 30px">Note that glMapBufferARB() causes a synchronizing issue. If GPU is still working with the buffer object, glMapBufferARB() will not return until GPU finishes its job with the corresponding buffer object. </p>
<p style="MARGIN-LEFT: 30px">To avoid waiting (idle), you can call first glBufferDataARB() with NULL pointer, then call glMapBufferARB(). In this case, the previous data will be discarded and glMapBufferARB() returns a new allocated pointer immediately even if GPU is still working with the previous data. </p>
<p style="MARGIN-LEFT: 30px">However, this method is valid only if you want to update entire data set because you discard the previous data. If you want to change only portion of data or to read data, you better not release the previous data. </p>
<h4>glUnmapBufferARB()</h4>
<div class=code>GLboolean glUnmapBufferARB(GLenum target)</div>
<p style="MARGIN-LEFT: 30px">After modifying the data of VBO, it must be unmapped the buffer object from the client's memory. glUnmapBufferARB() returns GL_TRUE if success. When it returns GL_FALSE, the contents of VBO become corrupted while the buffer was mapped. The corruption results from screen resolution change or window system specific events. In this case, the data must be resubmitted. </p>
<p>Here is a sample code to modify VBO with mapping method. </p>
<div class=code>
<pre><span class=comment>// bind then map the VBO</span>
glBindBufferARB(GL_ARRAY_BUFFER_ARB, vboId);
float* ptr = (float*)glMapBufferARB(GL_ARRAY_BUFFER_ARB, GL_WRITE_ONLY_ARB);
<span class=comment>// if the pointer is valid(mapped), update VBO</span>
if(ptr)
{
updateMyVBO(ptr, ...);                 <span class=comment>// modify buffer data</span>
glUnmapBufferARB(GL_ARRAY_BUFFER_ARB); <span class=comment>// unmap it after use</span>
}
<span class=comment>// you can draw the updated VBO</span>
...
</pre>
</div>
<h3 id=example>Example</h3>
<p><img height=327 alt="Example of VBO" src="http://www.songho.ca/opengl/files/gl_vbo.jpg" width=408> <br>This demo application makes a VBO wobbling in and out along normals. It maps a VBO and updates its vertices every frame with the pointer to the mapped buffer. You can compare the performace with a traditional vertex array implementation. </p>
<p>It uses 2 vertex buffers; one for both vertex coords and normals, and the other stores index array only. </p>
<p>Download the source and binary: <a href="http://www.songho.ca/opengl/files/vbo.zip">vbo.zip</a>, <a href="http://www.songho.ca/opengl/files/vboSimple.zip">vboSimple.zip</a>. </p>
<p>vboSimple is a very simple example to draw a cube using VBO and <a href="http://www.songho.ca/opengl/gl_vertexarray.html">Vertex Array</a>. You can easily see what is common and what is different between VBO and VA. </p>
<p>I also include a makefile (Makefile.linux) for linux system in <em>src</em> folder, so you can build an executable on your linux box, for example: </p>
<div class=code>&gt; make -f Makefile.linux</div>
<img src ="http://www.cppblog.com/zmj/aggbug/61420.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-09-09 21:59 <a href="http://www.cppblog.com/zmj/archive/2008/09/09/61420.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>OpenGL Vertex Array</title><link>http://www.cppblog.com/zmj/archive/2008/09/09/61419.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Tue, 09 Sep 2008 13:56:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/09/09/61419.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/61419.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/09/09/61419.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/61419.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/61419.html</trackback:ping><description><![CDATA[<a href="http://www.songho.ca/opengl/gl_vertexarray.html">http://www.songho.ca/opengl/gl_vertexarray.html</a><br>
<h1>OpenGL Vertex Array</h1>
<p><strong>Related Topics:</strong> <a href="http://www.songho.ca/opengl/gl_vbo.html"><u><font color=#800080>Vertex Buffer Object</font></u></a>, <a href="http://www.songho.ca/opengl/gl_displaylist.html"><u><font color=#0000ff>Display List</font></u></a> <br><strong>Download:</strong> <a href="http://www.songho.ca/opengl/files/vertexArray.zip"><u><font color=#0000ff>vertexArray.zip</font></u></a> </p>
<p>Instead you specify individual vertex data in immediate mode (between <a href="http://www.songho.ca/opengl/gl_overview.html#glbegin"><u><font color=#0000ff><em>glBegin()</em> and <em>glEnd()</em></font></u></a> pairs), you can store vertex data in a set of arrays including vertex coordinates, normals, texture coordinates and color information. And you can draw geometric primitives by dereferencing the array elements with array indices. </p>
<div style="FLOAT: left"><img height=192 alt="" src="http://www.songho.ca/opengl/files/gl_cube.gif" width=204> </div>
<p>Take a look the following code to draw a cube with immediate mode. </p>
<p>Each face needs 4 times of glVertex*() calls to make a quad, for example, the quad at front is v0-v1-v2-v3. A cube has 6 faces, so the total number of glVertex*() calls is 24. If you also specify normals and colors to the corresponding vertices, the number of function calls increases to 3 times more; 24 of glColor*() and 24 of glNormal*(). </p>
<p>The other thing that you should notice is the vertex "v0" is shared with 3 adjacent polygons; front, right and up face. In immediate mode, you have to provide the shared vertex 3 times, once for each face as shown in the code. </p>
<div class=code style="CLEAR: both">
<pre>glBegin(GL_QUADS);      <span class=comment>// draw a cube with 6 quads</span>
glVertex3fv(v0);    <span class=comment>// front face</span>
glVertex3fv(v1);
glVertex3fv(v2);
glVertex3fv(v3);
glVertex3fv(v0);    <span class=comment>// right face</span>
glVertex3fv(v3);
glVertex3fv(v4);
glVertex3fv(v5);
glVertex3fv(v0);    <span class=comment>// up face</span>
glVertex3fv(v5);
glVertex3fv(v6);
glVertex3fv(v1);
...                 <span class=comment>// draw other 3 faces</span>
glEnd();
</pre>
</div>
<p>Using vertex arrays reduces the number of function calls and redundant usage of shared vertices. Therefore, you may increase the performance of rendering. Here, 3 different OpenGL functions are explained to use vertex arrays; <strong>glDrawArrays()</strong>, <strong>glDrawElements()</strong> and <strong>glDrawRangeElements()</strong>. Although, better approach is using <a href="http://www.songho.ca/opengl/gl_vbo.html"><u><font color=#800080>vertex buffer objects (VBO)</font></u></a> or <a href="http://www.songho.ca/opengl/gl_displaylist.html"><u><font color=#0000ff>display lists</font></u></a>. </p>
<h3>Initialization</h3>
<p>OpenGL provides <strong>glEnableClientState()</strong> and <strong>glDisableClientState()</strong> functions to activate and deactivate 6 different types of arrays. Plus, there are 6 functions to specify the exact positions(addresses) of arrays, so, OpenGL can access the arrays in your application. </p>
<ul>
    <li><strong>glVertexPointer()</strong>:&nbsp; specify pointer to vertex coords array
    <li><strong>glNormalPointer()</strong>:&nbsp; specify pointer to normal array
    <li><strong>glColorPointer()</strong>:&nbsp; specify pointer to RGB color array
    <li><strong>glIndexPointer()</strong>:&nbsp; specify pointer to indexed color array
    <li><strong>glTexCoordPointer()</strong>:&nbsp; specify pointer to texture cords array
    <li><strong>glEdgeFlagPointer()</strong>:&nbsp; specify pointer to edge flag array </li>
</ul>
<p>Each specifying function requires different parameters. Please look at OpenGL function manuals. Edge flags are used to mark whether the vertex is on the boundary edge or not. Hence, the only edges where edge flags are on will be visible if glPolygonMode() is set with GL_LINE.</p>
<p>Notice that vertex arrays are located in your application(system memory), which is on the client side. And, OpenGL on the server side gets access to them. That is why there are distinctive commands for vertex array; <strong>glEnableClientState()</strong> and <strong>glDisableClientState()</strong> instead of using <strong>glEnable()</strong> and <strong>glDisable()</strong>. </p>
<h3>glDrawArrays()</h3>
<p><strong>glDrawArrays()</strong> reads vertex data from the enabled arrays by marching straight through the array without skipping or hopping. Because <strong>glDrawArrays() </strong>does not allows hopping around the vertex arrays, you still have to repeat the shared vertices once per face. </p>
<p><strong>glDrawArrays()</strong> takes 3 arguments. The first thing is the primitive type. The second parameter is the starting offset of the array. The last parameter is the number of vertices to pass to rendering pipeline of OpenGL. <br>For above example to draw a cube, the first parameter is GL_QUADS, the second is 0, which means starting from beginning of the array. And the last parameter is 24: a cube requires 6 faces and each face needs 4 vertices to build a quad, 6 &#215; 4 = 24. </p>
<div class=code>
<pre>GLfloat vertices[] = {...}; <span class=comment>// 24 of vertex coords</span>
...
<span class=comment>// activate and specify pointer to vertex array</span>
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(3, GL_FLOAT, 0, vertices);
<span class=comment>// draw a cube</span>
glDrawArrays(GL_QUADS, 0, 24);
<span class=comment>// deactivate vertex arrays after drawing</span>
glDisableClientState(GL_VERTEX_ARRAY);
</pre>
</div>
<p>As a result of using <strong>glDrawArrays()</strong>, you can replace 24 <strong>glVertex*()</strong> calls with a single <strong>glDrawArrays()</strong> call. However, we still need to duplicate the shared vertices, so the number of vertices defined in the array is still 24 instead of 8. <strong>glDrawElements()</strong> is the solution to reduce the number of vertices in the array, so it allows transferring less data to OpenGL. </p>
<h3>glDrawElements()</h3>
<p><strong>glDrawElements()</strong> draws a sequence of primitives by hopping around vertex arrays with the associated array indices. It reduces both the number of function calls and the number of vertices to transfer. Furthermore, OpenGL may cache the recently processed vertices and reuse them without resending the same vertices into vertex transform pipeline multiple times. </p>
<p><strong>glDrawElements()</strong> requires 4 parameters. The first one is the type of primitive, the second is the number of indices of index array, the third is data type of index array and the last parameter is the address of index array. In this example, the parameters are, GL_QUADS, 24, GL_UNSIGNED_BYTE and indices respectively. </p>
<div class=code>
<pre>GLfloat vertices[] = {...};     <span class=comment>// 8 of vertex coords</span>
GLubyte indices[] = {0,1,2,3,   <span class=comment>// 24 of indices</span>
0,3,4,5,
0,5,6,1,
1,6,7,2,
7,4,3,2,
4,7,6,5};
...
<span class=comment>// activate and specify pointer to vertex array</span>
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(3, GL_FLOAT, 0, vertices);
<span class=comment>// draw a cube</span>
glDrawElements(GL_QUADS, 24, GL_UNSIGNED_BYTE, indices);
<span class=comment>// deactivate vertex arrays after drawing</span>
glDisableClientState(GL_VERTEX_ARRAY);
</pre>
</div>
<p>The size of vertex coordinates array is now 8, which is exactly same number of vertices in the cube without any redundant entries. </p>
<p>Note that the data type of index array is GLubyte instead of GLuint or GLushort. It should be the smallest data type that can fit maximum index number in order to reduce the size of index array, otherwise, it may cause performance drop due to the size of index array. Since the vertex array contains 8 vertices, GLubyte is enough to store all indices. </p>
<div style="FLOAT: left; TEXT-ALIGN: center"><img height=190 alt="" src="http://www.songho.ca/opengl/files/gl_cubeNormal.gif" width=194> <br><span class=caption>Different normals at shared vertex</span> </div>
<p>Another thing you should consider is the normal vectors at the shared vertices. If the normals of the adjacent polygons at a shared vertex are all different, then normal vectors should be specified as many as the number of faces, once for each face. <br><br>For example, the vertex v0 is shared with the front, right and up face, but, the normals cannot be shared at v0. The normal of the front face is n0, the right face normal is n1 and the up face is n2. For this situation, the normal is not the same at a shared vertex, the vertex cannot be defined only once in vertex array any more. It must be defined multiple times in the array for vertex coordinates in order to match the same amount of elements in the normal array. See the actual implementation in the example <a href="http://www.songho.ca/opengl/files/vertexArray.zip"><u><font color=#0000ff>code</font></u></a>. </p>
<h3 style="CLEAR: both">glDrawRangeElements()</h3>
<p>Like <strong>glDrawElements()</strong>, <strong>glDrawRangeElements()</strong> is also good for hopping around vertex array. However, <strong>glDrawRangeElements()</strong> has two more parameters (<em>start</em> and <em>end</em> index) to specify a range of vertices to be prefetched. By adding this restriction of a range, OpenGL may be able to obtain only limited amount of vertex array data prior to rendering, and may increase performance. </p>
<p>The additional parameters in <strong>glDrawRangeElements()</strong> are <em>start</em> and <em>end</em> index, then OpenGL prefetches a limited amount of vertices from these values: <em>end - start + 1</em>. And the values in index array must lie in between <em>start</em> and <em>end</em> index. Note that not all vertices in range (<em>start, end</em>) must be referenced. But, if you specify a sparsely used range, it causes unnecessary process for many unused vertices in that range. </p>
<div class=code>
<pre>GLfloat vertices[] = {...};     <span class=comment>// 8 of vertex coords</span>
GLubyte indices[] = {0,1,2,3,   <span class=comment>// 24 of indices</span>
0,3,4,5,
0,5,6,1,
1,6,7,2,
7,4,3,2,
4,7,6,5};
...
<span class=comment>// activate and specify pointer to vertex array</span>
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(3, GL_FLOAT, 0, vertices);
<span class=comment>// draw first half, range is 6 - 0 + 1 = 7 vertices</span>
glDrawRangeElements(GL_QUADS, 0, 6, 12, GL_UNSIGNED_BYTE, indices);
<span class=comment>// draw second half, range is 7 - 1 + 1 = 7 vertices</span>
glDrawRangeElements(GL_QUADS, 1, 7, 12, GL_UNSIGNED_BYTE, indices+12);
<span class=comment>// deactivate vertex arrays after drawing</span>
glDisableClientState(GL_VERTEX_ARRAY);
</pre>
</div>
<p>You can find out maximum number of vertices to be prefetched and the maximum number of indices to be referenced by using <strong>glGetIntegerv()</strong> with GL_MAX_ELEMENTS_VERTICES and GL_MAX_ELEMENTS_INDICES. </p>
<p>Note that glDrawRangeElements() is available OpenGL version 1.2 or greater. </p>
<h3>Example</h3>
<p><img height=327 alt="Example of Vertex Array" src="http://www.songho.ca/opengl/files/gl_vertexArray.jpg" width=408> <br>This demo application renders a cube with 4 different ways; immediate mode, <strong>glDrawArrays()</strong>, <strong>glDrawElements()</strong> and <strong>glDrawRangeElements()</strong>. </p>
<p>Download the source and binary: <a href="http://www.songho.ca/opengl/files/vertexArray.zip"><u><font color=#0000ff>vertexArray.zip</font></u></a>. </p>
<p>In order to run this program properly, video card must support OpenGL v1.2 or greater because of glDrawRangeElements(). Make sure your video driver supports version 1.2 or higher with <a href="http://www.songho.ca/opengl/files/glinfo.zip"><u><font color=#0000ff>glinfo</font></u></a>. </p>
<!-- footer -->
<img src ="http://www.cppblog.com/zmj/aggbug/61419.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-09-09 21:56 <a href="http://www.cppblog.com/zmj/archive/2008/09/09/61419.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>OpenGL Rendering Pipeline</title><link>http://www.cppblog.com/zmj/archive/2008/09/09/61418.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Tue, 09 Sep 2008 13:55:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/09/09/61418.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/61418.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/09/09/61418.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/61418.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/61418.html</trackback:ping><description><![CDATA[<a href="http://www.songho.ca/opengl/gl_pipeline.html">http://www.songho.ca/opengl/gl_pipeline.html</a><br>
<h1>OpenGL Rendering Pipeline</h1>
<p>OpenGL Pipeline has a series of processing stages in order. Two graphical information, vertex-based data and pixel-based data, are processed through the pipeline, combined together then written into the frame buffer. Notice that OpenGL can send the processed data back to your application. <em>(See the grey colour lines)</em> </p>
<div style="PADDING-RIGHT: 30px; FLOAT: left; TEXT-ALIGN: center"><img height=324 alt="OpenGL Pipeline" src="http://www.songho.ca/opengl/files/gl_pipeline.gif" width=642> <br><span class=caption>OpenGL Pipeline</span> </div>
<h4 style="CLEAR: both">Display List</h4>
<p style="MARGIN-LEFT: 30px">Display list is a group of OpenGL commands that have been stored (compiled) for later execution. All data, geometry (vertex) and pixel data, can be stored in a display list. It may improve performance since commands and data are cached in a display list. When OpenGL program runs on the network, you can reduce data transmission over the network by using display list. Since display lists are part of server state and reside on the server machine, the client machine needs to send commands and data only once to server's display list. <em>(See more details in <a href="http://www.songho.ca/opengl/gl_displaylist.html"><u><font color=#0000ff>Display List</font></u></a>.)</em> <br>&nbsp; </p>
<h4>Vertex Operation</h4>
<p style="MARGIN-LEFT: 30px">Each vertex and normal coordinates are transformed by GL_MODELVIEW matrix (from object coordinates to eye coordinates). Also, if lighting is enabled, the lighting calculation per vertex is performed using the transformed vertex and normal data. This lighting calculation updates new color of the vertex. <em>(See more details in <a href="http://www.songho.ca/opengl/gl_transform.html"><u><font color=#0000ff>Transformation</font></u></a>)</em> <br>&nbsp; </p>
<h4>Primitive Assembly</h4>
<p style="MARGIN-LEFT: 30px">After vertex operation, the primitives (point, line, and polygon) are transformed once again by projection matrix then clipped by viewing volume clipping planes; from eye coordinates to clip coordinates. After that, perspective division by w occurs and viewport transform is applied in order to map 3D scene to window space coordinates. Last thing to do in Primitive Assembly is culling test if culling is enabled. <br>&nbsp; </p>
<h4>Pixel Transfer Operation</h4>
<p style="MARGIN-LEFT: 30px">After the pixels from client's memory are unpacked(read), the data are performed scaling, bias, mapping and clamping. These operations are called Pixel Transfer Operation. The transferred data are either stored in texture memory or rasterized directly to fragments. <br>&nbsp; </p>
<h4>Texture Memory</h4>
<p style="MARGIN-LEFT: 30px">Texture images are loaded into texture memory to be applied onto geometric objects. <br>&nbsp; </p>
<h4>Raterization</h4>
<p style="MARGIN-LEFT: 30px">Rasterization is the conversion of both geometric and pixel data into fragment. Fragments are a rectangular array containing color, depth, line width, point size and antialiasing calculations (GL_POINT_SMOOTH, GL_LINE_SMOOTH, GL_POLYGON_SMOOTH). If shading mode is GL_FILL, then the interior pixels (area) of polygon will be filled at this stage. Each fragment corresponds to a pixel in the frame buffer. <br>&nbsp; </p>
<h4>Fragment Operation</h4>
<p style="MARGIN-LEFT: 30px">It is the last process to convert fragments to pixels onto frame buffer. The first process in this stage is texel generation; A texture element is generated from texture memory and it is applied to the each fragment. Then fog calculations are applied. After that, there are several fragment tests follow in order; Scissor Test &#8658; Alpha Test &#8658; Stencil Test &#8658; Depth Test. <br>Finally, blending, dithering, logical operation and masking by bitmask are performed and actual pixel data are stored in frame buffer. <br>&nbsp; </p>
<h4>Feedback</h4>
<p style="MARGIN-LEFT: 30px">OpenGL can return most of current states and information through <strong>glGet*()</strong> and <strong>glIsEnabled()</strong> commands. Further more, you can read a rectangular area of pixel data from frame buffer using <strong>glReadPixels()</strong>, and get fully transformed vertex data using <strong>glRenderMode(GL_FEEDBACK)</strong>. <strong>glCopyPixels()</strong> does not return pixel data to the specified system memory, but copy them back to the another frame buffer, for example, from front buffer to back buffer. <br><br>See more detail <a href="http://www.songho.ca/opengl/gl_feedback.html"><u><font color=#0000ff>here</font></u></a> how to extract vertex data from OpenGL pipeline. </p>
<img src ="http://www.cppblog.com/zmj/aggbug/61418.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-09-09 21:55 <a href="http://www.cppblog.com/zmj/archive/2008/09/09/61418.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>COLLADA</title><link>http://www.cppblog.com/zmj/archive/2008/08/29/60376.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Fri, 29 Aug 2008 09:13:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/08/29/60376.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/60376.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/08/29/60376.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/60376.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/60376.html</trackback:ping><description><![CDATA[<a href="http://en.wikipedia.org/wiki/Collada">http://en.wikipedia.org/wiki/Collada</a><br>
<h3 id=siteSub>From Wikipedia, the free encyclopedia</h3>
<div id=contentSub>&nbsp;&nbsp;(Redirected from <a title=Collada href="http://en.wikipedia.org/w/index.php?title=Collada&amp;redirect=no"><u><font color=#0000ff>Collada</font></u></a>)</div>
<div id=jump-to-nav>Jump to: <a href="http://en.wikipedia.org/wiki/Collada#column-one"><u><font color=#800080>navigation</font></u></a>, <a href="http://en.wikipedia.org/wiki/Collada#searchInput"><u><font color=#800080>search</font></u></a></div>
<!-- start content -->
<table class=infobox style="FONT-SIZE: 88%; WIDTH: 22em; LINE-HEIGHT: 1.5em; TEXT-ALIGN: left" cellSpacing=5>
    <caption class="" style="FONT-WEIGHT: bold; FONT-SIZE: 125%">COLLADA</caption>
    <tbody>
        <tr>
            <th><a title="Filename extension" href="http://en.wikipedia.org/wiki/Filename_extension"><u><font color=#0000ff>Filename extension</font></u></a></th>
            <td class=""><code><tt>.dae</tt></code></td>
        </tr>
        <tr>
            <th>Extended from</th>
            <td class=""><a title=XML href="http://en.wikipedia.org/wiki/XML"><font color=#0000ff><u>XML</u></font></a></td>
        </tr>
        <tr>
            <th><a title=Website href="http://en.wikipedia.org/wiki/Website"><font color=#0000ff><u>Website</u></font></a></th>
            <td class=""><a class="external text" title=http://www.khronos.org/collada/ href="http://www.khronos.org/collada/" rel=nofollow><u><font color=#0000ff>khronos.org/collada</font></u></a></td>
        </tr>
    </tbody>
</table>
<p><strong>COLLADA</strong> is a <strong>COLLA</strong>borative <strong>D</strong>esign <strong>A</strong>ctivity for establishing an <a title=Interchange href="http://en.wikipedia.org/wiki/Interchange"><u><font color=#0000ff>interchange</font></u></a> <a title="File format" href="http://en.wikipedia.org/wiki/File_format"><u><font color=#0000ff>file format</font></u></a> for interactive <a class=mw-redirect title="3-D computer graphics" href="http://en.wikipedia.org/wiki/3-D_computer_graphics"><u><font color=#0000ff>3D</font></u></a> applications.</p>
<p>COLLADA defines an <a title="Open standard" href="http://en.wikipedia.org/wiki/Open_standard"><u><font color=#0000ff>open standard</font></u></a> <a title="XML schema" href="http://en.wikipedia.org/wiki/XML_schema"><u><font color=#0000ff>XML schema</font></u></a> for exchanging <a title="Digital asset" href="http://en.wikipedia.org/wiki/Digital_asset"><u><font color=#0000ff>digital assets</font></u></a> among various graphics software applications that might otherwise store their assets in incompatible formats. COLLADA documents that describe digital assets are <a title=XML href="http://en.wikipedia.org/wiki/XML"><u><font color=#0000ff>XML</font></u></a> files, usually identified with a .dae (<strong>d</strong>igital <strong>a</strong>sset <strong>e</strong>xchange) <a title="Filename extension" href="http://en.wikipedia.org/wiki/Filename_extension"><u><font color=#0000ff>filename extension</font></u></a>.</p>
<table class=toc id=toc summary=Contents>
    <tbody>
        <tr>
            <td>
            <div id=toctitle>
            <h2>Contents</h2>
            <span class=toctoggle>[<a class=internal id=togglelink href="javascript:toggleToc()"><u><font color=#0000ff>hide</font></u></a>]</span></div>
            <ul>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Collada#History"><u><font color=#800080><span class=tocnumber>1</span> <span class=toctext>History</span></font></u></a>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Collada#Tools_and_compatibility"><u><font color=#800080><span class=tocnumber>2</span> <span class=toctext>Tools and compatibility</span></font></u></a>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Collada#COLLADA_Physics"><u><font color=#800080><span class=tocnumber>3</span> <span class=toctext>COLLADA Physics</span></font></u></a>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Collada#Versions"><u><font color=#800080><span class=tocnumber>4</span> <span class=toctext>Versions</span></font></u></a>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Collada#See_also"><u><font color=#800080><span class=tocnumber>5</span> <span class=toctext>See also</span></font></u></a>
                <li class=toclevel-1><a href="http://en.wikipedia.org/wiki/Collada#External_links"><u><font color=#800080><span class=tocnumber>6</span> <span class=toctext>External links</span></font></u></a> </li>
            </ul>
            </td>
        </tr>
    </tbody>
</table>
<script type=text/javascript>
//<![cdata[
if (window.showTocToggle) { var tocShowText = "show"; var tocHideText = "hide"; showTocToggle(); }
//]]&gt;
</script>
<p><a id=History name=History></a></p>
<h2><span class=editsection>[<a title="Edit section: History" href="http://en.wikipedia.org/w/index.php?title=COLLADA&amp;action=edit&amp;section=1"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>History</span></h2>
<p>Originally created by <a title="Sony Computer Entertainment" href="http://en.wikipedia.org/wiki/Sony_Computer_Entertainment"><u><font color=#0000ff>Sony Computer Entertainment</font></u></a> as the official format for <a title="PlayStation 3" href="http://en.wikipedia.org/wiki/PlayStation_3"><u><font color=#0000ff>PlayStation 3</font></u></a> and <a title="PlayStation Portable" href="http://en.wikipedia.org/wiki/PlayStation_Portable"><u><font color=#0000ff>PlayStation Portable</font></u></a> development, it has since become the property of the <a title="Khronos Group" href="http://en.wikipedia.org/wiki/Khronos_Group"><u><font color=#0000ff>Khronos Group</font></u></a>, a member-funded industry consortium, which now shares the copyright with Sony. Several graphics companies collaborated with Sony from COLLADA's beginnings to create a tool that would be useful to the widest possible audience, and COLLADA continues to evolve through the efforts of the Khronos contributors. Early collaborators included <a title="Alias Systems Corporation" href="http://en.wikipedia.org/wiki/Alias_Systems_Corporation"><u><font color=#0000ff>Alias Systems Corporation</font></u></a>, <a class=mw-redirect title="Criterion Software" href="http://en.wikipedia.org/wiki/Criterion_Software"><u><font color=#0000ff>Criterion Software</font></u></a>, <a title=Autodesk href="http://en.wikipedia.org/wiki/Autodesk"><u><font color=#0000ff>Autodesk, Inc.</font></u></a>, and <a title="Avid Technology" href="http://en.wikipedia.org/wiki/Avid_Technology"><u><font color=#0000ff>Avid Technology</font></u></a>. Dozens of commercial game studios and game engines have adopted the standard.</p>
<p><a id=Tools_and_compatibility name=Tools_and_compatibility></a></p>
<h2><span class=editsection>[<a title="Edit section: Tools and compatibility" href="http://en.wikipedia.org/w/index.php?title=COLLADA&amp;action=edit&amp;section=2"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>Tools and compatibility</span></h2>
<p>COLLADA was intended originally as an intermediate format for transporting data from one <a title="Digital content creation" href="http://en.wikipedia.org/wiki/Digital_content_creation"><u><font color=#0000ff>digital content creation</font></u></a> (DCC) tool to another. Applications exist to support that usage for several DCCs, including <a title="Maya (software)" href="http://en.wikipedia.org/wiki/Maya_(software)"><u><font color=#0000ff>Maya</font></u></a> (using ColladaMaya); <a title="3ds Max" href="http://en.wikipedia.org/wiki/3ds_Max"><u><font color=#0000ff>3ds Max</font></u></a> (using ColladaMax); <a title="LightWave 3D" href="http://en.wikipedia.org/wiki/LightWave_3D"><u><font color=#0000ff>LightWave 3D</font></u></a> (version 9.5); <a title="Cinema 4D" href="http://en.wikipedia.org/wiki/Cinema_4D"><u><font color=#0000ff>Maxon|Cinema 4D R11</font></u></a>; <a title="Softimage XSI" href="http://en.wikipedia.org/wiki/Softimage_XSI"><u><font color=#0000ff>Softimage|XSI</font></u></a>; <a title="Houdini (software)" href="http://en.wikipedia.org/wiki/Houdini_(software)"><u><font color=#0000ff>Side Effect's Houdini</font></u></a>; <a title=MeshLab href="http://en.wikipedia.org/wiki/MeshLab"><u><font color=#0000ff>MeshLab</font></u></a>; <a title=SketchUp href="http://en.wikipedia.org/wiki/SketchUp"><u><font color=#0000ff>SketchUp</font></u></a>, <a title="Blender (software)" href="http://en.wikipedia.org/wiki/Blender_(software)"><u><font color=#0000ff>Blender</font></u></a> and <a title="Modo (software)" href="http://en.wikipedia.org/wiki/Modo_(software)"><u><font color=#0000ff>modo</font></u></a>. COLLADA .dae files can be used in <a title="Adobe Photoshop" href="http://en.wikipedia.org/wiki/Adobe_Photoshop"><u><font color=#0000ff>Adobe Photoshop software</font></u></a> since version CS3. Game engines, such as <a class=mw-redirect title="Unreal engine" href="http://en.wikipedia.org/wiki/Unreal_engine"><u><font color=#0000ff>Unreal engine</font></u></a>, have also adopted this format.</p>
<p>Two open-source utility libraries are available to simplify the import and export of COLLADA documents: the <a class=new title="COLLADA DOM (page does not exist)" href="http://en.wikipedia.org/w/index.php?title=COLLADA_DOM&amp;action=edit&amp;redlink=1"><u><font color=#0000ff>COLLADA DOM</font></u></a> and the <a class=new title="FCollada (page does not exist)" href="http://en.wikipedia.org/w/index.php?title=FCollada&amp;action=edit&amp;redlink=1"><u><font color=#0000ff>FCollada</font></u></a> library. The COLLADA DOM is generated at compile-time from the COLLADA schema. It provides a low-level interface that eliminates the need for hand-written parsing routines, but is limited to reading and writing only one version of COLLADA, making it difficult to upgrade as new versions are released. In contrast, Feeling Software's FCollada provides a higher-level interface and can import all versions of COLLADA. FCollada is used in ColladaMaya, ColladaMax and several commercial game engines.</p>
<p>However, some applications have adopted COLLADA as their native format or as one variety of native input rather than simply using it as an intermediate format. <a title="Google Earth" href="http://en.wikipedia.org/wiki/Google_Earth"><u><font color=#0000ff>Google Earth</font></u></a> (release 4) has adopted COLLADA (1.4) as its native format for describing the objects populating the earth. Users can simply drag and drop a COLLADA (.dae) file on top of the virtual Earth. Alternatively, Google <a title=SketchUp href="http://en.wikipedia.org/wiki/SketchUp"><u><font color=#0000ff>SketchUp</font></u></a> can also be used to create .kmz files, a zip file containing a <a title="Keyhole Markup Language" href="http://en.wikipedia.org/wiki/Keyhole_Markup_Language"><u><font color=#0000ff>KML</font></u></a> file, a COLLADA (.dae) file, and all the texture images.</p>
<p><a id=COLLADA_Physics name=COLLADA_Physics></a></p>
<h2><span class=editsection>[<a title="Edit section: COLLADA Physics" href="http://en.wikipedia.org/w/index.php?title=COLLADA&amp;action=edit&amp;section=3"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>COLLADA Physics</span></h2>
<p>As of version 1.4, <a title=Physics href="http://en.wikipedia.org/wiki/Physics"><u><font color=#0000ff>physics</font></u></a> support was added to the COLLADA standard. The goal is to allow content creators to define various physical attributes in visual scenes. For example, one can define surface material properties such as friction. Furthermore, content creators can define the physical attributes for the objects in the scene. This is done by defining the rigid bodies that should be linked to the visual representations. More features include support for ragdolls, collision volumes, physical constraints between physical objects, and global physical properties such as gravitation.</p>
<p>Physics middleware products that support this standard include <a title="Bullet (software)" href="http://en.wikipedia.org/wiki/Bullet_(software)"><u><font color=#0000ff>Bullet Physics Library</font></u></a>, <a title="Open Dynamics Engine" href="http://en.wikipedia.org/wiki/Open_Dynamics_Engine"><u><font color=#0000ff>Open Dynamics Engine</font></u></a>, <a title="Physics Abstraction Layer" href="http://en.wikipedia.org/wiki/Physics_Abstraction_Layer"><u><font color=#0000ff>PAL</font></u></a>, nVidia's <a title=PhysX href="http://en.wikipedia.org/wiki/PhysX"><u><font color=#0000ff>PhysX</font></u></a> and Algoryx's <a title="AgX Multi Physics" href="http://en.wikipedia.org/wiki/AgX_Multi_Physics"><u><font color=#0000ff>AgX Multi Physics</font></u></a>. These products support by reading the abstract found in the COLLADA file and transferring it into a form that the middleware can support and represent in a physical simulation. This also enables different middleware and tools to exchange physics data in a standardized manner.</p>
<p>The <a title="Physics Abstraction Layer" href="http://en.wikipedia.org/wiki/Physics_Abstraction_Layer"><u><font color=#0000ff>Physics Abstraction Layer</font></u></a> provides support for COLLADA Physics to multiple physics engines that do not natively provide COLLADA support including <a class=new title="JigLib (page does not exist)" href="http://en.wikipedia.org/w/index.php?title=JigLib&amp;action=edit&amp;redlink=1"><u><font color=#0000ff>JigLib</font></u></a>, <a class=new title="OpenTissue (page does not exist)" href="http://en.wikipedia.org/w/index.php?title=OpenTissue&amp;action=edit&amp;redlink=1"><u><font color=#0000ff>OpenTissue</font></u></a>, <a title="Tokamak physics engine" href="http://en.wikipedia.org/wiki/Tokamak_physics_engine"><u><font color=#0000ff>Tokamak physics engine</font></u></a> and <a class=new title="True Axis (page does not exist)" href="http://en.wikipedia.org/w/index.php?title=True_Axis&amp;action=edit&amp;redlink=1"><u><font color=#0000ff>True Axis</font></u></a>. <a title="Physics Abstraction Layer" href="http://en.wikipedia.org/wiki/Physics_Abstraction_Layer"><u><font color=#0000ff>PAL</font></u></a> also provides support for COLLADA to physics engines that also feature a native interface.</p>
<p><a id=Versions name=Versions></a></p>
<h2><span class=editsection>[<a title="Edit section: Versions" href="http://en.wikipedia.org/w/index.php?title=COLLADA&amp;action=edit&amp;section=4"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>Versions</span></h2>
<ul>
    <li>1.0: October 2004
    <li>1.2: February 2005
    <li>1.3: June 2005
    <li>1.4.0: January 2006; added features such as character skinning and morph targets, rigid body dynamics, support for OpenGL ES materials, and shader effects for multiple shading languages including the <a class=mw-redirect title="Cg programming language" href="http://en.wikipedia.org/wiki/Cg_programming_language"><u><font color=#0000ff>Cg programming language</font></u></a>, <a title=GLSL href="http://en.wikipedia.org/wiki/GLSL"><u><font color=#0000ff>GLSL</font></u></a>, and <a class=mw-redirect title=HLSL href="http://en.wikipedia.org/wiki/HLSL"><u><font color=#0000ff>HLSL</font></u></a>. First release through Khronos.
    <li>1.4.1: July 2006; primarily a patch release. </li>
</ul>
<p><a id=See_also name=See_also></a></p>
<h2><span class=editsection>[<a title="Edit section: See also" href="http://en.wikipedia.org/w/index.php?title=COLLADA&amp;action=edit&amp;section=5"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>See also</span></h2>
<ul>
    <li><a class=mw-redirect title=U3D href="http://en.wikipedia.org/wiki/U3D"><u><font color=#0000ff>U3D</font></u></a>
    <li><a title=X3D href="http://en.wikipedia.org/wiki/X3D"><u><font color=#0000ff>X3D</font></u></a> / <a title=VRML href="http://en.wikipedia.org/wiki/VRML"><u><font color=#0000ff>VRML</font></u></a>
    <li><a title=3DMLW href="http://en.wikipedia.org/wiki/3DMLW"><u><font color=#0000ff>3DMLW (3D Markup Language for Web)</font></u></a>
    <li><a title="List of vector graphics markup languages" href="http://en.wikipedia.org/wiki/List_of_vector_graphics_markup_languages"><u><font color=#0000ff>List of vector graphics markup languages</font></u></a>
    <li><a class=mw-redirect title="PAL (software)" href="http://en.wikipedia.org/wiki/PAL_(software)"><u><font color=#0000ff>PAL XML physics format</font></u></a> </li>
</ul>
<p><a id=External_links name=External_links></a></p>
<h2><span class=editsection>[<a title="Edit section: External links" href="http://en.wikipedia.org/w/index.php?title=COLLADA&amp;action=edit&amp;section=6"><u><font color=#0000ff>edit</font></u></a>]</span> <span class=mw-headline>External links</span></h2>
<ul>
    <li><a class="external text" title=http://www.khronos.org/collada/ href="http://www.khronos.org/collada/" rel=nofollow><u><font color=#0000ff>Official homepage</font></u></a>
    <li><a class="external text" title=http://collada.org/ href="http://collada.org/" rel=nofollow><u><font color=#0000ff>Forum</font></u></a>
    <li><a class="external text" title=http://www.akpeters.com/product.asp?ProdCode=2876 href="http://www.akpeters.com/product.asp?ProdCode=2876" rel=nofollow><u><font color=#0000ff>COLLADA book</font></u></a>
    <li><a class="external text" title=http://sourceforge.net/projects/collada-dom href="http://sourceforge.net/projects/collada-dom" rel=nofollow><u><font color=#0000ff>COLLADA DOM, COLLADA RT, and COLLADA FX libraries are on sourceforge</font></u></a>
    <li><a class="external text" title=http://bullet.sourceforge.net href="http://bullet.sourceforge.net/" rel=nofollow><u><font color=#0000ff>Bullet Physics Library - First open source rigid body dynamics simulator with COLLADA Physics import</font></u></a>
    <li><a class="external text" title=http://wiki.codesynthesis.com/Schemas/COLLADA href="http://wiki.codesynthesis.com/Schemas/COLLADA" rel=nofollow><u><font color=#0000ff>C++ Data Binding for COLLADA</font></u></a>
    <li><a class="external text" title=http://sourceforge.net/projects/colladaloader/ href="http://sourceforge.net/projects/colladaloader/" rel=nofollow><u><font color=#0000ff>ColladaLoader. An open source application to load and visualize COLLADA files in real time using OpenGL.</font></u></a> </li>
</ul>
<!--
NewPP limit report
Preprocessor node count: 852/1000000
Post-expand include size: 1988/2048000 bytes
Template argument size: 636/2048000 bytes
Expensive parser function count: 0/500
--><!-- Saved in parser cache with key enwiki:pcache:idhash:1464418-0!1!0!default!!en!2 and timestamp 20080824123318 -->
<div class=printfooter>Retrieved from "<a href="http://en.wikipedia.org/wiki/COLLADA"><u><font color=#0000ff>http://en.wikipedia.org/wiki/COLLADA</font></u></a>"</div>
<div class=catlinks id=catlinks>
<div id=mw-normal-catlinks><a title=Special:Categories href="http://en.wikipedia.org/wiki/Special:Categories"><u><font color=#0000ff>Categories</font></u></a>: <span dir=ltr><a title="Category:Computer file formats" href="http://en.wikipedia.org/wiki/Category:Computer_file_formats"><u><font color=#0000ff>Computer file formats</font></u></a></span> | <span dir=ltr><a title="Category:CAD file formats" href="http://en.wikipedia.org/wiki/Category:CAD_file_formats"><u><font color=#0000ff>CAD file formats</font></u></a></span> | <span dir=ltr><a title="Category:XML-based standards" href="http://en.wikipedia.org/wiki/Category:XML-based_standards"><u><font color=#0000ff>XML-based standards</font></u></a></span> | <span dir=ltr><a title="Category:3D computer graphics" href="http://en.wikipedia.org/wiki/Category:3D_computer_graphics"><u><font color=#0000ff>3D computer graphics</font></u></a></span> | <span dir=ltr><a title="Category:Graphics standards" href="http://en.wikipedia.org/wiki/Category:Graphics_standards"><u><font color=#0000ff>Graphics standards</font></u></a></span></div>
</div>
<img src ="http://www.cppblog.com/zmj/aggbug/60376.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-08-29 17:13 <a href="http://www.cppblog.com/zmj/archive/2008/08/29/60376.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>COLLADA DOM Tutorial</title><link>http://www.cppblog.com/zmj/archive/2008/08/28/60258.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Thu, 28 Aug 2008 05:39:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/08/28/60258.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/60258.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/08/28/60258.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/60258.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/60258.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: http://www.cnblogs.com/Jedimaster/archive/2007/12/01/979256.html引言　　COLLADA是一个开放的标准，最初用于3D软件数据交换，由SCEA发起，现在则被许多著名厂家支持如Autodesk、XSI等。COLLADA不仅仅可以用于建模工具之间交换数据之用，也可以作为场景描述语言用于小规模的实时渲染。因为COLLADA DOM...&nbsp;&nbsp;<a href='http://www.cppblog.com/zmj/archive/2008/08/28/60258.html'>阅读全文</a><img src ="http://www.cppblog.com/zmj/aggbug/60258.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-08-28 13:39 <a href="http://www.cppblog.com/zmj/archive/2008/08/28/60258.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>The Graphics File Formats Page</title><link>http://www.cppblog.com/zmj/archive/2008/08/28/60238.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Thu, 28 Aug 2008 03:08:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/08/28/60238.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/60238.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/08/28/60238.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/60238.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/60238.html</trackback:ping><description><![CDATA[<p><strong><font size=6>3</font><font size=5>D</font> <font size=6>G</font><font size=5>eometry</font> <font size=6>S</font><font size=5>pecifications:</font> </strong>
<hr SIZE=3>
<font size=4><strong>
<dl>
<dd><a href="http://www.martinreddy.net/gfx/3d-hi.html">http://www.martinreddy.net/gfx/3d-hi.html</a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>3DS</strong> - <a href="http://www.martinreddy.net/gfx/3d/3DS.spec"><u><font color=#0000ff>The 3D Studio Format</font></u></a>
<dl>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball2.gif"> <strong>MLI</strong> - <a href="http://www.martinreddy.net/gfx/3d/MLI.spec"><u><font color=#0000ff>3D Studio's Material-Library Format</font></u></a> </dd></dl>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>BYU</strong> - <a href="http://www.martinreddy.net/gfx/3d/BYU.spec"><u><font color=#0000ff>Movie BYU file format</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>DEM</strong> - <a href="http://www-nmd.usgs.gov/www/ti/DEM/standards_dem.html"><u><font color=#0000ff>USGS Standards for Digital Elevation Models</font></u></a> [Link]
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>DXF</strong> - Used by Autodesk's AutoCAD
<dl>
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.mcwi.com/dxf13/dxf_01.html"><u><font color=#0000ff>DXF Release 13 specification</font></u></a> [Link]
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.martinreddy.net/gfx/3d/DXF12.spec"><u><font color=#0000ff>DXF Release 12 specification</font></u></a> / <a href="http://www.mcwi.com/dxf11-12/r12dxf_01.html"><u><font color=#0000ff>[Link]</font></u></a>
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.martinreddy.net/gfx/3d/DXF10.spec"><u><font color=#0000ff>DXF Release 10 specification</font></u></a> / <a href="http://www.mcwi.com/dxf10/r10dxf_01.html"><u><font color=#0000ff>[Link]</font></u></a>
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.martinreddy.net/gfx/3d/DXF.info"><u><font color=#0000ff>Creating DXF files</font></u></a> </dd></dl>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>FIG</strong> - <a href="http://www.martinreddy.net/gfx/3d/FIG.spec"><u><font color=#0000ff>Used by REND386/AVRIL</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>FLT</strong> - <a href="http://www.multigen-paradigm.com/support/dc_standards.shtml"><u><font color=#0000ff>MulitGen Inc.'s OpenFlight format</font></u></a> [link]
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>GLC</strong> - <a href="http://www.martinreddy.net/gfx/3d/GLC.spec"><u><font color=#0000ff>File format information</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>HDF</strong> - <a href="http://hdf.ncsa.uiuc.edu/"><u><font color=#0000ff>Hierarchical Data Format</font></u></a> [Link]
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>IGES</strong> - <a href="http://www.martinreddy.net/gfx/3d/IGES.info"><u><font color=#0000ff>Initial Graphics Exchange Specification</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>IV</strong> - <a href="http://www.cica.indiana.edu/graphics/object_specs/inventor/inventor.format.html"><u><font color=#0000ff>Open Inventor File Format Info</font></u></a> [Link]
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>LWLO</strong>, <strong>LWOB</strong> &amp; <strong>LWSC</strong> - Lightwave 3D file formats
<dl>
<dd><img alt=- src="http://www.martinreddy.net/gfx/img/ball2.gif"> <strong>LWLO</strong> - <a href="http://www.martinreddy.net/gfx/3d/LWLO.txt"><u><font color=#0000ff>Lightwave 3D Layered Object</font></u></a>
<dd><img alt=- src="http://www.martinreddy.net/gfx/img/ball2.gif"> <strong>LWOB</strong> - <a href="http://www.martinreddy.net/gfx/3d/LWOB.txt"><u><font color=#0000ff>Lightwave 3D Object</font></u></a>
<dd><img alt=- src="http://www.martinreddy.net/gfx/img/ball2.gif"> <strong>LWSC</strong> - <a href="http://www.martinreddy.net/gfx/3d/LWSC.txt"><u><font color=#0000ff>Lightwave 3D Scene</font></u></a> </dd></dl>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>MAZ</strong> - <a href="http://www.martinreddy.net/gfx/3d/MAZ.spec"><u><font color=#0000ff>Used by Division's dVS/dVISE</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>MGF</strong> - <a href="http://radsite.lbl.gov/mgf/HOME.html"><u><font color=#0000ff>Materials and Geometry Format</font></u></a> [Link]
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>MSDL</strong> - <a href="http://info.mcc.ac.uk/CGU/MSDL/documentation/msdl/msdl.html"><u><font color=#0000ff>Manchester Scene Description Language</font></u></a> [Link]
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>NFF</strong> &amp; <strong>ENFF</strong> - (Extended) Neutral File Format
<dl>
<dd><img alt=- src="http://www.martinreddy.net/gfx/img/ball2.gif"> <strong>NFF</strong> - <a href="http://www.martinreddy.net/gfx/3d/NFF2.spec"><u><font color=#0000ff>Scene description language by Eric Haines</font></u></a>
<dd><img alt=- src="http://www.martinreddy.net/gfx/img/ball2.gif"> <strong>NFF</strong> - <a href="http://www.martinreddy.net/gfx/3d/NFF.spec"><u><font color=#0000ff>Used by Sense8's WorldToolKit</font></u></a>
<dd><img alt=- src="http://www.martinreddy.net/gfx/img/ball2.gif"> <strong>ENFF</strong> - <a href="http://www.martinreddy.net/gfx/3d/ENFF.spec"><u><font color=#0000ff>Extensions to Eric Haines' NFF</font></u></a> </dd></dl>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>OBJ</strong> - <a href="http://www.martinreddy.net/gfx/3d/OBJ.spec"><u><font color=#800080>Wavefront Object Files</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>OFF</strong> - <a href="http://www.martinreddy.net/gfx/3d/OFF.spec"><u><font color=#0000ff>A 3D mesh Object File Format</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>OOGL</strong> - <a href="http://www.martinreddy.net/gfx/3d/OOGL.spec"><u><font color=#0000ff>Object Oriented Graphics Library</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>PLG</strong> - <a href="http://www.martinreddy.net/gfx/3d/PLG.spec"><u><font color=#0000ff>Used by REND386/AVRIL</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>POV</strong> - <a href="http://www.martinreddy.net/gfx/3d/POV.spec"><u><font color=#0000ff>Persistence of Vision ray-tracer</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>QD3D</strong> - <a href="http://product.info.apple.com/qd3d/QD3DMetaFile/3DMetafileRefTOC.html"><u><font color=#0000ff>Apple's QuickDraw 3D Metafile format</font></u></a> [Link]
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>TDDD</strong> - <a href="http://www.martinreddy.net/gfx/3d/TDDD.spec"><u><font color=#0000ff>Used by the Imagine &amp; Turbo Silver ray-tracers</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>VIZ</strong> - <a href="http://www.martinreddy.net/gfx/3d/VIZ.spec"><u><font color=#0000ff>Used by Division's dVS/dVISE</font></u></a>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>VRML</strong> - Virtual Reality Modeling Language
<dl>
<dd><img alt=- src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.web3d.org/technicalinfo/specifications/vrml97/index.htm"><u><font color=#0000ff>VRML97 ISO Specification</font></u></a> [Link]
<dd><img alt=- src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.vrml.org/VRML1.0/vrml10c.html"><u><font color=#0000ff>Version 1.0 Specification</font></u></a> / <a href="http://www.martinreddy.net/gfx/3d/VRML.spec"><u><font color=#0000ff>[Link]</font></u></a> </dd></dl>
<dd><img alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif"> <strong>WLD</strong> - <a href="http://www.martinreddy.net/gfx/3d/WLD.spec"><u><font color=#0000ff>Used by REND386/AVRIL</font></u></a> </dd></dl></strong></font><img alt=Separator src="http://www.martinreddy.net/gfx/img/line-rainbow.gif">
<p><strong><font size=6>M</font><font size=5>oving</font> <font size=6>I</font><font size=5>mage</font> <font size=6>R</font><font size=5>esources:</font> </strong>
<hr SIZE=3>
<font size=4><strong>
<dl>
<dd><img height=14 alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif" width=14> <strong>MPEG</strong> - Moving Picture Expert Group
<dl>
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.mpeg1.de/"><u><font color=#0000ff>The MPEG-1 Archive</font></u></a> and <a href="http://www.mpeg2.de/"><u><font color=#0000ff>The MPEG-2 Archive</font></u></a> [Link]
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.cs.ubc.ca/spider/ladic/mpeg.html"><u><font color=#0000ff>Lance Ladic's Info on the MPEG Format</font></u></a> [Link]
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.mpeg.org/"><u><font color=#0000ff>MPEG Resources on the Web</font></u></a> [Link]
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.tardis.ed.ac.uk/~ark/mpegelib/"><u><font color=#0000ff>MPEGe Lib: A library to help create MPEG movies</font></u></a> [Link] </dd></dl>
<dd><img height=14 alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif" width=14> <strong>QuickTime</strong> - Info on QuickTime Movies
<dl>
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://quicktime.apple.com/"><u><font color=#0000ff>Apple's QuickTime Continuum</font></u></a> [Link]
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.cs.ubc.ca/spider/ladic/qtime.html"><u><font color=#0000ff>Lance Ladic's Info on the QuickTime Format</font></u></a> [Link]
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.astro.nwu.edu/lentz/mac/qt/"><u><font color=#0000ff>QuickTime players for a number of platforms</font></u></a> [Link] </dd></dl>
<dd><img height=14 alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif" width=14> <strong>FLI/FLC</strong> - Autodesk's Flic Animation format
<dl>
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.martinreddy.net/gfx/anim/FLI.txt"><u><font color=#0000ff>Flic format description</font></u></a>
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.martinreddy.net/gfx/anim/FLC.txt"><u><font color=#0000ff>Further Flic format description</font></u></a> </dd></dl>
<dd><img height=14 alt=* src="http://www.martinreddy.net/gfx/img/ball1.gif" width=14> <strong>AVI</strong> - Microsoft's Audio Video Interleave format
<dl>
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.cs.ubc.ca/spider/ladic/avi.html"><u><font color=#0000ff>Lance Ladic's Info on the AVI Format</font></u></a> [Link]
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.matrox.com/videoweb/odmlff2.htm"><u><font color=#0000ff>OpenDML AVI File Format Extensions V1.0</font></u></a> [Link]
<dd><img alt=. src="http://www.martinreddy.net/gfx/img/ball2.gif"> <a href="http://www.nctech.fr/NCTech/html/English/ConfigAVI.html"><u><font color=#0000ff>Short Overview of AVI features</font></u></a> [Link] </dd></dl></dd></dl></strong></font><img alt=Separator src="http://www.martinreddy.net/gfx/img/line-rainbow.gif">
<center><strong>
<p><a href="http://www.martinreddy.net/gfx/index-hi.html"><u><font color=#0000ff>Graphics File Formats Home Page</font></u></a> / <a href="http://www.martinreddy.net/gfx/3d-lo.html"><u><font color=#0000ff>Low-Res Version of This Page</font></u></a>
<p><a href="http://www.martinreddy.net/gfx/2d-hi.html"><u><font color=#0000ff>2D Specs</font></u></a> / <a href="http://www.martinreddy.net/gfx/utils-hi.html"><u><font color=#0000ff>Utils &amp; Info</font></u></a> / <a href="http://www.martinreddy.net/gfx/credits-hi.html"><u><font color=#0000ff>Credits</font></u></a>
<p>N.B. If you are interested in graphics viewers/converters for a particular format, please check the <a href="http://www.martinreddy.net/gfx/faqs/FileFormats.faq"><u><font color=#0000ff>File Formats FAQ</font></u></a> and the <a href="http://www.public.iastate.edu/~stark/gutil_sv.html"><u><font color=#0000ff>Graphics Utils' Site &amp; Version FAQ</font></u></a>. </strong></center>
<hr>
<center><font size=2>Last Updated: 27 Jun, 1997. HTML code checked with weblint V1.017. Contains Netscape extensions.</font></center>
<img src ="http://www.cppblog.com/zmj/aggbug/60238.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-08-28 11:08 <a href="http://www.cppblog.com/zmj/archive/2008/08/28/60238.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>设计模式之Observer</title><link>http://www.cppblog.com/zmj/archive/2008/08/27/60129.html</link><dc:creator>zmj</dc:creator><author>zmj</author><pubDate>Wed, 27 Aug 2008 03:17:00 GMT</pubDate><guid>http://www.cppblog.com/zmj/archive/2008/08/27/60129.html</guid><wfw:comment>http://www.cppblog.com/zmj/comments/60129.html</wfw:comment><comments>http://www.cppblog.com/zmj/archive/2008/08/27/60129.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/zmj/comments/commentRss/60129.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/zmj/services/trackbacks/60129.html</trackback:ping><description><![CDATA[<p><a href="http://www.jdon.com/designpatterns/observer.htm">http://www.jdon.com/designpatterns/observer.htm</a><br>Java深入到一定程度,就不可避免的碰到设计模式(design pattern)这一概念,了解设计模式,将使自己对java中的接口或抽象类应用有更深的理解.设计模式在java的中型系统中应用广泛,遵循一定的编程模式,才能使自己的代码便于理解,易于交流,Observer(观察者)模式是比较常用的一个模式,尤其在界面设计中应用广泛,而本站所关注的是Java在电子商务系统中应用,因此想从电子商务实例中分析Observer的应用.</p>
<p>虽然网上商店形式多样,每个站点有自己的特色,但也有其一般的共性,单就"商品的变化,以便及时通知订户"这一点,是很多网上商店共有的模式,这一模式类似Observer patern观察者模式.</p>
<p>具体的说,如果网上商店中商品在名称 价格等方面有变化,如果系统能自动通知会员,将是网上商店区别传统商店的一大特色.这就需要在商品product中加入Observer这样角色,以便product细节发生变化时,Observer能自动观察到这种变化,并能进行及时的update或notify动作.</p>
<p><img height=323 src="http://www.jdon.com/designpatterns/images/observer1.jpg" width=443 p="100" h="323" w="443"></p>
<p>Java的API还为为我们提供现成的Observer接口Java.util.Observer.我们只要直接使用它就可以.</p>
<p>我们必须extends Java.util.Observer才能真正使用它:<br>1.提供Add/Delete observer的方法;<br>2.提供通知(notisfy) 所有observer的方法;<br></p>
<table cellSpacing=3 cellPadding=3 width="80%" bgColor=#cccccc border=0>
    <tbody>
        <tr>
            <td>//产品类 可供Jsp直接使用UseBean调用 该类主要执行产品数据库插入 更新<br>public class product extends Observable{
            <p>　　private String name;<br>　　private float price;</p>
            <p>　　public String getName(){ return name;}<br>　　public void setName(String name){<br>　　 this.name=name;<br>　　//设置变化点 <br>　　 setChanged();<br>　　 notifyObservers(name);</p>
            <p>　　}　　　</p>
            <p>　　public float getPrice(){ return price;}<br>　　public void setPrice(float price){<br>　　 this.price=price;<br>　　//设置变化点<br>　　 setChanged();<br>　　 notifyObservers(new Float(price)); </p>
            <p>　　}<br><br>　　//以下可以是数据库更新 插入命令.<br>　　public void saveToDb(){<br>　　.....................<br></p>
            <p>}</p>
            </td>
        </tr>
    </tbody>
</table>
<p><br>我们注意到,在product类中 的setXXX方法中,我们设置了 notify(通知)方法, 当Jsp表单调用setXXX(如何调用见我的<a href="http://www.jdon.com/idea/数据库bean.htm" target=_blank><u><font color=#0000ff>另外一篇文章</font></u></a>),实际上就触发了notisfyObservers方法,这将通知相应观察者应该采取行动了.</p>
<p>下面看看这些观察者的代码,他们究竟采取了什么行动:</p>
<table cellSpacing=3 cellPadding=3 width="99%" border=0>
    <tbody>
        <tr>
            <td bgColor=#cccccc>
            <p>//观察者NameObserver主要用来对产品名称(name)进行观察的<br>public class NameObserver implements Observer{</p>
            <p>　　private String name=null;</p>
            <p>　　public void update(Observable obj,Object arg){<br><br>　　　　if (arg <a href="http://www-900.ibm.com/developerWorks/java/l-leditor/index.shtml" target=_blank><u><font color=#0000ff>instanceof</font></u></a> String){</p>
            <p>　　　　 name=(String)arg;<br>　　　　 //产品名称改变值在name中<br>　　　　 System.out.println("NameObserver :name changet to "+name);</p>
            <p>　　　　}<br></p>
            <p>　　}</p>
            <p>}</p>
            <p>//观察者PriceObserver主要用来对产品价格(price)进行观察的<br>public class PriceObserver implements Observer{</p>
            <p>　　private float price=0;</p>
            <p>　　public void update(Observable obj,Object arg){<br><br>　　　　if (arg instanceof Float){</p>
            <p>　　　　 price=((Float)arg).floatValue();<br>　　<br>　　　　 System.out.println("PriceObserver :price changet to "+price);</p>
            <p>　　　　}<br></p>
            <p>　　}</p>
            <p>}</p>
            </td>
        </tr>
    </tbody>
</table>
<p><br>Jsp中我们可以来正式执行这段观察者程序:</p>
<table cellSpacing=3 cellPadding=3 width="96%" border=0>
    <tbody>
        <tr>
            <td bgColor=#cccccc>
            <p><strong>&lt;jsp:useBean id="product" scope="session" class="Product" /&gt;<br>&lt;jsp:setProperty name="product" property="*" /&gt;</strong></p>
            <p><strong>&lt;jsp:useBean id="nameobs" scope="session" class="NameObserver" /&gt;<br>&lt;jsp:setProperty name="product" property="*" /&gt;</strong></p>
            <p><strong>&lt;jsp:useBean id="priceobs" scope="session" class="PriceObserver" /&gt;<br>&lt;jsp:setProperty name="product" property="*" /&gt;</strong></p>
            <p>&lt;%<br><br>if (request.getParameter("save")!=null)<br>{ <br>　　product.saveToDb();<br><br><br>　　out.println("产品数据变动 保存! 并已经自动通知客户"); </p>
            <p>}else{<br><br>　　//加入观察者<br>　　product.addObserver(<strong>nameobs</strong>);<br><br>　　product.addObserver(<strong>priceobs</strong>);</p>
            <p>%&gt;</p>
            <p>　　//request.getRequestURI()是产生本jsp的程序名,就是自己调用自己<br>　　&lt;form action="&lt;%=request.getRequestURI()%&gt;" method=post&gt;</p>
            <p>　　&lt;input type=hidden name="save" value="1"&gt;<br>　　产品名称:&lt;input type=text name="name" &gt;<br>　　产品价格:&lt;input type=text name="price"&gt;<br>　　&lt;input type=submit&gt;</p>
            <p>　　&lt;/form&gt;</p>
            <p>&lt;%<br><br>} </p>
            <p>%&gt;</p>
            <p>&nbsp;</p>
            <p>&nbsp;</p>
            <p>&nbsp;</p>
            </td>
        </tr>
    </tbody>
</table>
<p>执行改Jsp程序,会出现一个表单录入界面, 需要输入产品名称 产品价格, 点按Submit后,还是执行该jsp的<br>if (request.getParameter("save")!=null)之间的代码.<br><br><br>由于这里使用了数据javabeans的自动赋值概念,实际程序自动执行了setName setPrice语句.你会在服务器控制台中发现下面信息::<br><strong><br>NameObserver :name changet to ?????(Jsp表单中输入的产品名称)<br><br>PriceObserver :price changet to ???(Jsp表单中输入的产品价格);</strong></p>
<p>这说明观察者已经在行动了.!!<br>同时你会在执行jsp的浏览器端得到信息:<br><br><strong>产品数据变动 保存! 并已经自动通知客户</strong> <br><br></p>
<p>上文由于使用jsp概念,隐含很多自动动作,现将调用观察者的Java代码写如下:</p>
<table cellSpacing=3 cellPadding=3 width="80%" bgColor=#cccccc border=0>
    <tbody>
        <tr>
            <td>
            <p>&nbsp;</p>
            <p>public class Test {</p>
            <p>　　public static void main(String args[]){</p>
            <p>Product product=new Product();<br><br>NameObserver nameobs=new NameObserver();<br>PriceObserver priceobs=new PriceObserver();</p>
            <p>//加入观察者<br>product.addObserver(nameobs);<br>product.addObserver(priceobs);</p>
            <p>product.setName("橘子红了");<br>product.setPrice(9.22f); </p>
            <p>　　}</p>
            <p>}</p>
            <p>&nbsp;</p>
            <p>&nbsp;</p>
            <p>&nbsp;</p>
            </td>
        </tr>
    </tbody>
</table>
<p>你会在发现下面信息::<br><strong><br>NameObserver :name changet to 橘子红了<br><br>PriceObserver :price changet to 9.22</strong></p>
<p>这说明观察者在行动了.!!</p>
<p>&nbsp;</p>
<h2><a href="http://www.jdon.com/jivejdon/key/observer" target=_blank><u><font color=#0000ff>更多相关话题讨论</font></u></a></h2>
<img src ="http://www.cppblog.com/zmj/aggbug/60129.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/zmj/" target="_blank">zmj</a> 2008-08-27 11:17 <a href="http://www.cppblog.com/zmj/archive/2008/08/27/60129.html#Feedback" targ