source: OGRE/trunk/ogrenew/Docs/manual/manual_19.html @ 657

Revision 657, 20.5 KB checked in by mattausch, 19 years ago (diff)

added ogre dependencies and patched ogre sources

Line 
1<HTML>
2<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
3<!-- Created on , 12 2006 by texi2html 1.64 -->
4<!--
5Written by: Lionel Cons <Lionel.Cons@cern.ch> (original author)
6            Karl Berry  <karl@freefriends.org>
7            Olaf Bachmann <obachman@mathematik.uni-kl.de>
8            and many others.
9Maintained by: Olaf Bachmann <obachman@mathematik.uni-kl.de>
10Send bugs and suggestions to <texi2html@mathematik.uni-kl.de>
11 
12-->
13<HEAD>
14<TITLE>OGRE Manual v1.0.7: Declaring Vertex and Fragment Programs</TITLE>
15
16<META NAME="description" CONTENT="OGRE Manual v1.0.7: Declaring Vertex and Fragment Programs">
17<META NAME="keywords" CONTENT="OGRE Manual v1.0.7: Declaring Vertex and Fragment Programs">
18<META NAME="resource-type" CONTENT="document">
19<META NAME="distribution" CONTENT="global">
20<META NAME="Generator" CONTENT="texi2html 1.64">
21<LINK TYPE="text/css" rel="stylesheet" href="../style.css"> 
22</HEAD>
23
24<BODY LANG="" BGCOLOR="#FFFFFF" TEXT="#000000" LINK="#0000FF" VLINK="#800080" ALINK="#FF0000">
25
26<A NAME="SEC76"></A>
27<TABLE CELLPADDING=1 CELLSPACING=1 BORDER=0>
28<TR><TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="manual_18.html#SEC54"> &lt; </A>]</TD>
29<TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="manual_15.html#SEC24"> Up </A>]</TD>
30<TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="manual_20.html#SEC86"> &gt; </A>]</TD>
31<TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="index.html#SEC_Top">Top</A>]</TD>
32<TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="manual_toc.html#SEC_Contents">Contents</A>]</TD>
33<TD VALIGN="MIDDLE" ALIGN="LEFT">[Index]</TD>
34<TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="manual_abt.html#SEC_About"> ? </A>]</TD>
35</TR></TABLE>
36<HR SIZE=1>
37<H3> 3.1.4 Declaring Vertex and Fragment Programs </H3>
38<!--docid::SEC76::-->
39<P>
40
41In order to use a vertex or fragment program in your materials (See section <A HREF="manual_20.html#SEC86">3.1.5 Using Vertex and Fragment Programs in a Pass</A>), you first have to define them. A single program definition can be used by any number of materials, the only prerequisite is that a program must be defined before being referenced in the pass section of a material.<BR><BR>
42</P><P>
43
44The definition of a program can either be embedded in the .material script itself (in which case it must precede any references to it in the script), or if you wish to use the same program across multiple .material files, you can define it in an external .program script. You define the program in exactly the same way whether you use a .program script or a .material script, the only difference is that all .program scripts are guaranteed to have been parsed before <STRONG>all</STRONG> .material scripts, so you can guarantee that your program has been defined before any .material script that might use it. Just like .material scripts, .program scripts will be read from any location which is on your resource path, and you can define many programs in a single script.<BR><BR>
45</P><P>
46
47Vertex and fragment programs can be low-level (i.e. assembler code written to the specification of a given low level syntax such as vs_1_1 or arbfp1) or high-level such as nVidia's Cg language (See section <A HREF="manual_19.html#SEC78">High-level Programs</A>). High level languages give you a number of advantages, such as being able to write more intuitive code, and possibly being able to target multiple architectures in a single program (for example, the same Cg program might be able to be used in both D3D and GL, whilst the equivalent low-level programs would require separate techniques, each targetting a different API). High-level programs also allow you to use named parameters instead of simply indexed ones, although parameters are not defined here, they are used in the Pass.<BR><BR>
48</P><P>
49
50Here is an example of a definition of a low-level vertex program:
51<TABLE><tr><td>&nbsp;</td><td class=example><pre>vertex_program myVertexProgram asm
52{
53    source myVertexProgram.asm
54    syntax vs_1_1
55}
56</pre></td></tr></table>As you can see, that's very simple, and defining a fragment program is exactly the same, just with vertex_program replaced with fragment_program. You give the program a name in the header, followed by the word 'asm' to indicate that this is a low-level program. Inside the braces, you specify where the source is going to come from (and this is loaded from any of the resource locations as with other media), and also indicate the syntax being used. You might wonder why the syntax specification is required when many of the assembler syntaxes have a header identifying them anyway - well the reason is that the engine needs to know what syntax the program is in before reading it, because during compilation of the material, we want to skip progams which use an unsupportable syntax quickly, without loading the program first.<BR><BR>
57</P><P>
58
59The current supported syntaxes are:
60<DL COMPACT>
61<DT>vs_1_1
62<DD>This is one of the DirectX vertex shader assembler syntaxes. <BR>
63Supported on cards from: ATI Radeon 8500, nVidia GeForce 3 <BR>
64<DT>vs_2_0
65<DD>Another one of the DirectX vertex shader assembler syntaxes. <BR>
66Supported on cards from: ATI Radeon 9600, nVidia GeForce FX 5 series <BR>
67<DT>vs_2_x
68<DD>Another one of the DirectX vertex shader assembler syntaxes. <BR>
69Supported on cards from: ATI Radeon X series, nVidia GeForce FX 6 series <BR>
70<DT>vs_3_0
71<DD>Another one of the DirectX vertex shader assembler syntaxes. <BR>
72Supported on cards from: nVidia GeForce FX 6 series
73<DT>arbvp1
74<DD>This is the OpenGL standard assembler format for vertex programs. It's roughly equivalent to DirectX vs_1_1.
75<DT>vp20
76<DD>This is an nVidia-specific OpenGL vertex shader syntax which is a superset of vs 1.1.
77<DT>vp30
78<DD>Another nVidia-specific OpenGL vertex shader syntax. It is a superset of vs 2.0, which is supported on nVidia GeForce FX 5 series and higher.
79<DT>vp40
80<DD>Another nVidia-specific OpenGL vertex shader syntax. It is a superset of vs 3.0, which is supported on nVidia GeForce FX 6 series and higher.
81<DT>ps_1_1, ps_1_2, ps_1_3
82<DD>DirectX pixel shader (ie fragment program) assembler syntax. <BR>
83Supported on cards from: ATI Radeon 8500, nVidia GeForce 3 <BR>
84NOTE: for ATI 8500, 9000, 9100, 9200 hardware, this profile can also be used in OpenGL.  The ATI 8500 to 9200 do not support arbfp1 but do support atifs extension in OpenGL which is very similar in function to ps_1_4 in DirectX.  Ogre has a built in ps_1_x to atifs compiler that is automatically invoked when ps_1_x is used in OpenGL on ATI hardware.
85<DT>ps_1_4
86<DD>DirectX pixel shader (ie fragment program) assembler syntax. <BR>
87Supported on cards from: ATI Radeon 8500, nVidia GeForce FX 5 series <BR>
88NOTE: for ATI 8500, 9000, 9100, 9200 hardware, this profile can also be used in OpenGL.  The ATI 8500 to 9200 do not support arbfp1 but do support atifs extension in OpenGL which is very similar in function to ps_1_4 in DirectX.  Ogre has a built in ps_1_x to atifs compiler that is automatically invoked when ps_1_x is used in OpenGL on ATI hardware.
89<DT>ps_2_0
90<DD>DirectX pixel shader (ie fragment program) assembler syntax. <BR>
91Supported cards: ATI Radeon 9600, nVidia GeForce FX 5 series<BR>
92<DT>ps_2_x
93<DD>DirectX pixel shader (ie fragment program) assembler syntax. This is basically
94ps_2_0 with a higher number of instructions. <BR>
95Supported cards: ATI Radeon X series, nVidia GeForce FX 6 series<BR>
96<DT>ps_3_0
97<DD>DirectX pixel shader (ie fragment program) assembler syntax. <BR>
98Supported cards: nVidia GeForce FX6 series<BR>
99<DT>ps_3_x
100<DD>DirectX pixel shader (ie fragment program) assembler syntax. <BR>
101Supported cards: nVidia GeForce FX7 series<BR>
102<DT>arbfp1
103<DD>This is the OpenGL standard assembler format for fragment programs. It's roughly equivalent to ps_2_0, which means that not all cards that support basic pixel shaders under DirectX support arbfp1 (for example neither the GeForce3 or GeForce4 support arbfp1, but they do support ps_1_1).
104<DT>fp20
105<DD>This is an nVidia-specific OpenGL fragment syntax which is a superset of ps 1.3. It allows you to use the 'nvparse' format for basic fragment programs. It actually uses NV_texture_shader and NV_register_combiners to provide functionality equivalent to DirectX's ps_1_1 under GL, but only for nVidia cards. However, since ATI cards adopted arbfp1 a little earlier than nVidia, it is mainly nVidia cards like the GeForce3 and GeForce4 that this will be useful for. You can find more information about nvparse at http://developer.nvidia.com/object/nvparse.html.
106<DT>fp30
107<DD>Another nVidia-specific OpenGL fragment shader syntax. It is a superset of ps 2.0, which is supported on nVidia GeForce FX 5 series and higher.
108<DT>fp40
109<DD>Another nVidia-specific OpenGL fragment shader syntax. It is a superset of ps 3.0, which is supported on nVidia GeForce FX 6 series and higher.
110<P>
111
112</DL>
113<P>
114
115You can get a definitive list of the syntaxes supported by the current card by calling GpuProgramManager::getSingleton().getSupportedSyntax().<BR><BR>
116</P><P>
117
118<A NAME="Default Program Parameters"></A>
119<A NAME="SEC77"></A>
120<H3> Default Program Parameters </H3>
121<!--docid::SEC77::-->
122While defining a vertex or fragment program, you can also specify the default parameters to be used for materials which use it, unless they specifically override them. You do this by including a nested 'default_params' section, like so:
123<TABLE><tr><td>&nbsp;</td><td class=example><pre>vertex_program Ogre/CelShadingVP cg
124{
125        source Example_CelShading.cg
126        entry_point main_vp
127        profiles vs_1_1 arbvp1
128
129        default_params
130        {
131                param_named_auto lightPosition light_position_object_space 0
132                param_named_auto eyePosition camera_position_object_space
133                param_named_auto worldViewProj worldviewproj_matrix
134                param_named shininess float 10
135        }
136}
137</pre></td></tr></table>The syntax of the parameter definition is exactly the same as when you define parameters when using programs, See  <A HREF="manual_20.html#Program Parameter Specification">Program Parameter Specification</A>. Defining default parameters allows you to avoid rebinding common parameters repeatedly (clearly in the above example, all but 'shininess' are unlikely to change between uses of the program) which makes your material declarations shorter.
138<P>
139
140<A NAME="High-level Programs"></A>
141<A NAME="SEC78"></A>
142<H2> High-level Programs </H2>
143<!--docid::SEC78::-->
144Support for high level vertex and fragment programs is provided through plugins; this is to make sure that an application using OGRE can use as little or as much of the high-level program functionality as they like. OGRE currently supports 3 high-level program types, Cg (an API- and card-independent, high-level language which lets you write programs for both OpenGL and DirectX for lots of cards), DirectX 9 High-Level Shader Language (HLSL), and OpenGL Shader Language (GLSL). HLSL is provided for people who only want to deploy in DirectX, or who don't want to include the Cg plugin for whatever reason. GLSL is only for the OpenGL API and can not be used with the DirectX api.  To support both DirectX and OpenGL you could write your shaders in both HLSL and GLSL along with having seperate techniques in the material script.  To be honest, Cg is a better bet because it lets you stay API independent - and don't be put off by the fact that it's made by nVidia, it will happily compile programs down to vendor-independent standards like DirectX and OpenGL's assembler formats, so you're not limited to nVidia cards.<BR><BR>
145<P>
146
147<A NAME="SEC79"></A>
148<H3> Cg programs </H3>
149<!--docid::SEC79::-->
150In order to define Cg programs, you have to have to load Plugin_CgProgramManager.so/.dll at startup, either through plugins.cfg or through your own plugin loading code. They are very easy to define:
151<TABLE><tr><td>&nbsp;</td><td class=example><pre>fragment_program myCgFragmentProgram cg
152{
153    source myCgFragmentProgram.cg
154    entry_point main
155    profiles ps_2_0 arbfp1
156}
157</pre></td></tr></table>There are a few differences between this and the assembler program - to begin with, we declare that the fragment program is of type 'cg' rather than 'asm', which indicates that it's a high-level program using Cg. The 'source' parameter is the same, except this time it's referencing a Cg source file instead of a file of assembler. <BR><BR>
158Here is where things start to change. Firstly, we need to define an 'entry_point', which is the name of a function in the Cg program which will be the first one called as part of the fragment program. Unlike assembler programs, which just run top-to-bottom, Cg programs can include multiple functions and as such you must specify the one which start the ball rolling.<BR><BR>
159Next, instead of a fixed 'syntax' parameter, you specify one or more 'profiles'; profiles are how Cg compiles a program down to the low-level assembler. The profiles have the same names as the assembler syntax codes mentioned above; the main difference is that you can list more than one, thus allowing the program to be compiled down to more low-level syntaxes so you can write a single high-level program which runs on both D3D and GL. You are advised to just enter the simplest profiles under which your programs can be compiled in order to give it the maximum compatibility. The ordering also matters; if a card supports more than one syntax then the one listed first will be used.
160<P>
161
162<A NAME="SEC80"></A>
163<H3> DirectX9 HLSL </H3>
164<!--docid::SEC80::-->
165DirectX9 HLSL has a very similar language syntax to Cg but is tied to the DirectX API. The only benefit over Cg is that it only requires the DirectX 9 render system plugin, not any additional plugins. Declaring a DirectX9 HLSL program is very similar to Cg. Here's an example:
166<TABLE><tr><td>&nbsp;</td><td class=example><pre>vertex_program myHLSLVertexProgram hlsl
167{
168    source myHLSLVertexProgram.txt
169    entry_point main
170    target vs_2_0
171}
172</pre></td></tr></table>As you can see, the syntax is almost identical, except that instead of 'profiles' with a list of assembler formats, you have a 'target' parameter which allows a single assembler target to be specified - obviously this has to be a DirectX assembler format syntax code.<BR><BR>
173<P>
174
175<A NAME="SEC81"></A>
176<H3> OpenGL GLSL </H3>
177<!--docid::SEC81::-->
178OpenGL GLSL has a similar language syntax to HLSL but is tied to the OpenGL API. The are a few benefits over Cg in that it only requires the OpenGL render system plugin, not any additional plugins. Declaring a OpenGL GLSL program is similar to Cg but simpler. Here's an example:
179<TABLE><tr><td>&nbsp;</td><td class=example><pre>vertex_program myGLSLVertexProgram glsl
180{
181    source myGLSLVertexProgram.txt
182}
183</pre></td></tr></table>In GLSL, no entry point needs to be defined since it is always 'main()' and there is no target definition since GLSL source is compiled into native GPU code and not intermediate assembly. <BR><BR>
184<P>
185
186GLSL supports the use of modular shaders.  This means you can write GLSL external functions that can be used in multiple shaders.
187</P><P>
188
189<TABLE><tr><td>&nbsp;</td><td class=example><pre>vertex_program myExteranalGLSLFunction1 glsl
190{
191    source myExternalGLSLfunction1.txt
192}
193
194vertex_program myExteranalGLSLFunction2 glsl
195{
196    source myExternalGLSLfunction2.txt
197}
198
199vertex_program myGLSLVertexProgram1 glsl
200{
201    source myGLSLfunction.txt
202    attach myExteranalGLSLFunction1 myExteranalGLSLFunction2
203}
204
205vertex_program myGLSLVertexProgram2 glsl
206{
207    source myGLSLfunction.txt
208    attach myExteranalGLSLFunction1
209}
210</pre></td></tr></table></P><P>
211
212External GLSL functions are attached to the program that needs them by using 'attach' and including the names of all external programs required on the same line seperated by spaces.  This can be done for both vertex and fragment programs.
213</P><P>
214
215<A NAME="SEC82"></A>
216<H3> GLSL Texture Samplers </H3>
217<!--docid::SEC82::-->
218To pass texture unit index values from the material script to texture samplers in glsl use 'int' type named parameters.  See the example below:<BR>
219<P>
220
221excerpt from GLSL example.frag source:
222<TABLE><tr><td>&nbsp;</td><td class=example><pre>varying vec2 UV;
223uniform sampler2D diffuseMap;
224
225void main(void)
226{
227        gl_FragColor = texture2D(diffuseMap, UV);
228}
229</pre></td></tr></table></P><P>
230
231In material script:
232<TABLE><tr><td>&nbsp;</td><td class=example><pre>fragment_program myFragmentShader glsl
233{
234  source example.frag
235}
236
237material exampleGLSLTexturing
238{
239  technique
240  {
241    pass
242    {
243      fragment_program_ref myFragmentShader
244      {
245        param_named diffuseMap int 0
246      }
247
248      texture_unit
249      {
250        texture myTexture.jpg 2d
251      }
252    }
253  }
254}
255</pre></td></tr></table></P><P>
256
257An index value of 0 refers to the first texture unit in the pass, an index value of 1 refers to the second unit in the pass and so on.<BR><BR>
258</P><P>
259
260<A NAME="SEC83"></A>
261<H3> Accessing OpenGL states in GLSL </H3>
262<!--docid::SEC83::-->
263GLSL can access most of the GL states directly so you do not need to pass these states through <A HREF="manual_20.html#SEC91">param_named_auto</A> in the material script.  This includes lights, material state, and all the matrices used in the openGL state ie model view matrix, worldview projection matrix etc. <BR><BR><P>
264
265<A NAME="SEC84"></A>
266<H3> Skeletal Animation in Vertex Programs </H3>
267<!--docid::SEC84::-->
268You can implement skeletal animation in hardware by writing a vertex program which uses the per-vertex blending indices and blending weights, together with an array of world matrices (which will be provided for you by Ogre if you bind the automatic parameter 'world_matrix_array_3x4'). However, you need to communicate this support to Ogre so it does not perform skeletal animation in software for you. You do this by adding the following attribute to your vertex_program definition:
269<TABLE><tr><td>&nbsp;</td><td class=example><pre>       includes_skeletal_animation true
270</pre></td></tr></table>When you do this, any skeletally animated entity which uses this material will forgo the usual animation blend and will expect the vertex program to do it, for both vertex positions and normals.
271<P>
272
273<A NAME="SEC85"></A>
274<H3> Vertex Programs With Shadows </H3>
275<!--docid::SEC85::-->
276When using shadows (See section <A HREF="manual_57.html#SEC212">7. Shadows</A>), the use of vertex programs can add some additional complexities, because Ogre can only automatically deal with everything when using the fixed-function pipeline. If you use vertex programs, and you are also using shadows, you may need to make some adjustments. <BR><BR>
277<P>
278
279If you use <STRONG>stencil shadows</STRONG>, then any vertex programs which do vertex deformation can be a problem, because stencil shadows are calculated on the CPU, which does not have access to the modified vertices. If the vertex program is doing standard skeletal animation, this is ok (see section above) because Ogre knows how to replicate the effect in software, but any other vertex deformation cannot be replicated, and you will either have to accept that the shadow will not reflect this deformation, or you should turn off shadows for that object. <BR><BR>
280</P><P>
281
282If you use <STRONG>texture shadows</STRONG>, then vertex deformation is acceptable; however, when rendering the object into the shadow texture (the shadow caster pass), the shadow has to be rendered in a solid colour (linked to the ambient colour). You must therefore provide an alternative vertex program, so Ogre provides you with a way of specifying one to use when rendering the caster, See section <A HREF="manual_20.html#SEC92">Shadows and Vertex Programs</A>.
283</P><P>
284
285<A NAME="Using Vertex and Fragment Programs in a Pass"></A>
286<HR SIZE=1>
287<TABLE CELLPADDING=1 CELLSPACING=1 BORDER=0>
288<TR><TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="manual_18.html#SEC54"> &lt; </A>]</TD>
289<TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="manual_15.html#SEC24"> Up </A>]</TD>
290<TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="manual_20.html#SEC86"> &gt; </A>]</TD>
291<TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT"> &nbsp; <TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="index.html#SEC_Top">Top</A>]</TD>
292<TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="manual_toc.html#SEC_Contents">Contents</A>]</TD>
293<TD VALIGN="MIDDLE" ALIGN="LEFT">[Index]</TD>
294<TD VALIGN="MIDDLE" ALIGN="LEFT">[<A HREF="manual_abt.html#SEC_About"> ? </A>]</TD>
295</TR></TABLE>
296<BR> 
297<FONT SIZE="-1">
298This document was generated
299by <I>Steve Streeting</I> on <I>, 12 2006</I>
300using <A HREF="http://www.mathematik.uni-kl.de/~obachman/Texi2html
301"><I>texi2html</I></A>
302
303</BODY>
304</HTML>
Note: See TracBrowser for help on using the repository browser.