\input texinfo   @c -*-texinfo-*-
@c %**start of header
@setfilename manual.info
@settitle OGRE Manual v1.4 ('Eihort')
@c %**end of header
   
@titlepage
@title OGRE Manual
@author Steve Streeting
@page
@vskip 0pt plus 1filll
Copyright @copyright{} The OGRE Team@*@*

Permission is granted to make and distribute verbatim
copies of this manual provided the copyright notice and
this permission notice are preserved on all copies.@*@*

Permission is granted to copy and distribute modified
versions of this manual under the conditions for verbatim
copying, provided that the entire resulting derived work is
distributed under the terms of a permission notice
identical to this one.@*@*
@end titlepage

@node Top
@top OGRE Manual
Copyright @copyright{} The OGRE Team@*@*


This work is licenced under the Creative Commons Attribution-ShareAlike 2.5 License. To view a copy of this licence, visit @url{http://creativecommons.org/licenses/by-sa/2.5/} or send a letter to Creative Commons, 559 Nathan Abbott Way, Stanford, California 94305, USA.@*@*

@ifinfo
@menu
* Introduction::
* The Core Objects::
* Scripts::
* Mesh Tools::
* Hardware Buffers::
* External Texture Sources::
* Shadows::
* Animation::
@detailmenu
@end detailmenu
@end menu
@end ifinfo

@c -------------------------------------------
@node Introduction
@chapter Introduction
This chapter is intended to give you an overview of the main components of OGRE and why they have been put together that way.
@c -------------------------------------------
@node Object Orientation - more than just a buzzword
@section Object Orientation - more than just a buzzword
The name is a dead giveaway. It says Object-Oriented Graphics Rendering Engine, and that's exactly what it is. Ok, but why? Why did I choose to make such a big deal about this?@*@*

Well, nowadays graphics engines are like any other large software system. They start small, but soon they balloon into monstrously complex beasts which just can't be all understood at once. It's pretty hard to manage systems of this size, and even harder to make changes to them reliably, and that's pretty important in a field where new techniques and approaches seem to appear every other week. Designing systems around huge files full of C function calls just doesn't cut it anymore - even if the whole thing is written by one person (not likely) they will find it hard to locate that elusive bit of code after a few months and even harder to work out how it all fits together.@*@*

Object orientation is a very popular approach to addressing the complexity problem. It's a step up from decomposing your code into separate functions, it groups function and state data together in classes which are designed to represent real concepts. It allows you to hide complexity inside easily recognised packages with a conceptually simple interface so they are easy to recognise and have a feel of 'building blocks' which you can plug together again later. You can also organise these blocks so that some of them look the same on the outside, but have very different ways of achieving their objectives on the inside, again reducing the complexity for the developers because they only have to learn one interface.@*@*

I'm not going to teach you OO here, that's a subject for many other books, but suffice to say I'd seen enough benefits of OO in business systems that I was surprised most graphics code seemed to be written in C function stylee. I was interested to see whether I could apply my design experience in other types of software to an area which has long held a place in my heart - 3D graphics engines. Some people I spoke to were of the opinion that using full C++ wouldn't be fast enough for a real-time graphics engine, but others (including me) were of the opinion that, with care, and object-oriented framework can be performant. We were right.

In summary, here's the benefits an object-oriented approach brings to OGRE:
@table @asis
@item Abstraction
Common interfaces hide the nuances between different implementations of 3D API and operating systems
@item Encapsulation
There is a lot of state management and context-specific actions to be done in a graphics engine - encapsulation allows me to put the code and data nearest to where it is used which makes the code cleaner and easier to understand, and more reliable because duplication is avoided
@item Polymorphism
The behaviour of methods changes depending on the type of object you are using, even if you only learn one interface, e.g. a class specialised for managing indoor levels behaves completely differently from the standard scene manager, but looks identical to other classes in the system and has the same methods called on it
@end table
@c -------------------------------------------
@node Multi-everything
@section Multi-everything
I wanted to do more than create a 3D engine that ran on one 3D API, on one platform, with one type of scene (indoor levels are most popular). I wanted OGRE to be able to extend to any kind of scene (but yet still implement scene-specific optimisations under the surface), any platform and any 3D API.@*@*

Therefore all the 'visible' parts of OGRE are completely independent of platform, 3D API and scene type. There are no dependencies on Windows types, no assumptions about the type of scene you are creating, and the principles of the 3D aspects are based on core maths texts rather than one particular API implementation.@*@*

Now of course somewhere OGRE has to get down to the nitty-gritty of the specifics of the platform, API and scene, but it does this in subclasses specially designed for the environment in question, but which still expose the same interface as the abstract versions.@*@*

For example, there is a 'Win32Window' class which handles all the details about rendering windows on a Win32 platform - however the application designer only has to manipulate it via the superclass interface 'RenderWindow', which will be the same across all platforms.

Similarly the 'SceneManager' class looks after the arrangement of objects in the scene and their rendering sequence. Applications only have to use this interface, but there is a 'BspSceneManager' class which optimises the scene management for indoor levels, meaning you get both performance and an easy to learn interface. All applications have to do is hint about the kind of scene they will be creating and let OGRE choose the most appropriate implementation - this is covered in a later tutorial.@*@*

OGRE's object-oriented nature makes all this possible. Currently OGRE runs on Windows, Linux and Mac OSX using plugins to drive the underlying rendering API (currently Direct3D or OpenGL). Applications use OGRE at the abstract level, thus ensuring that they automatically operate on all platforms and rendering subsystems that OGRE provides without any need for platform or API specific code.@*@*

@node The Core Objects
@chapter The Core Objects
@heading Introduction

This tutorial gives you a quick summary of the core objects that you will use in OGRE and what they are used for.

@heading A Word About Namespaces

OGRE uses a C++ feature called namespaces. This lets you put classes, enums, structures, anything really within a 'namespace' scope which is an easy way to prevent name clashes, i.e. situations where you have 2 things called the same thing. Since OGRE is designed to be used inside other applications, I wanted to be sure that name clashes would not be a problem. Some people prefix their classes/types with a short code because some compilers don't support namespaces, but I chose to use them because they are the 'right' way to do it. Sorry if you have a non-compliant compiler, but hey, the C++ standard has been defined for years, so compiler writers really have no excuse anymore. If your compiler doesn't support namespaces then it's probably because it's sh*t - get a better one. ;)

This means every class, type etc should be prefixed with 'Ogre::', e.g. 'Ogre::Camera', 'Ogre::Vector3' etc which means if elsewhere in your application you have used a Vector3 type you won't get name clashes. To avoid lots of extra typing you can add a 'using namespace Ogre;' statement to your code which means you don't have to type the 'Ogre::' prefix unless there is ambiguity (in the situation where you have another definition with the same name).

@heading Overview from 10,000 feet

Shown below is a diagram of some of the core objects and where they 'sit' in the grand sceme of things. This is not all the classes by a long shot, just a few examples of the more more significant ones to give you an idea of how it slots together.
@image{images/uml-overview}

At the very top of the diagram is the Root object. This is your 'way in' to the OGRE system, and it's where you tend to create the top-level objects that you need to deal with, like scene managers, rendering systems and render windows, loading plugins, all the fundamental stuff. If you don't know where to start, Root is it for almost everything, although often it will just give you another object which will actually do the detail work, since Root itself is more of an organiser and facilitator object.

The majority of rest of OGRE's classes fall into one of 3 roles:
@table @asis
@item Scene Management
This is about the contents of your scene, how it's structured, how it's viewed from cameras, etc. Objects in this area are responsible for giving you a natural declarative interface to the world you're building; ie you don't tell OGRE "set these render states and then render 3 polygons", you tell it "I want an object here, here and here, with these materials on them, rendered from this view", and let it get on with it.
@item Resource Management
All rendering needs resources, whether it's geometry, textures, fonts, whatever. It's important to manage the loading, re-use and unloading of these things carefully, so that's what classes in this area do.
@item Rendering
Finally, there's getting the visuals on the screen - this is about the lower-level end of the rendering pipeline, the specific rendering system API objects like buffers, render states and the like and pushing it all down the pipeline. Classes in the Scene Management subsystem use this to get their higher-level scene information onto the screen.
@end table

You'll notice that scattered around the edge are a number of plugins. OGRE is designed to be extended, and plugins are the usual way to go about it. Many of the classes in OGRE can be subclassed and extended, whether it's changing the scene organisation through a custom SceneManager, adding a new render system implementation (e.g. Direct3D or OpenGL), or providing a way to load resources from another source (say from a web location or a database). Again this is just a small smattering of the kinds of things plugins can do, but as you can see they can plug in to almost any aspect of the system. This way, OGRE isn't just a solution for one narrowly defined problem, it can extend to pretty much anything you need it to do.

@node The Root Object
@section The Root object
The 'Root' object is the entry point to the OGRE system. This object MUST be the first one to be created, and the last one to be destroyed. In the example applications I chose to make an instance of Root a member of my application object which ensured that it was created as soon as my application object was, and deleted when the application object was deleted.@*@*

The root object lets you configure the system, for example through the showConfigDialog() method which is an extremely handy method which performs all render system options detection and shows a dialog for the user to customise resolution, colour depth, full screen options etc. It also sets the options the user selects so that you can initialise the system directly afterwards.@*@*

The root object is also your method for obtaining pointers to other objects in the system, such as the SceneManager, RenderSystem and various other resource managers. See below for details.@*@*

Finally, if you run OGRE in continuous rendering mode, i.e. you want to always refresh all the rendering targets as fast as possible (the norm for games and demos, but not for windowed utilities), the root object has a method called startRendering, which when called will enter a continuous rendering loop which will only end when all rendering windows are closed, or any FrameListener objects indicate that they want to stop the cycle (see below for details of FrameListener objects).@*@*

@node The RenderSystem object
@section The RenderSystem object

The RenderSystem object is actually an abstract class which defines the interface to the underlying 3D API. It is responsible for sending rendering operations to the API and setting all the various rendering options. This class is abstract because all the implementation is rendering API specific - there are API-specific subclasses for each rendering API (e.g. D3DRenderSystem for Direct3D). After the system has been initialised through Root::initialise, the RenderSystem object for the selected rendering API is available via the Root::getRenderSystem() method.@*@*

However, a typical application should not normally need to manipulate the RenderSystem object directly - everything you need for rendering objects and customising settings should be available on the SceneManager, Material and other scene-oriented classes. It's only if you want to create multiple rendering windows (completely separate windows in this case, not multiple viewports like a split-screen effect which is done via the RenderWindow class) or access other advanced features that you need access to the RenderSystem object.@*@*

For this reason I will not discuss the RenderSystem object further in these tutorials. You can assume the SceneManager handles the calls to the RenderSystem at the appropriate times.@*@*

@node The SceneManager object
@section The SceneManager object

Apart from the Root object, this is probably the most critical part of the system from the application's point of view. Certainly it will be the object which is most used by the application. The SceneManager is in charge of the contents of the scene which is to be rendered by the engine. It is responsible for organising the contents using whatever technique it deems best, for creating and managing all the cameras, movable objects (entities), lights and materials (surface properties of objects), and for managing the 'world geometry' which is the sprawling static geometry usually used to represent the immovable parts of a scene.@*@*

It is to the SceneManager that you go when you want to create a camera for the scene. It's also where you go to retrieve or to remove a light from the scene. There is no need for your application to keep lists of objects, the SceneManager keeps a named set of all of the scene objects for you to access, should you need them. Look in the main documentation under the getCamera, getLight, getEntity etc methods.@*@*

The SceneManager also sends the scene to the RenderSystem object when it is time to render the scene. You never have to call the SceneManager::_renderScene method directly though - it is called automatically whenever a rendering target is asked to update.@*@*

So most of your interaction with the SceneManager is during scene setup. You're likely to call a great number of methods (perhaps driven by some input file containing the scene data) in order to set up your scene. You can also modify the contents of the scene dynamically during the rendering cycle if you create your own FrameListener object (see later).@*@*

Because different scene types require very different algorithmic approaches to deciding which objects get sent to the RenderSystem in order to attain good rendering performance, the SceneManager class is designed to be subclassed for different scene types. The default SceneManager object will render a scene, but it does little or no scene organisation and you should not expect the results to be high performance in the case of large scenes. The intention is that specialisations will be created for each type of scene such that under the surface the subclass will optimise the scene organisation for best performance given assumptions which can be made for that scene type. An example is the BspSceneManager which optimises rendering for large indoor levels based on a Binary Space Partition (BSP) tree.@*@*

The application using OGRE does not have to know which subclasses are available. The application simply calls Root::createSceneManager(..) passing as a parameter one of a number of scene types (e.g. ST_GENERIC, ST_INTERIOR etc). OGRE will automatically use the best SceneManager subclass available for that scene type, or default to the basic SceneManager if a specialist one is not available. This allows the developers of OGRE to add new scene specialisations later and thus optimise previously unoptimised scene types without the user applications having to change any code.@*@*


@node The ResourceGroupManager Object
@section The ResourceGroupManager Object

The ResourceGroupManager class is actually a 'hub' for loading of reusable resources like textures and meshes. It is the place that you define groups for your resources, so they may be unloaded and reloaded when you want. Servicing it are a number of ResourceManagers which manage the individual types of resource, like TextureManager or MeshManager. In this context, resources are sets of data which must be loaded from somewhere to provide OGRE with the data it needs. @*@*

ResourceManagers ensure that resources are only loaded once and shared throughout the OGRE engine. They also manage the memory requirements of the resources they look after. They can also search in a number of locations for the resources they need, including multiple search paths and compressed archives (ZIP files).@*@*

Most of the time you won't interact with resource managers directly. Resource managers will be called by other parts of the OGRE system as required, for example when you request for a texture to be added to a Material, the TextureManager will be called for you. If you like, you can call the appropriate resource manager directly to preload resources (if for example you want to prevent disk access later on) but most of the time it's ok to let OGRE decide when to do it.@*@*

One thing you will want to do is to tell the resource managers where to look for resources. You do this via Root::getSingleton().addResourceLocation, which actually passes the information on to ResourceGroupManager. @*@*

Because there is only ever 1 instance of each resource manager in the engine, if you do want to get a reference to a resource manager use the following syntax:
@example
TextureManager::getSingleton().someMethod()
MeshManager::getSingleton().someMethod()
@end example
@*@*

@node The Mesh Object
@section The Mesh Object

A Mesh object represents a discrete model, a set of geometry which is self-contained and is typically fairly small on a world scale. Mesh objects are assumed to represent movable objects and are not used for the sprawling level geometry typically used to create backgrounds.@*@*

Mesh objects are a type of resource, and are managed by the MeshManager resource manager. They are typically loaded from OGRE's custom object format, the '.mesh' format. Mesh files are typically created by exporting from a modelling tool @xref{Exporters} and can be maipulated through various @ref{Mesh Tools}@*@*

You can also create Mesh objects manually by calling the MeshManager::createManual method. This way you can define the geometry yourself, but this is outside the scope of this manual.@*@*

Mesh objects are the basis for the individual movable objects in the world, which are called @ref{Entities}.@*@*

Mesh objects can also be animated using @xref{Skeletal Animation}.

@node Entities
@section Entities

An entity is an instance of a movable object in the scene. It could be a car, a person, a dog, a shuriken, whatever. The only assumption is that it does not necessarily have a fixed position in the world.@*@*

Entities are based on discrete meshes, i.e. collections of geometry which are self-contained and typically fairly small on a world scale, which are represented by the Mesh object. Multiple entities can be based on the same mesh, since often you want to create multiple copies of the same type of object in a scene.@*@*

You create an entity by calling the SceneManager::createEntity method, giving it a name and specifying the name of the mesh object which it will be based on (e.g. 'muscleboundhero.mesh'). The SceneManager will ensure that the mesh is loaded by calling the MeshManager resource manager for you. Only one copy of the Mesh will be loaded.@*@*

Entities are not deemed to be a part of the scene until you attach them to a SceneNode (see the section below). By attaching entities to SceneNodes, you can create complex hierarchical relationships between the positions and orientations of entities. You then modify the positions of the nodes to indirectly affect the entity positions.@*@*

When a Mesh is loaded, it automatically comes with a number of materials defined. It is possible to have more than one material attached to a mesh - different parts of the mesh may use different materials. Any entity created from the mesh will automatically use the default materials. However, you can change this on a per-entity basis if you like so you can create a number of entities based on the same mesh but with different textures etc.@*@*

To understand how this works, you have to know that all Mesh objects are actually composed of SubMesh objects, each of which represents a part of the mesh using one Material. If a Mesh uses only one Material, it will only have one SubMesh.@*@*

When an Entity is created based on this Mesh, it is composed of (possibly) multiple SubEntity objects, each matching 1 for 1 with the SubMesh objects from the original Mesh. You can access the SubEntity objects using the Entity::getSubEntity method. Once you have a reference to a SubEntity, you can change the material it uses by calling it's setMaterialName method. In this way you can make an Entity deviate from the default materials and thus create an individual looking version of it.@*@*

@node Materials
@section Materials

The Material object controls how objects in the scene are rendered. It specifies what basic surface properties objects have such as reflectance of colours, shininess etc, how many texture layers are present, what images are on them and how they are blended together, what special effects are applied such as environment mapping, what culling mode is used, how the textures are filtered etc.@*@*

Materials can either be set up programmatically, by calling SceneManager::createMaterial and tweaking the settings, or by specifying it in a 'script' which is loaded at runtime. @xref{Material Scripts} for more info.@*@*

Basically everything about the appearance of an object apart from it's shape is controlled by the Material class.@*@*

The SceneManager class manages the master list of materials available to the scene. The list can be added to by the application by calling SceneManager::createMaterial, or by loading a Mesh (which will in turn load material properties). Whenever materials are added to the SceneManager, they start off with a default set of properties; these are defined by OGRE as the following:@*@*

@itemize @bullet
@item
ambient reflectance = ColourValue::White (full)
@item
diffuse reflectance = ColourValue::White (full)
@item
specular reflectance = ColourValue::Black (none)
@item
emmissive = ColourValue::Black (none)
@item 
shininess = 0 (not shiny)
@item 
No texture layers (& hence no textures)
@item 
SourceBlendFactor = SBF_ONE, DestBlendFactor = SBF_ZERO (opaque)
@item 
Depth buffer checking on
@item 
Depth buffer writing on
@item 
Depth buffer comparison function = CMPF_LESS_EQUAL
@item 
Culling mode = CULL_CLOCKWISE
@item 
Ambient lighting in scene = ColourValue(0.5, 0.5, 0.5) (mid-grey)
@item 
Dynamic lighting enabled
@item 
Gourad shading mode
@item
Solid polygon mode
@item 
Bilinear texture filtering
@end itemize

You can alter these settings by calling SceneManager::getDefaultMaterialSettings() and making the required changes to the Material which is returned.

Entities automatically have Material's associated with them if they use a Mesh object, since the Mesh object typically sets up it's required materials on loading. You can also customise the material used by an entity as described in @ref{Entities}. Just create a new Material, set it up how you like (you can copy an existing material into it if you like using a standard assignment statement) and point the SubEntity entries at it using SubEntity::setMaterialName().


@node Overlays
@section Overlays

Overlays allow you to render 2D and 3D elements on top of the normal scene contents to create effects like heads-up displays (HUDs), menu systems, status panels etc. The frame rate statistics panel which comes as standard with OGRE is an example of an overlay. Overlays can contain 2D or 3D elements. 2D elements are used for HUDs, and 3D elements can be used to create cockpits or any other 3D object which you wish to be rendered on top of the rest of the scene.@*@*

You can create overlays either through the SceneManager::createOverlay method, or you can define them in an .overlay script. In reality the latter is likely to be the most practical because it is easier to tweak (without the need to recompile the code). Note that you can define as many overlays as you like: they all start off life hidden, and you display them by calling their 'show()' method. You can also show multiple overlays at once, and their Z order is determined by the Overlay::setZOrder() method.@*@*

@heading Creating 2D Elements

The OverlayElement class abstracts the details of 2D elements which are added to overlays. All items which can be added to overlays are derived from this class. It is possible (and encouraged) for users of OGRE to define their own custom subclasses of OverlayElement in order to provide their own user controls. The key common features of all OverlayElements are things like size, position, basic material name etc. Subclasses extend this behaviour to include more complex properties and behaviour.@*@*

An important built-in subclass of OverlayElement is OverlayContainer. OverlayContainer is the same as a OverlayElement, except that it can contain other OverlayElements, grouping them together (allowing them to be moved together for example) and providing them with a local coordinate origin for easier lineup.@*@*

The third important class is OverlayManager. Whenever an application wishes to create a 2D element to add to an overlay (or a container), it should call OverlayManager::createOverlayElement. The type of element you wish to create is identified by a string, the reason being that it allows plugins to register new types of OverlayElement for you to create without you having to link specifically to those libraries. For example, to create a panel (a plain rectangular area which can contain other OverlayElements) you would call OverlayManager::getSingleton().createOverlayElement("Panel", "myNewPanel");@*@*

@heading Adding 2D Elements to the Overlay

Only OverlayContainers can be added direct to an overlay. The reason is that each level of container establishes the Zorder of the elements contained within it, so if you nest several containers, inner containers have a higher zorder than outer ones to ensure they are displayed correctly. To add a container (such as a Panel) to the overlay, simply call Overlay::add2D.@*@*

If you wish to add child elements to that container, call OverlayContainer::addChild. Child elements can be OverlayElements or OverlayContainer instances themselves. Remember that the position of a child element is relative to the top-left corner of it's parent.@*@*

@heading A word about 2D coordinates

OGRE allows you to place and size elements based on 2 coordinate systems: @strong{relative} and @strong{pixel} based. 
@table @asis
@item Pixel Mode
This mode is useful when you want to specify an exact size for your overlay items, and you don't mind if those items get smaller on the screen if you increase the screen resolution (in fact you might want this). In this mode the only way to put something in the middle or at the right or bottom of the screen reliably in any resolution is to use the aligning options, whilst in relative mode you can do it just by using the right relative coordinates. This mode is very simple, the top-left of the screen is (0,0) and the bottom-right of the screen depends on the resolution. As mentioned above, you can use the aligning options to make the horizontal and vertical coordinate origins the right, bottom or center of the screen if you want to place pixel items in these locations without knowing the resolution.
@item Relative Mode
This mode is useful when you want items in the overlay to be the same size on the screen no matter what the resolution. In relative mode, the top-left of the screen is (0,0) and the bottom-right is (1,1). So if you place an element at (0.5, 0.5), it's top-left corner is placed exactly in the center of the screen, no matter what resolution the application is running in. The same principle applies to sizes; if you set the width of an element to 0.5, it covers half the width of the screen. Note that because the aspect ratio of the screen is typically 1.3333 : 1 (width : height), an element with dimensions (0.25, 0.25) will not be square, but it will take up exactly 1/16th of the screen in area terms. If you want square-looking areas you will have to compensate using the typical aspect ratio eg use (0.1875, 0.25) instead.
@end table

@heading Transforming Overlays

Another nice feature of overlays is being able to rotate, scroll and scale them as a whole. You can use this for zooming in / out menu systems, dropping them in from off screen and other nice effects. See the Overlay::scroll, Overlay::rotate and Overlay::scale methods for more information.

@heading Scripting overlays
Overlays can also be defined in scripts. @xref{Overlay Scripts} for details.

@heading GUI systems
Overlays are only really designed for non-interactive screen elements, although you can use them as a crude GUI. For a far more complete GUI solution, we recommend CEGui (@url{http://www.cegui.org.uk}), as demonstrated in the sample Demo_Gui.

@node Scripts
@chapter Scripts
OGRE drives many of its features through scripts in order to make it easier to set up. The scripts are simply plain text files which can be edited in any standard text editor, and modiying them immediately takes effect on your OGRE-based applications, without any need to recompile. This makes prototyping a lot faster. Here are the items that OGRE lets you script:
@itemize @bullet
@item
@ref{Material Scripts}
@item
@ref{Compositor Scripts}
@item
@ref{Particle Scripts}
@item
@ref{Overlay Scripts}
@item
@ref{Font Definition Scripts}
@end itemize
@node Material Scripts
@section Material Scripts

Material scripts offer you the ability to define complex materials in a script which can be reused easily. Whilst you could set up all materials for a scene in code using the methods of the Material and TextureLayer classes, in practice it's a bit unwieldy. Instead you can store material definitions in text files which can then be loaded whenever required.@*@*

@heading Loading scripts

Material scripts are loaded when resource groups are initialised: OGRE looks in all resource locations associated with the group (see Root::addResourceLocation) for files with the '.material' extension and parses them. If you want to parse files manually, use MaterialSerializer::parseScript.@*@*

It's important to realise that materials are not loaded completely by this parsing process: only the definition is loaded, no textures or other resources are loaded. This is because it is common to have a large library of materials, but only use a relatively small subset of them in any one scene. To load every material completely in every script would therefore cause unnecessary memory overhead. You can access a 'deferred load' Material in the normal way (MaterialManager::getSingleton().getByName()), but you must call the 'load' method before trying to use it. Ogre does this for you when using the normal material assignment methods of entities etc.@*@*

Another important factor is that material names must be unique throughout ALL scripts loaded by the system, since materials are always identified by name.@*@*

@heading Format

Several materials may be defined in a single script. The script format is pseudo-C++, with sections delimited by curly braces ('{', '}'), and comments indicated by starting a line with '//' (note, no nested form comments allowed). The general format is shown below in the example below (note that to start with, we only consider fixed-function materials which don't use vertex or fragment programs, these are covered later):@*@*
@example
// This is a comment
material walls/funkywall1
{
    // first, preferred technique
    technique
    {
        // first pass
        pass
        {
            ambient 0.5 0.5 0.5
            diffuse 1.0 1.0 1.0
			
            // Texture unit 0
            texture_unit 
            {
                texture wibbly.jpg
                scroll_anim 0.1 0.0
                wave_xform scale sine 0.0 0.7 0.0 1.0
            }
            // Texture unit 1 (this is a multitexture pass)
            texture_unit
            {
                texture wobbly.png
                rotate_anim 0.25
                colour_op add
            }
        }
    }

    // Second technique, can be used as a fallback or LOD level
    technique
    {
        // .. and so on
    }
		
}
@end example

Every material in the script must be given a name, which is the line 'material <blah>' before the first opening '{'. This name must be globally unique. It can include path characters (as in the example) to logically divide up your materials, and also to avoid duplicate names, but the engine does not treat the name as hierarchical, just as a string.@*@*

@strong{ NOTE: ':' is the delimiter for specifying material copy in the script so it can't be used as part of the material name.}
@*@*

A material can copy from a previously defined material by using a @emph{colon} @strong{:} after the material name followed by the name of the reference material to copy. If the reference material can not be found then it is ignored.  (@xref{Copying Materials})@*@*

A material can be made up of many techniques (@xref{Techniques})- a technique is one way of achieving the effect you are looking for. You can supply more than one technique in order to provide fallback approaches where a card does not have the ability to render the preferred technique, or where you wish to define lower level of detail versions of the material in order to conserve rendering power when objects are more distant. @*@*

Each technique can be made up of many passes (@xref{Passes}), that is a complete render of the object can be performed multiple times with different settings in order to produce composite effects. Ogre may also split the passes you have defined into many passes at runtime, if you define a pass which uses too many texture units for the card you are currently running on (note that it can only do this if you are not using a fragment program). Each pass has a number of top-level attributes such as 'ambient' to set the amount & colour of the ambient light reflected by the material. Some of these options do not apply if you are using vertex programs, @xref{Passes} for more details. @*@*

Within each pass, there can be zero or many texture units in use (@xref{Texture Units}). These define the texture to be used, and optionally some blending operations (which use multitexturing) and texture effects.@*@*

You can also reference vertex and fragment programs (or vertex and pixel shaders, if you want to use that terminology) in a pass with a given set of parameters. Programs themselves are declared in separate .program scripts (@xref{Declaring Vertex and Fragment Programs}) and are used as described in @ref{Using Vertex and Fragment Programs in a Pass}.

@subheading Top-level material attributes
The outermost section of a material definition does not have a lot of attributes of its own (most of the configurable parameters are within the child sections. However, it does have some, and here they are:@*@*
@anchor{lod_distances}
@subheading lod_distances
This attribute controls the distances at which different Techniques can come into effect. @xref{Techniques} for a full discussion of this option.
@*@*
@anchor{receive_shadows}
@subheading receive_shadows
This attribute controls whether objects using this material can have shadows cast upon them.@*@* 

Format: receive_shadows <on|off>@*
Default: on@*@*

Whether or not an object receives a shadow is the combination of a number of factors, @xref{Shadows} for full details; however this allows you to make a material opt-out of receiving shadows if required. Note that transparent materials never receive shadows so this option only has an effect on solid materials.

@anchor{transparency_casts_shadows}
@subheading transparency_casts_shadows
This attribute controls whether transparent materials can cast certain kinds of shadow.@*@* 

Format: transparency_casts_shadows <on|off>@*
Default: off@*@*
Whether or not an object casts a shadow is the combination of a number of factors, @xref{Shadows} for full details; however this allows you to make a transparent material cast shadows, when it would otherwise not. For example, when using texture shadows, transparent materials are normally not rendered into the shadow texture because they should not block light. This flag overrides that.

@anchor{set_texture_alias}
@subheading set_texture_alias
This attribute associates a texture alias with a texture name.@*@*

Format: set_texture_alias <alias name> <texture name>@*@*

This attribute is used to set the textures used in texture unit states that were copied from another material.(@xref{Copying Materials})@*@*

@node Techniques
@subsection Techniques

A "technique" section in your material script encapsulates a single method of rendering an object. The simplest of material definitions only contains a single technique, however since PC hardware varies quite greatly in it's capabilities, you can only do this if you are sure that every card for which you intend to target your application will support the capabilities which your technique requires. In addition, it can be useful to define simpler ways to render a material if you wish to use material LOD, such that more distant objects use a simpler, less performance-hungry technique.@*@*

When a material is used for the first time, it is 'compiled'. That involves scanning the techniques which have been defined, and marking which of them are supportable using the current rendering API and graphics card. If no techniques are supportable, your material will render as blank white. The compilation examines a number of things, such as:
@itemize @bullet
@item The number of texture_unit entries in each pass@*
Note that if the number of texture_unit entries exceeds the number of texture units in the current graphics card, the technique may still be supportable so long as a fragment program is not being used. In this case, Ogre will split the pass which has too many entries into multiple passes for the less capable card, and the multitexture blend will be turned into a multipass blend (@xref{colour_op_multipass_fallback}).
@item Whether vertex or fragment programs are used, and if so which syntax they use (e.g. vs_1_1, ps_2_x, arbfp1 etc)
@item Other effects like cube mapping and dot3 blending
@end itemize
@*
In a material script, techniques must be listed in order of preference, i.e. the earlier techniques are preferred over the later techniques. This normally means you will list your most advanced, most demanding techniques first in the script, and list fallbacks afterwards.@*@*

To help clearly identify what each technique is used for, the technique can be named but its optional.  Techniques not named within the script will take on a name that is the technique index number.  For example: the first technique in a material is index 0, its name would be "0" if it was not given a name in the script.  The technique name must be unqiue within the material or else the final technique is the resulting merge of all techniques with the same name in the material.  A warning message is posted in the Ogre.log if this occurs.  Named techniques can help when copying a material and modifying an existing technique: (@xref{Copying Materials})@*@*

Format: technique name@*@*

Techniques have only a small number of attributes of their own, the 'scheme'(@xref{scheme})  they belong to, and the LOD index within that scheme (@xref{lod_index}). We also mention an extra Material attribute called @ref{lod_distances} which isn't a Technique attribute but is directly related to the lod_index attribute, so it's listed here for convenience.@*@*

@anchor{scheme}
@subheading scheme

Sets the 'scheme' this Technique belongs to. Material schemes are used to control top-level switching from one set of techniques to another. For example, you might use this to define 'high', 'medium' and 'low' complexity levels on materials to allow a user to pick a performance / quality ratio. Another possibility is that you have a fully HDR-enabled pipeline for top machines, rendering all objects using unclamped shaders, and a simpler pipeline for others; this can be implemented using schemes. The active scheme is typically controlled at a viewport level, and the active one defaults to 'Default'.@*@*

Format: scheme <name>@*
Example: scheme hdr@*
Default: scheme Default@*@*


@anchor{lod_index}
@subheading lod_index

Sets the level-of-detail (LOD) index this Technique belongs to. @*@*

Format: lod_index <number>@*
NB Valid values are 0 (highest level of detail) to 65535, although this is unlikely. You should not leave gaps in the LOD indexes between Techniques.@*@*

Example: lod_index 1@*@*

All techniques must belong to a LOD index, by default they all belong to index 0, ie the highest LOD. Increasing indexes denote lower levels of detail. You can (and often will) assign more than one technique to the same LOD index, what this means is that OGRE will pick the best technique of the ones listed at the same LOD index. For readability, it is advised that you list your techniques in order of LOD, then in order of preference, although the latter is the only prerequisite (OGRE determines which one is 'best' by which one is listed first). You must always have at least one Technique at lod_index 0.@*@*
The distance at which a LOD level is applied is determined by the lod_distances attribute of the containing material, @xref{lod_distances} for details.@*@*

Default: lod_index 0@*@*

@anchor{lod_distances}
@subheading lod_distances
@strong{Note: this attribute must be specified in the outer material section (ie the parent of all the techniques), but it's specified here since it is most relevant to this section.}@*@*

By setting this attribute, you indicate that you want this material to alter the Technique that it uses based on distance from the camera. You must give it a list of distances, in ascending order, each one indicating the distance at which the material will switch to the next LOD. Implicitly, all materials activate LOD index 0 for distances less than the smallest of these. You must ensure that there is at least one Technique with a @ref{lod_index} value for each distance in the list (so if you specify 3 distances, you must have techniques for indexes 1, 2 and 3). Note you must always have at least one Technique at lod_index 0.@*@*

Format: lod_distances <distance_1> [<distance_2> ... <distance_n>]@*

Example: lod_distances 300.0 600.5 1200@*@*

The above example would cause the material to use the best Technique at lod_index 0 up to a distance of 300 world units, the best from lod_index 1 from 300 up to 600, lod_index 2 from 600 to 1200, and lod_index 3 from 1200 upwards.@*@*

Techniques also contain one or more passes (and there must be at least one), @xref{Passes}.



@node Passes
@subsection Passes
A pass is a single render of the geometry in question; a single call to the rendering API with a certain set of rendering properties. A technique can have between one and 16 passes, although clearly the more passes you use, the more expensive the technique will be to render.@*@*

To help clearly identify what each pass is used for, the pass can be named but its optional.  Passes not named within the script will take on a name that is the pass index number.  For example: the first pass in a technique is index 0 so its name would be "0" if it was not given a name in the script.  The pass name must be unqiue within the technique or else the final pass is the resulting merge of all passes with the same name in the technique.  A warning message is posted in the Ogre.log if this occurs.  Named passes can help when copying a material and modifying an existing pass: (@xref{Copying Materials})@*@*

Passes have a set of global attributes (described below), zero or more nested texture_unit entries (@xref{Texture Units}), and optionally a reference to a vertex and / or a fragment program (@xref{Using Vertex and Fragment Programs in a Pass}).

@*@*
Here are the attributes you can use in a 'pass' section of a .material script:

@itemize @bullet
@item
@ref{ambient}
@item
@ref{diffuse}
@item
@ref{specular}
@item
@ref{emissive}
@item
@ref{scene_blend}
@item
@ref{depth_check}
@item
@ref{depth_write}
@item
@ref{depth_func}
@item
@ref{depth_bias}
@item
@ref{alpha_rejection}
@item
@ref{cull_hardware}
@item
@ref{cull_software}
@item
@ref{lighting}
@item
@ref{shading}
@item 
@ref{polygon_mode}
@item
@ref{fog_override}
@item
@ref{colour_write}
@item
@ref{max_lights}
@item
@ref{start_light}
@item
@ref{iteration}
@item
@ref{point_size}
@item
@ref{point_sprites}
@item
@ref{point_size_attenuation}
@item
@ref{point_size_min}
@item
@ref{point_size_max}
@end itemize

@heading Attribute Descriptions
@anchor{ambient}
@subheading ambient

Sets the ambient colour reflectance properties of this pass. @strong{This attribute has no effect if a asm, CG, or HLSL shader program is used.  With GLSL, the shader can read the OpenGL material state.} @*@*

Format: ambient (<red> <green> <blue> [<alpha>]| vertexcolour)@*
NB valid colour values are between 0.0 and 1.0.@*@*

Example: ambient 0.0 0.8 0.0@*@*

The base colour of a pass is determined by how much red, green and blue light is reflects at each vertex. This property determines how much ambient light (directionless global light) is reflected. 
It is also possible to make the ambient reflectance track the vertex colour as defined in the mesh by using the keyword vertexcolour instead of the colour values.
The default is full white, meaning objects are completely globally illuminated. Reduce this if you want to see diffuse or specular light effects, or change the blend of colours to make the object have a base colour other than white. This setting has no effect if dynamic lighting is disabled using the 'lighting off' attribute, or if any texture layer has a 'colour_op replace' attribute.@*@*

Default: ambient 1.0 1.0 1.0 1.0@*@*

@anchor{diffuse}
@subheading diffuse

Sets the diffuse colour reflectance properties of this pass. @strong{This attribute has no effect if a asm, CG, or HLSL shader program is used.  With GLSL, the shader can read the OpenGL material state.}@*@*

Format: diffuse (<red> <green> <blue> [<alpha>]| vertexcolour)@*
NB valid colour values are between 0.0 and 1.0.@*@*

Example: diffuse 1.0 0.5 0.5@*@*

The base colour of a pass is determined by how much red, green and blue light is reflects at each vertex. This property determines how much diffuse light (light from instances of the Light class in the scene) is reflected. 
It is also possible to make the diffuse reflectance track the vertex colour as defined in the mesh by using the keyword vertexcolour instead of the colour values.
The default is full white, meaning objects reflect the maximum white light they can from Light objects. This setting has no effect if dynamic lighting is disabled using the 'lighting off' attribute, or if any texture layer has a 'colour_op replace' attribute.@*@*

Default: diffuse 1.0 1.0 1.0 1.0@*@*

@anchor{specular}
@subheading specular

Sets the specular colour reflectance properties of this pass. @strong{This attribute has no effect if a asm, CG, or HLSL shader program is used.  With GLSL, the shader can read the OpenGL material state.}@*@*

Format: specular (<red> <green> <blue> [<alpha>]| vertexcolour) <shininess>@*
NB valid colour values are between 0.0 and 1.0. Shininess can be any value greater than 0.@*@*

Example: specular 1.0 1.0 1.0 12.5@*@*

The base colour of a pass is determined by how much red, green and blue light is reflects at each vertex. This property determines how much specular light (highlights from instances of the Light class in the scene) is reflected. 
It is also possible to make the diffuse reflectance track the vertex colour as defined in the mesh by using the keyword vertexcolour instead of the colour values.
The default is to reflect no specular light. The colour of the specular highlights is determined by the colour parameters, and the size of the highlights by the separate shininess parameter.. The higher the value of the shininess parameter, the sharper the highlight ie the radius is smaller.  Beware of using shininess values in the range of 0 to 1 since this causes the the specular colour to be applied to the whole surface that has the material applied to it.  When the viewing angle to the surface changes, ugly flickering will also occur when shininess is in the range of 0 to 1.  Shininess values between 1 and 128 work best in both DirectX and OpenGL renderers.  This setting has no effect if dynamic lighting is disabled using the 'lighting off' attribute, or if any texture layer has a 'colour_op replace' attribute.@*@*

Default: specular 0.0 0.0 0.0 0.0 0.0@*@*

@anchor{emissive}
@subheading emissive

Sets the amount of self-illumination an object has. @strong{This attribute has no effect if a asm, CG, or HLSL shader program is used.  With GLSL, the shader can read the OpenGL material state.}@*@*

Format: emissive (<red> <green> <blue> [<alpha>]| vertexcolour)@*
NB valid colour values are between 0.0 and 1.0.@*@*

Example: emissive 1.0 0.0 0.0@*@*

If an object is self-illuminating, it does not need external sources to light it, ambient or otherwise. It's like the object has it's own personal ambient light. Unlike the name suggests, this object doesn't act as a light source for other objects in the scene (if you want it to, you have to create a light which is centered on the object). 
It is also possible to make the emissive colour track the vertex colour as defined in the mesh by using the keyword vertexcolour instead of the colour values.
This setting has no effect if dynamic lighting is disabled using the 'lighting off' attribute, or if any texture layer has a 'colour_op replace' attribute.@*@*

Default: emissive 0.0 0.0 0.0 0.0@*@*

@anchor{scene_blend}
@subheading scene_blend

Sets the kind of blending this pass has with the existing contents of the scene. Wheras the texture blending operations seen in the texture_unit entries are concerned with blending between texture layers, this blending is about combining the output of this pass as a whole with the existing contents of the rendering target. This blending therefore allows object transparency and other special effects. There are 2 formats, one using predefined blend types, the other allowing a roll-your-own approach using source and destination factors.@*@*

Format1: scene_blend <add|modulate|alpha_blend|colour_blend>@*@*

Example: scene_blend add@*@*

This is the simpler form, where the most commonly used blending modes are enumerated using a single parameter. Valid <blend_type> parameters are:
@table @asis
@item add
The colour of the rendering output is added to the scene. Good for exposions, flares, lights, ghosts etc. Equivalent to 'scene_blend one one'.
@item modulate
The colour of the rendering output is multiplied with the scene contents. Generally colours and darkens the scene, good for smoked glass, semi-transparent objects etc. Equivalent to 'scene_blend dest_colour zero'.
@item colour_blend
Colour the scene based on the brightness of the input colours, but don't darken. Equivalent to 'scene_blend src_colour one_minus_src_colour'
@item alpha_blend
The alpha value of the rendering output is used as a mask. Equivalent to 'scene_blend src_alpha one_minus_src_alpha'
@end table
@*
Format2: scene_blend <src_factor> <dest_factor>@*@*

Example: scene_blend one one_minus_dest_alpha@*@*

This version of the method allows complete control over the blending operation, by specifying the source and destination blending factors. The resulting colour which is written to the rendering target is (texture * sourceFactor) + (scene_pixel * destFactor). Valid values for both parameters are:
@table @asis
@item one
Constant value of 1.0
@item zero
Constant value of 0.0
@item dest_colour
The existing pixel colour
@item src_colour
The texture pixel (texel) colour
@item one_minus_dest_colour
1 - (dest_colour)
@item one_minus_src_colour
1 - (src_colour)
@item dest_alpha
The existing pixel alpha value
@item src_alpha
The texel alpha value
@item one_minus_dest_alpha
1 - (dest_alpha)
@item one_minus_src_alpha
1 - (src_alpha)
@end table
@*
Default: scene_blend one zero (opaque)
@*
@anchor{depth_check}
@subheading depth_check

Sets whether or not this pass renders with depth-buffer checking on or not.@*@*

Format: depth_check <on|off>@*@*

If depth-buffer checking is on, whenever a pixel is about to be written to the frame buffer the depth buffer is checked to see if the pixel is in front of all other pixels written at that point. If not, the pixel is not written. If depth checking is off, pixels are written no matter what has been rendered before. Also see depth_func for more advanced depth check configuration.@*@*

Default: depth_check on@*@*

@anchor{depth_write}
@subheading depth_write

Sets whether or not this pass renders with depth-buffer writing on or not.@*

Format: depth_write <on|off>@*@*

If depth-buffer writing is on, whenever a pixel is written to the frame buffer the depth buffer is updated with the depth value of that new pixel, thus affecting future rendering operations if future pixels are behind this one. If depth writing is off, pixels are written without updating the depth buffer. Depth writing should normally be on but can be turned off when rendering static backgrounds or when rendering a collection of transparent objects at the end of a scene so that they overlap each other correctly.@*@*

Default: depth_write on@*

@anchor{depth_func}
@subheading depth_func

Sets the function used to compare depth values when depth checking is on.@*@*

Format: depth_func <func>@*@*

If depth checking is enabled (see depth_check) a comparison occurs between the depth value of the pixel to be written and the current contents of the buffer. This comparison is normally less_equal, i.e. the pixel is written if it is closer (or at the same distance) than the current contents. The possible functions are:
@table @asis
@item always_fail
Never writes a pixel to the render target
@item always_pass
Always writes a pixel to the render target
@item less
Write if (new_Z < existing_Z)
@item less_equal
Write if (new_Z <= existing_Z)
@item equal
Write if (new_Z == existing_Z)
@item not_equal
Write if (new_Z != existing_Z)
@item greater_equal
Write if (new_Z >= existing_Z)
@item greater
Write if (new_Z >existing_Z)
@end table
@*
Default: depth_func less_equal

@anchor{depth_bias}
@subheading depth_bias

Sets the bias applied to the depth value of this pass. Can be used to make coplanar polygons appear on top of others e.g. for decals. @*@*

Format: depth_bias <constant_bias> [<slopescale_bias>]@*@*

The final depth bias value is constant_bias * minObservableDepth + maxSlope * slopescale_bias. Slope scale biasing is relative to the angle of the polygon to the camera, which makes for a more appropriate bias value, but this is ignored on some older hardware. Constant biasing is expressed as a factor of the minimum depth value, so a value of 1 will nudge the depth by one 'notch' if you will.@*@*

@anchor{alpha_rejection}
@subheading alpha_rejection

Sets the way the pass will have use alpha to totally reject pixels from the pipeline.@*@*

Format: alpha_rejection <function> <value>@*@*

Example: alpha_rejection greater_equal 128@*@*

The function parameter can be any of the options listed in the material depth_function attribute. The value parameter can theoretically be any value between 0 and 255, but is best limited to 0 or 128 for hardware compatibility.@*@*

Default: alpha_rejection always_pass@*@*

@anchor{cull_hardware}
@subheading cull_hardware

Sets the hardware culling mode for this pass.@*@*

Format: cull_hardware <clockwise|anticlockwise|none>@*@*

A typical way for the hardware rendering engine to cull triangles is based on the 'vertex winding' of triangles. Vertex winding refers to the direction in which the vertices are passed or indexed to in the rendering operation as viewed from the camera, and will wither be clockwise or anticlockwise (that's 'counterclockwise' for you Americans out there ;). If the option 'cull_hardware clockwise' is set, all triangles whose vertices are viewed in clockwise order from the camera will be culled by the hardware. 'anticlockwise' is the reverse (obviously), and 'none' turns off hardware culling so all triagles are rendered (useful for creating 2-sided passes).@*@*

Default: cull_hardware clockwise@*
NB this is the same as OpenGL's default but the opposite of Direct3D's default (because Ogre uses a right-handed coordinate system like OpenGL).

@anchor{cull_software}
@subheading cull_software

Sets the software culling mode for this pass.@*@*

Format: cull_software <back|front|none>@*@*

In some situations the engine will also cull geometry in software before sending it to the hardware renderer. This setting only takes effect on SceneManager's that use it (since it is best used on large groups of planar world geometry rather than on movable geometry since this would be expensive), but if used can cull geometry before it is sent to the hardware. In this case the culling is based on whether the 'back' or 'front' of the traingle is facing the camera - this definition is based on the face normal (a vector which sticks out of the front side of the polygon perpendicular to the face). Since Ogre expects face normals to be on anticlockwise side of the face, 'cull_software back' is the software equivalent of 'cull_hardware clockwise' setting, which is why they are both the default. The naming is different to reflect the way the culling is done though, since most of the time face normals are precalculated and they don't have to be the way Ogre expects - you could set 'cull_hardware none' and completely cull in software based on your own face normals, if you have the right SceneManager which uses them.@*@*

Default: cull_software back@*@*

@anchor{lighting}
@subheading lighting

Sets whether or not dynamic lighting is turned on for this pass or not. If lighting is turned off, all objects rendered using the pass will be fully lit. @strong{This attribute has no effect if a vertex program is used.}@*@*

Format: lighting <on|off>@*@*

Turning dynamic lighting off makes any ambient, diffuse, specular, emissive and shading properties for this pass redundant. When lighting is turned on, objects are lit according to their vertex normals for diffuse and specular light, and globally for ambient and emissive.@*@*

Default: lighting on@*@*

@anchor{shading}
@subheading shading

Sets the kind of shading which should be used for representing dynamic lighting for this pass.@*@*

Format: shading <flat|gouraud|phong>@*@*

When dynamic lighting is turned on, the effect is to generate colour values at each vertex. Whether these values are interpolated across the face (and how) depends on this setting.@*@*
@table @asis
@item flat
	No interpolation takes place. Each face is shaded with a single colour determined from the first vertex in the face.
@item gouraud
	Colour at each vertex is linearly interpolated across the face.
@item phong
	Vertex normals are interpolated across the face, and these are used to determine colour at each pixel. Gives a more natural lighting effect but is more expensive and works better at high levels of tesselation. Not supported on all hardware.
@end table
Default: shading gouraud@*@*

@anchor{polygon_mode}
@subheading polygon_mode

Sets how polygons should be rasterised, ie whether they should be filled in, or just drawn as lines or points.@*@*

Format: polygon_mode <solid|wireframe|points>@*@*

@table @asis
@item solid
The normal situation - polygons are filled in.
@item wireframe
Polygons are drawn in outline only.
@item points
Only the points of each polygon are rendered.
@end table
Default: polygon_mode solid@*@*


@anchor{fog_override}
@subheading fog_override

Tells the pass whether it should override the scene fog settings, and enforce it's own. Very useful for things that you don't want to be affected by fog when the rest of the scene is fogged, or vice versa. Note that this only affects fixed-function fog - the original scene fog parameters are still sent to shaders which use the fog_params parameter binding (this allows you to turn off fixed function fog and calculate it in the shader instead; if you want to disable shader fog you can do that through shader parameters anyway). @*@*

Format: fog_override <override?> [<type> <colour> <density> <start> <end>]@*@*

Default: fog_override false@*@*

If you specify 'true' for the first parameter and you supply the rest of the parameters, you are telling the pass to use these fog settings in preference to the scene settings, whatever they might be. If you specify 'true' but provide no further parameters, you are telling this pass to never use fogging no matter what the scene says. Here is an explanation of the parameters:@*
@table @asis
@item type
@strong{none} = No fog, equivalent of just using 'fog_override true'@*
@strong{linear} = Linear fog from the <start> and <end> distances@*
@strong{exp} = Fog increases exponentially from the camera (fog = 1/e^(distance * density)), use <density> param to control it@*
@strong{exp2} = Fog increases at the square of FOG_EXP, i.e. even quicker (fog = 1/e^(distance * density)^2), use <density> param to control it
@item colour
	Sequence of 3 floating point values from 0 to 1 indicating the red, green and blue intensities
@item density
	The density parameter used in the 'exp' or 'exp2' fog types. Not used in linear mode but param must still be there as a placeholder
@item start
	The start distance from the camera of linear fog. Must still be present in other modes, even though it is not used.
@item end
	The end distance from the camera of linear fog. Must still be present in other modes, even though it is not used.
@end table
@*
Example: fog_override true exp 1 1 1 0.002 100 10000

@anchor{colour_write}
@subheading colour_write

Sets whether or not this pass renders with colour writing on or not.@*

Format: colour_write <on|off>@*@*

If colour writing is off no visible pixels are written to the screen during this pass. You might think this is useless, but if you render with colour writing off, and with very minimal other settings, you can use this pass to initialise the depth buffer before subsequently rendering other passes which fill in the colour data. This can give you significant performance boosts on some newer cards, especially when using complex fragment programs, because if the depth check fails then the fragment program is never run. @*@*

Default: colour_write on@*

@anchor{start_light}
@subheading start_light

Sets the first light which will be considered for use with this pass.@*@*
Format: start_light <number>@*@*

You can use this attribute to offset the starting point of the lights for this pass. In other words, if you set start_light to 2 then the first light to be processed in that pass will be the third actual light in the applicable list. You could use this option to use different passes to process the first couple of lights versus the second couple of lights for example, or use it in conjunction with the @ref{iteration} option to start the iteration from a given point in the list (e.g. doing the first 2 lights in the first pass, and then iterating every 2 lights from then on perhaps). @*@*

Default: start_light 0@*

@anchor{max_lights}
@subheading max_lights

Sets the maximum number of lights which will be considered for use with this pass.@*@*
Format: max_lights <number>@*@*

The maximum number of lights which can be used when rendering fixed-function materials is set by the rendering system, and is typically set at 8. When you are using the programmable pipeline (@xref{Using Vertex and Fragment Programs in a Pass}) this limit is dependent on the program you are running, or, if you use 'iteration once_per_light' or a variant (@xref{iteration}), it effectively only bounded by the number of passes you are willing to use. If you are not using pass iteration, the light limit applies once for this pass. If you are using pass iteration, the light limit applies across all iterations of this pass - for example if you have 12 lights in range with an 'iteration once_per_light' setup but your max_lights is set to 4 for that pass, the pass will only iterate 4 times. @*@*

Default: max_lights 8@*

@anchor{iteration}
@subheading iteration

Sets whether or not this pass is iterated, ie issued more than once.@*@*

Format 1: iteration <once | once_per_light> [lightType]@*@*
Format 2: iteration <number> [<per_light> [lightType]]@*@*
Format 3: iteration <number> [<per_n_lights> <num_lights> [lightType]]@*@*
Examples:
@table @asis
@item iteration once
	The pass is only executed once which is the default behaviour.
@item iteration once_per_light point
	The pass is executed once for each point light.
@item iteration 5
	The render state for the pass will be setup and then the draw call will execute 5 times.
@item iteration 5 per_light point
	The render state for the pass will be setup and then the draw call will execute 5 times.  This will be done for each point light.
@item iteration 1 per_n_lights 2 point
	The render state for the pass will be setup and the draw call executed once for every 2 lights.
@end table
@*

By default, passes are only issued once. However, if you use the programmable pipeline, or you wish to exceed the normal limits on the number of lights which are supported, you might want to use the once_per_light option. In this case, only light index 0 is ever used, and the pass is issued multiple times, each time with a different light in light index 0. Clearly this will make the pass more expensive, but it may be the only way to achieve certain effects such as per-pixel lighting effects which take into account 1..n lights.@*@*

Using a number instead of "once" instructs the pass to iterate more than once after the render state is setup.  The render state is not changed after the initial setup so repeated draw calls are very fast and ideal for passes using programmable shaders that must iterate more than once with the same render state ie. shaders that do fur, motion blur, special filtering.@*@*

If you use once_per_light, you should also add an ambient pass to the technique before this pass, otherwise when no lights are in range of this object it will not get rendered at all; this is important even when you have no ambient light in the scene, because you would still want the objects sihouette to appear.@*@*

The lightType parameter to the attribute only applies if you use once_per_light, per_light, or per_n_lights and restricts the pass to being run for lights of a single type (either 'point', 'directional' or 'spot'). In the example, the pass will be run once per point light. This can be useful because when you're writing a vertex / fragment program it is a lot easier if you can assume the kind of lights you'll be dealing with. However at least point and directional lights can be dealt with in one way.
@*@*
Default: iteration once@*@*

@anchor{fur_example}
Example: Simple Fur shader material script that uses a second pass with 10 iterations to grow the fur:
@example
// GLSL simple Fur
vertex_program GLSLDemo/FurVS glsl 
{ 
  source fur.vert 
  default_params
  {
    param_named_auto lightPosition light_position_object_space 0
    param_named_auto eyePosition camera_position_object_space
    param_named_auto passNumber pass_number
    param_named_auto multiPassNumber pass_iteration_number
    param_named furLength float 0.15
  }
} 

fragment_program GLSLDemo/FurFS glsl 
{ 
  source fur.frag 
  default_params
  {
    param_named Ka float 0.2
    param_named Kd float 0.5
    param_named Ks float 0.0
    param_named furTU int 0
  }
} 

material Fur
{ 
  technique GLSL
  { 
    pass base_coat
    { 
      ambient 0.7 0.7 0.7
      diffuse 0.5 0.8 0.5
      specular 1.0 1.0 1.0 1.5

      vertex_program_ref GLSLDemo/FurVS
      {
      }

      fragment_program_ref GLSLDemo/FurFS 
      { 
      } 

      texture_unit
      {
        texture Fur.tga
        tex_coord_set 0
        filtering trilinear
      }

    } 

    pass grow_fur
    { 
      ambient 0.7 0.7 0.7
      diffuse 0.8 1.0 0.8
      specular 1.0 1.0 1.0 64
      depth_write off

      scene_blend src_alpha one
      iteration 10
      
      vertex_program_ref GLSLDemo/FurVS
      {
      }

      fragment_program_ref GLSLDemo/FurFS
      {
      }

      texture_unit
      {
        texture Fur.tga
        tex_coord_set 0
        filtering trilinear
      }
    } 
  } 
}
@end example
Note: use gpu program auto parameters @ref{pass_number} and @ref{pass_iteration_number} to tell the vertex or fragment program the pass number and iteration number.@*@*

@anchor{point_size}
@subheading point_size

This setting allows you to change the size of points when rendering a point list, or a list of point sprites. The interpretation of this command depends on the @ref{point_size_attenuation} option - if it is off (the default), the point size is in screen pixels, if it is on, it expressed as normalised screen coordinates (1.0 is the height of the screen) when the point is at the origin.  @*@*

NOTE: Some drivers have an upper limit on the size of points they support - this can even vary between APIs on the same card! Don't rely on point sizes that cause the points to get very large on screen, since they may get clamped on some cards. Upper sizes can range from 64 to 256 pixels.@*@*

Format: point_size <size>@*@*
Default: point_size 1.0@*@*

@anchor{point_sprites}
@subheading point_sprites

This setting specifies whether or not hardware point sprite rendering is enabled for this pass. Enabling it means that a point list is rendered as a list of quads rather than a list of dots. It is very useful to use this option if you're using a billboardset and only need to use point oriented billboards which are all of the same size. You can also use it for any other point list render. @*@*

Format: point_sprites <on|off>@*@*
Default: point_sprites off@*@*

@anchor{point_size_attenuation}
@subheading point_size_attenuation

Defines whether point size is attenuated with view space distance, and in what fashion. This option is especially useful when you're using point sprites (@xref{point_sprites}) since it defines how they reduce in size as they get further away from the camera. You can also disable this option to make point sprites a constant screen size (like points), or enable it for points so they change size with distance.@*@*

You only have to provide the final 3 parameters if you turn attenuation on. The formula for attenuation is that the size of the point is multiplied by 1 / (constant + linear * dist + quadratic * d^2); therefore turning it off is equivalent to (constant = 1, linear = 0, quadratic = 0) and standard perspective attenuation is (constant = 0, linear = 1, quadratic = 0). The latter is assumed if you leave out the final 3 parameters when you specify 'on'.@*@*

Note that the resulting attenuated size is clamped to the minimum and maximum point size, see the next section.@*@*

Format: point_size_attenuation <on|off> [constant linear quadratic]
Default: point_size_attenuation off

@anchor{point_size_min}
@subheading point_size_min

Sets the minimum point size after attenuation (@ref{point_size_attenuation}). For details on the size metrics, @xref{point_size}.@*@*

Format: point_size_min <size>
Default: point_size_min 0

@anchor{point_size_max}
@subheading point_size_max

Sets the maximum point size after attenuation (@ref{point_size_attenuation}). For details on the size metrics, @xref{point_size}. A value of 0 means the maximum is set to the same as the max size reported by the current card. @*@*

Format: point_size_max <size>
Default: point_size_max 0

@node Texture Units
@subsection Texture Units

Here are the attributes you can use in a 'texture_unit' section of a .material script:

@heading Available Texture Layer Attributes
@itemize @bullet
@item
@ref{texture_alias}
@item
@ref{texture}
@item
@ref{anim_texture}
@item
@ref{cubic_texture}
@item
@ref{tex_coord_set}
@item
@ref{tex_address_mode}
@item
@ref{tex_border_colour}
@item
@ref{filtering}
@item
@ref{max_anisotropy}
@item
@ref{mipmap_bias}
@item
@ref{colour_op}
@item
@ref{colour_op_ex}
@item
@ref{colour_op_multipass_fallback}
@item
@ref{alpha_op_ex}
@item
@ref{env_map}
@item
@ref{scroll}
@item
@ref{scroll_anim}
@item
@ref{rotate}
@item
@ref{rotate_anim}
@item
@ref{scale}
@item
@ref{wave_xform}
@item
@ref{transform}
@item
@ref{binding_type}
@item
@ref{content_type}
@end itemize

You can also use a nested 'texture_source' section in order to use a special add-in as a source of texture data, @xref{External Texture Sources} for details.

@heading Attribute Descriptions
@anchor{texture_alias}
@subheading texture_alias

Sets the alias name for this texture unit.@*@*

Format: texture_alias <name>@*@*

Example: texture_alias NormalMap@*@*

Setting the texture alias name is usefull if this material is to be copied by other other materials and only the textures will be changed in the new material.(@xref{Copying Materials})@*@*
Default: If a texture_unit has a name then the texture_alias defaults to the texture_unit name.

@anchor{texture}
@subheading texture

Sets the name of the static texture image this layer will use.@*@*

Format: texture <texturename> [<type>] [unlimited | numMipMaps] [alpha] [<PixelFormat>]@*@*

Example: texture funkywall.jpg@*@*

This setting is mutually exclusive with the anim_texture attribute. Note that the texture file cannot include spaces. Those of you Windows users who like spaces in filenames, please get over it and use underscores instead.@*@*
The 'type' parameter allows you to specify a the type of texture to create - the default is '2d', but you can override this; here's the full list:
@table @asis
@item 1d
A 1-dimensional texture; that is, a texture which is only 1 pixel high. These kinds of textures can be useful when you need to encode a function in a texture and use it as a simple lookup, perhaps in a fragment program. It is important that you use this setting when you use a fragment program which uses 1-dimensional texture coordinates, since GL requires you to use a texture type that matches (D3D will let you get away with it, but you ought to plan for cross-compatibility). Your texture widths should still be a power of 2 for best compatibility and performance.
@item 2d
The default type which is assumed if you omit it, your texture has a width and a height, both of which should preferably be powers of 2, and if you can, make them square because this will look best on the most hardware. These can be addressed with 2D texture coordinates.
@item 3d
A 3 dimensional texture ie volume texture. Your texture has a width, a height, both of which should be powers of 2, and has depth. These can be addressed with 3d texture coordinates ie through a pixel shader.
@item cubic
This texture is made up of 6 2D textures which are pasted around the inside of a cube. Can be addressed with 3D texture coordinates and are useful for cubic reflection maps and normal maps.
@end table
The 'numMipMaps' option allows you to specify the number of mipmaps to generate for this texture. The default is 'unlimited' which means mips down to 1x1 size are generated. You can specify a fixed number (even 0) if you like instead. Note that if you use the same texture in many material scripts, the number of mipmaps generated will conform to the number specified in the first texture_unit used to load the texture - so be consistent with your usage.@*@*

The 'alpha' option allows you to specify that a single channel (luminence) texture should be loaded as alpha, rather than the default which is to load it into the red channel. This can be helpful if you want to use alpha-only textures in the fixed function pipeline.

Default: none@*@*

The <PixelFormat> option allows you to specify the desired pixel format of the texture to create, which may be different to the pixel format of the texture file being loaded. Bear in mind that the final pixel format will be constrained by hardware capabilities so you may not get exactly what you ask for. The available options are:
@table @asis
@item PF_L8
8-bit pixel format, all bits luminace.
@item PF_L16
16-bit pixel format, all bits luminace.
@item PF_A8
8-bit pixel format, all bits alpha.
@item PF_A4L4
8-bit pixel format, 4 bits alpha, 4 bits luminace.
@item PF_BYTE_LA
2 byte pixel format, 1 byte luminance, 1 byte alpha
@item PF_R5G6B5
16-bit pixel format, 5 bits red, 6 bits green, 5 bits blue.
@item PF_B5G6R5
16-bit pixel format, 5 bits blue, 6 bits green, 5 bits red.
@item PF_R3G3B2
8-bit pixel format, 3 bits red, 3 bits green, 2 bits blue.
@item PF_A4R4G4B4
16-bit pixel format, 4 bits for alpha, red, green and blue.
@item PF_A1R5G5B5
16-bit pixel format, 1 bit for alpha, 5 bits for red, green and blue.
@item PF_R8G8B8
24-bit pixel format, 8 bits for red, green and blue.
@item PF_B8G8R8
24-bit pixel format, 8 bits for blue, green and red.
@item PF_A8R8G8B8
32-bit pixel format, 8 bits for alpha, red, green and blue.
@item PF_A8B8G8R8
32-bit pixel format, 8 bits for alpha, blue, green and red.
@item PF_B8G8R8A8
32-bit pixel format, 8 bits for blue, green, red and alpha.
@item PF_R8G8B8A8
32-bit pixel format, 8 bits for red, green, blue and alpha.
@item PF_X8R8G8B8
32-bit pixel format, 8 bits for red, 8 bits for green, 8 bits for blue
like PF_A8R8G8B8, but alpha will get discarded
@item PF_X8B8G8R8
32-bit pixel format, 8 bits for blue, 8 bits for green, 8 bits for red
like PF_A8B8G8R8, but alpha will get discarded
@item PF_A2R10G10B10
32-bit pixel format, 2 bits for alpha, 10 bits for red, green and blue.
@item PF_A2B10G10R10
32-bit pixel format, 2 bits for alpha, 10 bits for blue, green and red.
@item PF_FLOAT16_R
16-bit pixel format, 16 bits (float) for red
@item PF_FLOAT16_RGB
48-bit pixel format, 16 bits (float) for red, 16 bits (float) for green, 16 bits (float) for blue
@item PF_FLOAT16_RGBA
64-bit pixel format, 16 bits (float) for red, 16 bits (float) for green, 16 bits (float) for blue, 16 bits (float) for alpha
@item PF_FLOAT32_R
16-bit pixel format, 16 bits (float) for red
@item PF_FLOAT32_RGB
96-bit pixel format, 32 bits (float) for red, 32 bits (float) for green, 32 bits (float) for blue
@item PF_FLOAT32_RGBA
128-bit pixel format, 32 bits (float) for red, 32 bits (float) for green, 32 bits (float) for blue, 32 bits (float) for alpha
@item PF_SHORT_RGBA
64-bit pixel format, 16 bits for red, green, blue and alpha
@end table

@anchor{anim_texture}
@subheading anim_texture

Sets the images to be used in an animated texture layer. In this case an animated texture layer means one which has multiple frames, each of which is a separate image file. There are 2 formats, one for implicitly determined image names, one for explicitly named images.@*@*

Format1 (short): anim_texture <base_name> <num_frames> <duration>@*@*

Example: anim_texture flame.jpg 5 2.5@*@*

This sets up an animated texture layer made up of 5 frames named flame_0.jpg, flame_1.jpg, flame_2.jpg etc, with an animation length of 2.5 seconds (2fps). If duration is set to 0, then no automatic transition takes place and frames must be changed manually in code.@*@*

Format2 (long): anim_texture <frame1> <frame2> ... <duration>@*@*

Example: anim_texture flamestart.jpg flamemore.png flameagain.jpg moreflame.jpg lastflame.tga 2.5@*@*

This sets up the same duration animation but from 5 separately named image files. The first format is more concise, but the second is provided if you cannot make your images conform to the naming standard required for it. @*@*

Default: none@*@*

@anchor{cubic_texture}
@subheading cubic_texture

Sets the images used in a cubic texture, i.e. one made up of 6 individual images making up the faces of a cube. These kinds of textures are used for reflection maps (if hardware supports cubic reflection maps) or skyboxes. There are 2 formats, a brief format expecting image names of a particular format and a more flexible but longer format for arbitrarily named textures.@*@*

Format1 (short): cubic_texture <base_name> <combinedUVW|separateUV>@*@*

The base_name in this format is something like 'skybox.jpg', and the system will expect you to provide skybox_fr.jpg, skybox_bk.jpg, skybox_up.jpg, skybox_dn.jpg, skybox_lf.jpg, and skybox_rt.jpg for the individual faces.@*@*

Format2 (long): cubic_texture <front> <back> <left> <right> <up> <down> separateUV@*@*

In this case each face is specified explicitly, incase you don't want to conform to the image naming standards above. You can only use this for the separateUV version since the combinedUVW version requires a single texture name to be assigned to the combined 3D texture (see below).@*@*

In both cases the final parameter means the following:
@table @asis
@item combinedUVW
	The 6 textures are combined into a single 'cubic' texture map which is then addressed using 3D texture coordinates with U, V and W components. Necessary for reflection maps since you never know which face of the box you are going to need. Note that not all cards support cubic environment mapping.
@item separateUV
	The 6 textures are kept separate but are all referenced by this single texture layer. One texture at a time is active (they are actually stored as 6 frames), and they are addressed using standard 2D UV coordinates. This type is good for skyboxes since only one face is rendered at one time and this has more guaranteed hardware support on older cards.
@end table
@*
Default: none

@anchor{binding_type}
@subheading binding_type

Tells this texture unit to bind to either the fragment processing unit or the vertex processing unit (for @ref{Vertex Texture Fetch}). @*@*

Format: binding_type <vertex|fragment>
Default: binding_type fragment

@anchor{content_type}
@subheading content_type

Tells this texture unit where it should get its content from. The default is to get texture content from a named texture, as defined with the @ref{texture}, @ref{cubic_texture}, @ref{anim_texture} attributes. However you can also pull texture information from other automated sources. The options are:

@table @asis
@item named
	The default option, this derives texture content from a texture name, loaded by ordinary means from a file or having been manually created with a given name.
@item shadow
	This option allows you to pull in a shadow texture, and is only valid when you use texture shadows and one of the 'custom sequence' shadowing types (@xref{Shadows}). The shadow texture in question will be from the 'n'th closest light that casts shadows, unless you use light-based pass iteration or the light_start option which may start the light index higher. When you use this option in multiple texture units within the same pass, each one references the next shadow texture. The shadow texture index is reset in the next pass, in case you want to take into account the same shadow textures again in another pass (e.g. a separate specular / gloss pass). By using this option, the correct light frustum projection is set up for you for use in fixed-function, if you use shaders just reference the texture_viewproj_matrix auto parameter in your shader.
@end table

Format: content_type <named|shadow>
Default: content_type named

@anchor{tex_coord_set}
@subheading tex_coord_set

Sets which texture coordinate set is to be used for this texture layer. A mesh can define multiple sets of texture coordinates, this sets which one this material uses.@*@*

Format: tex_coord_set <set_num>@*@*

Example: tex_coord_set 2@*@*

Default: tex_coord_set 0@*@*

@anchor{tex_address_mode}
@subheading tex_address_mode
Defines what happens when texture coordinates exceed 1.0 for this texture layer.You can use the simple format to specify the addressing mode for all 3 potential texture coordinates at once, or you can use the 2/3 parameter extended format to specify a different mode per texture coordinate. @*@*

Simple Format: tex_address_mode <uvw_mode> @*
Extended Format: tex_address_mode <u_mode> <v_mode> [<w_mode>]
@table @asis
@item wrap
	Any value beyond 1.0 wraps back to 0.0. Texture is repeated.
@item clamp
	Values beyond 1.0 are clamped to 1.0. Texture 'streaks' beyond 1.0 since last line of pixels is used across the rest of the address space. Useful for textures which need exact coverage from 0.0 to 1.0 without the 'fuzzy edge' wrap gives when combined with filtering.
@item mirror
	Texture flips every boundary, meaning texture is mirrored every 1.0 u or v
@item border
	Values outside the range [0.0, 1.0] are set to the border colour, you might also set the @ref{tex_border_colour} attribute too.
@end table
@*
Default: tex_address_mode wrap@*@*

@anchor{tex_border_colour}
@subheading tex_border_colour

Sets the border colour of border texture address mode (see @ref{tex_address_mode}). @*@*

Format: tex_border_colour <red> <green> <blue> [<alpha>]@*
NB valid colour values are between 0.0 and 1.0.@*@*

Example: tex_border_colour 0.0 1.0 0.3@*@*

Default: tex_border_colour 0.0 0.0 0.0 1.0@*@*

@anchor{filtering}
@subheading filtering

Sets the type of texture filtering used when magnifying or minifying a texture. There are 2 formats to this attribute, the simple format where you simply specify the name of a predefined set of filtering options, and the complex format, where you individually set the minification, magnification, and mip filters yourself.@*@*
@strong{Simple Format}@*
Format: filtering <none|bilinear|trilinear|anisotropic>@*
Default: filtering bilinear@*@*
With this format, you only need to provide a single parameter which is one of the following:
@table @asis
@item none
	No filtering or mipmapping is used. This is equivalent to the complex format 'filtering point point none'.
@item bilinear
	2x2 box filtering is performed when magnifying or reducing a texture, and a mipmap is picked from the list but no filtering is done between the levels of the mipmaps. This is equivalent to the complex format 'filtering linear linear point'.
@item trilinear
	2x2 box filtering is performed when magnifying and reducing a texture, and the closest 2 mipmaps are filtered together. This is equivalent to the complex format 'filtering linear linear linear'.
@item anisotropic
	This is the same as 'trilinear', except the filtering algorithm takes account of the slope of the triangle in relation to the camera rather than simply doing a 2x2 pixel filter in all cases. This makes triangles at acute angles look less fuzzy. Equivalent to the complex format 'filtering anisotropic anisotropic linear'. Note that in order for this to make any difference, you must also set the @ref{max_anisotropy} attribute too.
@end table
@*@*
@strong{Complex Format}@*
Format: filtering <minification> <magnification> <mip>@*
Default: filtering linear linear point@*@*
This format gives you complete control over the minification, magnification, and mip filters. Each parameter can be one of the following:
@table @asis
@item none
	Nothing - only a valid option for the 'mip' filter , since this turns mipmapping off completely. The lowest setting for min and mag is 'point'. 
@item point
	Pick the closet pixel in min or mag modes. In mip mode, this picks the closet matching mipmap.
@item linear
	Filter a 2x2 box of pixels around the closest one. In the 'mip' filter this enables filtering between mipmap levels.
@item anisotropic
	Only valid for min and mag modes, makes the filter compensate for camera-space slope of the triangles. Note that in order for this to make any difference, you must also set the @ref{max_anisotropy} attribute too.
@end table

@anchor{max_anisotropy}
@subheading max_anisotropy

Sets the maximum degree of anisotropy that the renderer will try to compensate for when filtering textures. The degree of anisotropy is the ratio between the height of the texture segment visible in a screen space region versus the width - so for example a floor plane, which stretches on into the distance and thus the vertical texture coordinates change much faster than the horizontal ones, has a higher anisotropy than a wall which is facing you head on (which has an anisotropy of 1 if your line of sight is perfectly perpendicular to it). You should set the max_anisotropy value to something greater than 1 to begin compensating; higher values can compensate for more acute angles. The maximum value is determined by the hardware, but it is usually 8 or 16. @*@*
In order for this to be used, you have to set the minification and/or the magnification @ref{filtering} option on this texture to anisotropic.

Format: max_anisotropy <value>@*
Default: max_anisotropy 1

@anchor{mipmap_bias}
@subheading mipmap_bias

Sets the bias value applied to the mipmapping calculation, thus allowing you to alter the decision of which level of detail of the texture to use at any distance. The bias value is applied after the regular distance calculation, and adjusts the mipmap level by 1 level for each unit of bias. Negative bias values force larger mip levels to be used, positive bias values force smaller mip levels to be used. The bias is a floating point value so you can use values in between whole numbers for fine tuning.@*@*
In order for this option to be used, your hardware has to support mipmap biasing (exposed through the render system capabilities), and your minification @ref{filtering} has to be set to point or linear.

Format: mipmap_bias <value>@*
Default: mipmap_bias 0


@anchor{colour_op}
@subheading colour_op

Determines how the colour of this texture layer is combined with the one below it (or the lighting effect on the geometry if this is the first layer).@*@*

Format: colour_op <replace|add|modulate|alpha_blend>@*@*

This method is the simplest way to blend texture layers, because it requires only one parameter, gives you the most common blending types, and automatically sets up 2 blending methods: one for if single-pass multitexturing hardware is available, and another for if it is not and the blending must be achieved through multiple rendering passes. It is, however, quite limited and does not expose the more flexible multitexturing operations, simply because these can't be automatically supported in multipass fallback mode. If want to use the fancier options, use @ref{colour_op_ex}, but you'll either have to be sure that enough multitexturing units will be available, or you should explicitly set a fallback using @ref{colour_op_multipass_fallback}.@*
@table @asis
@item replace
	Replace all colour with texture with no adjustment.
@item add
	Add colour components together.
@item modulate
	Multiply colour components together.
@item alpha_blend
	Blend based on texture alpha.
@end table
@*
Default: colour_op modulate

@anchor{colour_op_ex}
@subheading colour_op_ex

This is an extended version of the @ref{colour_op} attribute which allows extremely detailed control over the blending applied between this and earlier layers. Multitexturing hardware can apply more complex blending operations that multipass blendind, but you are limited to the number of texture units which are available in hardware.@*@*

Format: colour_op_ex <operation> <source1> <source2> [<manual_factor>] [<manual_colour1>] [<manual_colour2>]@*@*

Example colour_op_ex add_signed src_manual src_current 0.5@*@*

See the IMPORTANT note below about the issues between mulitpass and multitexturing that using this method can create. Texture colour operations determine how the final colour of the surface appears when rendered. Texture units are used to combine colour values from various sources (e.g. the diffuse colour of the surface from lighting calculations, combined with the colour of the texture). This method allows you to specify the 'operation' to be used, i.e. the calculation such as adds or multiplies, and which values to use as arguments, such as a fixed value or a value from a previous calculation.@*@*

@table @asis
@item Operation options
@table @asis
@item source1
	Use source1 without modification
@item source2
	Use source2 without modification
@item modulate
	Multiply source1 and source2 together.
@item modulate_x2
	Multiply source1 and source2 together, then by 2 (brightening).
@item modulate_x4
	Multiply source1 and source2 together, then by 4 (brightening).
@item add
	Add source1 and source2 together.
@item add_signed
	Add source1 and source2 then subtract 0.5.
@item add_smooth
	Add source1 and source2, subtract the product
@item subtract
	Subtract source2 from source1
@item blend_diffuse_alpha
	Use interpolated alpha value from vertices to scale source1, then add source2 scaled by (1-alpha).
@item blend_texture_alpha
	As blend_diffuse_alpha but use alpha from texture
@item blend_current_alpha
	As blend_diffuse_alpha but use current alpha from previous stages (same as blend_diffuse_alpha for first layer)
@item blend_manual
	As blend_diffuse_alpha but use a constant manual alpha value specified in <manual>
@item dotproduct
	The dot product of source1 and source2
@item blend_diffuse_colour
	Use interpolated colour value from vertices to scale source1, then add source2 scaled by (1-colour).
@end table
@item Source1 and source2 options
@table @asis
@item src_current
	The colour as built up from previous stages.
@item src_texture
	The colour derived from the texture assigned to this layer.
@item src_diffuse
	The interpolated diffuse colour from the vertices (same as 'src_current' for first layer).
@item src_specular
	The interpolated specular colour from the vertices.
@item src_manual
	The manual colour specified at the end of the command.
@end table
@end table
@*
For example 'modulate' takes the colour results of the previous layer, and multiplies them with the new texture being applied. Bear in mind that colours are RGB values from 0.0-1.0 so multiplying them together will result in values in the same range, 'tinted' by the multiply. Note however that a straight multiply normally has the effect of darkening the textures - for this reason there are brightening operations like modulate_x2. Note that because of the limitations on some underlying APIs (Direct3D included) the 'texture' argument can only be used as the first argument, not the second. @*@*

Note that the last parameter is only required if you decide to pass a value manually into the operation. Hence you only need to fill these in if you use the 'blend_manual' operation.@*@*

IMPORTANT: Ogre tries to use multitexturing hardware to blend texture layers together. However, if it runs out of texturing units (e.g. 2 of a GeForce2, 4 on a GeForce3) it has to fall back on multipass rendering, i.e. rendering the same object multiple times with different textures. This is both less efficient and there is a smaller range of blending operations which can be performed. For this reason, if you use this method you really should set the colour_op_multipass_fallback attribute to specify which effect you want to fall back on if sufficient hardware is not available (the default is just 'modulate' which is unlikely to be what you want if you're doing swanky blending here). If you wish to avoid having to do this, use the simpler colour_op attribute which allows less flexible blending options but sets up the multipass fallback automatically, since it only allows operations which have direct multipass equivalents.@*@*

Default: none (colour_op modulate)@*

@anchor{colour_op_multipass_fallback}
@subheading colour_op_multipass_fallback

Sets the multipass fallback operation for this layer, if you used colour_op_ex and not enough multitexturing hardware is available.@*@*

Format: colour_op_multipass_fallback <src_factor> <dest_factor>@*@*

Example: colour_op_mulitpass_fallback one one_minus_dest_alpha@*@*

Because some of the effects you can create using colour_op_ex are only supported under multitexturing hardware, if the hardware is lacking the system must fallback on multipass rendering, which unfortunately doesn't support as many effects. This attribute is for you to specify the fallback operation which most suits you.@*@*

The parameters are the same as in the scene_blend attribute; this is because multipass rendering IS effectively scene blending, since each layer is rendered on top of the last using the same mechanism as making an object transparent, it's just being rendered in the same place repeatedly to get the multitexture effect. If you use the simpler (and less flexible) colour_op attribute you don't need to call this as the system sets up the fallback for you.@*@*

@anchor{alpha_op_ex}
@subheading alpha_op_ex

Behaves in exactly the same away as @ref{colour_op_ex} except that it determines how alpha values are combined between texture layers rather than colour values.The only difference is that the 2 manual colours at the end of colour_op_ex are just single floating-point values in alpha_op_ex.

@anchor{env_map}
@subheading env_map

Turns on/off texture coordinate effect that makes this layer an environment map.@*@*

Format: env_map <off|spherical|planar|cubic_reflection|cubic_normal>@*@*

Environment maps make an object look reflective by using automatic texture coordinate generation depending on the relationship between the objects vertices or normals and the eye.@*@*
@table @asis
@item spherical
	A spherical environment map. Requires a single texture which is either a fish-eye lens view of the reflected scene, or some other texture which looks good as a spherical map (a texture of glossy highlights is popular especially in car sims). This effect is based on the relationship between the eye direction and the vertex normals of the object, so works best when there are a lot of gradually changing normals, i.e. curved objects.
@item planar
	Similar to the spherical environment map, but the effect is based on the position of the vertices in the viewport rather than vertex normals. This effect is therefore useful for planar geometry (where a spherical env_map would not look good because the normals are all the same) or objects without normals.
@item cubic_reflection
	A more advanced form of reflection mapping which uses a group of 6 textures making up the inside of a cube, each of which is a view if the scene down each axis. Works extremely well in all cases but has a higher technical requirement from the card than spherical mapping. Requires that you bind a @ref{cubic_texture} to this texture unit and use the 'combinedUVW' option.
@item cubic_normal
	Generates 3D texture coordinates containing the camera space normal vector from the normal information held in the vertex data. Again, full use of this feature requires a @ref{cubic_texture} with the 'combinedUVW' option.
	
@end table
@*
Default: env_map off@*

@anchor{scroll}
@subheading scroll


Sets a fixed scroll offset for the texture.@*@*

Format: scroll <x> <y>@*@*

This method offsets the texture in this layer by a fixed amount. Useful for small adjustments without altering texture coordinates in models. However if you wish to have an animated scroll effect, see the @ref{scroll_anim} attribute.@*@*

@anchor{scroll_anim}
@subheading scroll_anim

Sets up an animated scroll for the texture layer. Useful for creating fixed-speed scrolling effects on a texture layer (for varying scroll speeds, see @ref{wave_xform}).@*@*

Format: scroll_anim <xspeed> <yspeed>@*

@anchor{rotate}
@subheading rotate

Rotates a texture to a fixed angle. This attribute changes the rotational orientation of a texture to a fixed angle, useful for fixed adjustments. If you wish to animate the rotation, see @ref{rotate_anim}.@*@*

Format: rotate <angle>@*@*

The parameter is a anticlockwise angle in degrees.@*@*

@anchor{rotate_anim}
@subheading rotate_anim

Sets up an animated rotation effect of this layer. Useful for creating fixed-speed rotation animations (for varying speeds, see @ref{wave_xform}).@*@*

Format: rotate_anim <revs_per_second>@*@*

The parameter is a number of anticlockwise revolutions per second.@*@*

@anchor{scale}
@subheading scale

Adjusts the scaling factor applied to this texture layer. Useful for adjusting the size of textures without making changes to geometry. This is a fixed scaling factor, if you wish to animate this see @ref{wave_xform}.@*@*

Format: scale <x_scale> <y_scale>@*@*

Valid scale values are greater than 0, with a scale factor of 2 making the texture twice as big in that dimension etc.@*@*

@anchor{wave_xform}
@subheading wave_xform

Sets up a transformation animation based on a wave function. Useful for more advanced texture layer transform effects. You can add multiple instances of this attribute to a single texture layer if you wish.@*@*

Format: wave_xform <xform_type> <wave_type> <base> <frequency> <phase> <amplitude>@*@*

Example: wave_xform scale_x sine 1.0 0.2 0.0 5.0@*@*
@table @asis
@item xform_type
@table @asis
@item scroll_x
	Animate the x scroll value
@item scroll_y
	Animate the y scroll value
@item rotate
	Animate the rotate value
@item scale_x
	Animate the x scale value
@item scale_y
	Animate the y scale value
@end table
@item wave_type
@table @asis
@item sine
	A typical sine wave which smoothly loops between min and max values
@item triangle
	An angled wave which increases & decreases at constant speed, changing instantly at the extremes
@item square
	Max for half the wavelength, min for the rest with instant transition between
@item sawtooth
	Gradual steady increase from min to max over the period with an instant return to min at the end.
@item inverse_sawtooth
	Gradual steady decrease from max to min over the period, with an instant return to max at the end.
@end table
@item base
	The base value, the minimum if amplitude > 0, the maximum if amplitdue < 0
@item frequency
	The number of wave iterations per second, i.e. speed
@item phase
	Offset of the wave start
@item amplitude
	The size of the wave
@end table
@*
The range of the output of the wave will be {base, base+amplitude}. So the example above scales the texture in the x direction between 1 (normal size) and 5 along a sine wave at one cycle every 5 second (0.2 waves per second).@*@*

@anchor{transform}
@subheading transform

This attribute allows you to specify a static 4x4 transformation matrix for the texture unit, thus replacing the individual scroll, rotate and scale attributes mentioned above. @*@*

Format: transform m00 m01 m02 m03 m10 m11 m12 m13 m20 m21 m22 m23 m30 m31 m32 m33@*@*

The indexes of the 4x4 matrix value above are expressed as m<row><col>.

@node Declaring Vertex and Fragment Programs
@subsection Declaring Vertex and Fragment Programs

In order to use a vertex or fragment program in your materials (@xref{Using Vertex and Fragment Programs in a Pass}), 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.@*@*

The 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} .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.@*@*

Vertex 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 DirectX9 HLSL, Open GL Shader Language, or nVidia's Cg language (@xref{High-level Programs}). 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.@*@*

Here is an example of a definition of a low-level vertex program:
@example
vertex_program myVertexProgram asm
{
    source myVertexProgram.asm 
    syntax vs_1_1
}
@end example
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.@*@*

The current supported syntaxes are:
@table @asis
@item vs_1_1
This is one of the DirectX vertex shader assembler syntaxes. @*
Supported on cards from: ATI Radeon 8500, nVidia GeForce 3 @*
@item vs_2_0
Another one of the DirectX vertex shader assembler syntaxes. @*
Supported on cards from: ATI Radeon 9600, nVidia GeForce FX 5 series @*
@item vs_2_x
Another one of the DirectX vertex shader assembler syntaxes. @*
Supported on cards from: ATI Radeon X series, nVidia GeForce FX 6 series @*
@item vs_3_0
Another one of the DirectX vertex shader assembler syntaxes. @*
Supported on cards from: nVidia GeForce FX 6 series
@item arbvp1
This is the OpenGL standard assembler format for vertex programs. It's roughly equivalent to DirectX vs_1_1.
@item vp20
This is an nVidia-specific OpenGL vertex shader syntax which is a superset of vs 1.1. 
@item vp30
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.
@item vp40
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.
@item ps_1_1, ps_1_2, ps_1_3
DirectX pixel shader (ie fragment program) assembler syntax. @*
Supported on cards from: ATI Radeon 8500, nVidia GeForce 3 @*
NOTE: 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.
@item ps_1_4
DirectX pixel shader (ie fragment program) assembler syntax. @*
Supported on cards from: ATI Radeon 8500, nVidia GeForce FX 5 series @*
NOTE: 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.
@item ps_2_0
DirectX pixel shader (ie fragment program) assembler syntax. @*
Supported cards: ATI Radeon 9600, nVidia GeForce FX 5 series@*
@item ps_2_x
DirectX pixel shader (ie fragment program) assembler syntax. This is basically
ps_2_0 with a higher number of instructions. @*
Supported cards: ATI Radeon X series, nVidia GeForce FX 6 series@*
@item ps_3_0
DirectX pixel shader (ie fragment program) assembler syntax. @*
Supported cards: nVidia GeForce FX6 series@*
@item ps_3_x
DirectX pixel shader (ie fragment program) assembler syntax. @*
Supported cards: nVidia GeForce FX7 series@*
@item arbfp1
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).
@item fp20
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.
@item fp30
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.
@item fp40
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.

@end table

You can get a definitive list of the syntaxes supported by the current card by calling GpuProgramManager::getSingleton().getSupportedSyntax().@*@*

@anchor{Default Program Parameters}
@subheading Default Program Parameters
While 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:
@example
vertex_program Ogre/CelShadingVP cg
{
	source Example_CelShading.cg
	entry_point main_vp
	profiles vs_1_1 arbvp1

	default_params
	{
		param_named_auto lightPosition light_position_object_space 0
		param_named_auto eyePosition camera_position_object_space
		param_named_auto worldViewProj worldviewproj_matrix
		param_named shininess float 10 
	}
}
@end example
The syntax of the parameter definition is exactly the same as when you define parameters when using programs, @xref{Program Parameter Specification}. 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.

@node High-level Programs
@heading High-level Programs
Support 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 (@ref{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 (@ref{HLSL}), and OpenGL Shader Language (@ref{GLSL}). HLSL can only be used with the DirectX rendersystem, and GLSL can only be used with the GL rendersystem. Cg can be used with both, although experience has shown that more advanced programs, particularly fragment programs which perform a lot of texture fetches, can produce better code in the rendersystem-specific shader langauge. @*@*

One way to support both HLSL and GLSL is to include seperate techniques in the material script, each one referencing separate programs. However, if the programs are basically the same, with the same parameters, and the techniques are complex this can bloat your material scripts with duplication fairly quickly. Instead, if the only difference is the language of the vertex & fragment program you can use OGRE's @ref{Unified High-level Programs} to automatically pick a program suitable for your rendersystem whilst using a single technique.@*@*

@subheading Skeletal Animation in Vertex Programs
You 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:
@example
	includes_skeletal_animation true
@end example
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. Note that ALL submeshes must be assigned a material which implements this, and that if you combine skeletal animation with vertex animation (@xref{Animation}) then all techniques must be hardware accelerated for any to be.

@subheading Morph Animation in Vertex Programs
You can implement morph animation in hardware by writing a vertex program which linearly blends between the first and second position keyframes passed as positions and the first free texture coordinate set, and by binding the animation_parametric value to a parameter (which tells you how far to interpolate between the two). However, you need to communicate this support to Ogre so it does not perform morph animation in software for you. You do this by adding the following attribute to your vertex_program definition:
@example
	includes_morph_animation true
@end example
When you do this, any skeletally animated entity which uses this material will forgo the usual software morph and will expect the vertex program to do it. Note that if your model includes both skeletal animation and morph animation, they must both be implemented in the vertex program if either is to be hardware acceleration. Note that ALL submeshes must be assigned a material which implements this, and that if you combine skeletal animation with vertex animation (@xref{Animation}) then all techniques must be hardware accelerated for any to be.

@subheading Pose Animation in Vertex Programs
You can implement pose animation (blending between multiple poses based on weight) in a vertex program by pulling in the original vertex data (bound to position), and as many pose offset buffers as you've defined in your 'includes_pose_animation' declaration, which will be in the first free texture unit upwards. You must also use the animation_parametric parameter to define the starting point of the constants which will contain the pose weights; they will start at the parameter you define and fill 'n' constants, where 'n' is the max number of poses this shader can blend, ie the parameter to includes_pose_animation. 
@example
	includes_pose_animation 4
@end example
Note that ALL submeshes must be assigned a material which implements this, and that if you combine skeletal animation with vertex animation (@xref{Animation}) then all techniques must be hardware accelerated for any to be.

@subheading Vertex texture fetching in vertex programs
If your vertex program makes use of @ref{Vertex Texture Fetch}, you should declare that with the 'uses_vertex_texture_fetch' directive. This is enough to tell Ogre that your program uses this feature and that hardware support for it should be checked.
@example
	uses_vertex_texture_fetch true
@end example
	

@subheading Vertex Programs With Shadows
When using shadows (@xref{Shadows}), 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. @*@*

If you use @strong{stencil shadows}, 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. @*@*

If you use @strong{texture shadows}, then vertex deformation is acceptable; however, when rendering the object into a shadow texture (the shadow caster pass), the shadow has to be rendered in a solid colour (linked to the ambient colour for modulative shadows, black for additive shadows). You must therefore provide an alternative vertex program, so Ogre provides you with a way of specifying one to use when rendering the caster, @xref{Shadows and Vertex Programs}.


@node Cg
@subsection Cg programs
In 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:
@example
fragment_program myCgFragmentProgram cg
{
    source myCgFragmentProgram.cg
    entry_point main
    profiles ps_2_0 arbfp1
}
@end example
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. @*@*
Here 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.@*@*
Next, 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.@*@*

Lastly, there is a final option called 'compile_arguments', where you can specify arguments exactly as you would to the cgc command-line compiler, should you wish to.

@node HLSL
@subsection DirectX9 HLSL
DirectX9 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:
@example
vertex_program myHLSLVertexProgram hlsl
{
    source myHLSLVertexProgram.txt
    entry_point main
    target vs_2_0
}
@end example
As you can see, the main 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.@*@*

@strong{Important Matrix Ordering Note:} One thing to bear in mind is that HLSL allows you to use 2 different ways to multiply a veector by a matrix - mul(v,m) or mul(m,v). The only difference between them is that the matrix is effectively transposed. You should use mul(m,v) with the matrices passed in from Ogre - this agrees with the shaders produced from tools like RenderMonkey, and is consistent with Cg too, but disagrees with the Dx9 SDK and FX Composer which use mul(v,m) - you will have to switch the parameters to mul() in those shaders.@*@*

Note that if you use the float3x4 / matrix3x4 type in your shader, bound to an OGRE auto-definition (such as bone matrices) you should use the column_major_matrices = false option (discussed below) in your program definition. This is because OGRE passes float3x4 as row-major to save constant space (3 float4's rather than 4 float4's with only the top 3 values used) and this tells OGRE to pass all matrices like this, so that you can use mul(m,v) consistently for all calculations. OGRE will also to tell the shader to compile in row-major form (you don't have to set the /Zpr compile option or #pragma pack(row-major) option, OGRE does this for you). Note that passing bones in float4x3 form is not supported by OGRE, but you don't need it given the above.@*@*

@strong{Advanced options}@*
@table @asis
@item preprocessor_defines <defines>
This allows you to define symbols which can be used inside the HLSL shader code to alter the behaviour (through #ifdef or #if clauses). Definitions are separated by ';' or ',' and may optionally have a '=' operator within them to specify a definition value. Those without an '=' will implicitly have a definition of 1.
@item column_major_matrices <true|false>
The default for this option is 'true' so that OGRE passes matrices auto-bound matrices in a form where mul(m,v) works. Setting this option to false does 2 things - it transpose auto-bound 4x4 matrices and also sets the /Zpr (row-major) option on the shader compilation. This means you can still use mul(m,v), but the matrix layout is row-major instead. This is only useful if you need to use bone matrices (float3x4) in a shader since it saves a float4 constant for every bone involved.
@end table

@include glsl.inc

@node Unified High-level Programs
@subsection Unified High-level Programs

As mentioned above, it can often be useful to write both HLSL and GLSL programs to specifically target each platform, but if you do this via multiple material techniques this can cause a bloated material definition when the only difference is the program language. Well, there is another option. You can 'wrap' multiple programs in a 'unified' program definition, which will automatically choose one of a series of 'delegate' programs depending on the rendersystem and hardware support.
@example
vertex_program myVertexProgram unified
{
	delegate realProgram1
	delegate realProgram2
	... etc
}
@end example
This works for both vertex and fragment programs, and you can list as many delegates as you like - the first one to be supported by the current rendersystem & hardware will be used as the real program. This is almost like a mini-technique system, but for a single program and with a much tighter purpose. You can only use this where the programs take all the same inputs, particularly textures and other pass / sampler state. Where the only difference between the programs is the language (or possibly the target in HLSL - you can include multiple HLSL programs with different targets in a single unified program too if you want, or indeed any number of other high-level programs), this can become a very powerful feature. For example, without this feature here's how you'd have to define a programmable material which supported HLSL and GLSL:
@example
vertex_program myVertexProgramHLSL hlsl
{
	source prog.hlsl
	entry_point main_vp
	target vs_2_0
}
fragment_program myFragmentProgramHLSL hlsl
{
	source prog.hlsl
	entry_point main_fp
	target ps_2_0
}
vertex_program myVertexProgramGLSL glsl
{
	source prog.vert
}
fragment_program myFragmentProgramGLSL glsl
{
	source prog.frag
	default_params
	{
		param_named tex int 0
	}
}
material SupportHLSLandGLSLwithoutUnified
{
	// HLSL technique
	technique
	{
		pass
		{
			vertex_program_ref myVertexProgramHLSL
			{
				param_named_auto worldViewProj world_view_proj_matrix
				param_named_auto lightColour light_diffuse_colour 0
				param_named_auto lightSpecular light_specular_colour 0
				param_named_auto lightAtten light_attenuation 0
			}
			fragment_program_ref myFragmentProgramHLSL
			{
			}
		}
	}
	// GLSL technique
	technique
	{
		pass
		{
			vertex_program_ref myVertexProgramHLSL
			{
				param_named_auto worldViewProj world_view_proj_matrix
				param_named_auto lightColour light_diffuse_colour 0
				param_named_auto lightSpecular light_specular_colour 0
				param_named_auto lightAtten light_attenuation 0
			}
			fragment_program_ref myFragmentProgramHLSL
			{
			}
		}
	}
}
@end example
And that's a really small example. Everything you added to the HLSL technique, you'd have to duplicate in the GLSL technique too. So instead, here's how you'd do it with unified program definitions:
@example
vertex_program myVertexProgramHLSL hlsl
{
	source prog.hlsl
	entry_point main_vp
	target vs_2_0
}
fragment_program myFragmentProgramHLSL hlsl
{
	source prog.hlsl
	entry_point main_fp
	target ps_2_0
}
vertex_program myVertexProgramGLSL glsl
{
	source prog.vert
}
fragment_program myFragmentProgramGLSL glsl
{
	source prog.frag
	default_params
	{
		param_named tex int 0
	}
}
// Unified definition
vertex_program myVertexProgram unified
{
	delegate myVertexProgramGLSL
	delegate myVertexProgramHLSL
}
fragment_program myFragmentProgram unified
{
	delegate myFragmentProgramGLSL
	delegate myFragmentProgramHLSL
}
material SupportHLSLandGLSLwithUnified
{
	// HLSL technique
	technique
	{
		pass
		{
			vertex_program_ref myVertexProgram
			{
				param_named_auto worldViewProj world_view_proj_matrix
				param_named_auto lightColour light_diffuse_colour 0
				param_named_auto lightSpecular light_specular_colour 0
				param_named_auto lightAtten light_attenuation 0
			}
			fragment_program_ref myFragmentProgram
			{
			}
		}
	}
}
@end example
At runtime, when myVertexProgram or myFragmentProgram are used, OGRE automatically picks a real program to delegate to based on what's supported on the current hardware / rendersystem. If none of the delegates are supported, the entire technique referencing the unified program is marked as unsupported and the next technique in the material is checked fro fallback, just like normal. As your materials get larger, and you find you need to support HLSL and GLSL specifically (or need to write multiple interface-compatible versions of a program for whatever other reason), unified programs can really help reduce duplication.


@node Using Vertex and Fragment Programs in a Pass
@subsection Using Vertex and Fragment Programs in a Pass

Within a pass section of a material script, you can reference a vertex and / or a fragment program which is been defined in a .program script (@xref{Declaring Vertex and Fragment Programs}). The programs are defined separately from the usage of them in the pass, since the programs are very likely to be reused between many separate materials, probably across many different .material scripts, so this approach lets you define the program only once and use it many times.@*@*

As well as naming the program in question, you can also provide parameters to it. Here's a simple example:
@example
vertex_program_ref myVertexProgram
{
	param_indexed_auto 0 worldviewproj_matrix
	param_indexed      4 float4  10.0 0 0 0
}
@end example
In this example, we bind a vertex program called 'myVertexProgram' (which will be defined elsewhere) to the pass, and give it 2 parameters, one is an 'auto' parameter, meaning we do not have to supply a value as such, just a recognised code (in this case it's the world/view/projection matrix which is kept up to date automatically by Ogre). The second parameter is a manually specified parameter, a 4-element float. The indexes are described later.@*@*

The syntax of the link to a vertex program and a fragment program are identical, the only difference is that 'fragment_program_ref' is used instead of 'vertex_program_ref'.@*@*

For many situations a vertex and fragment program are associated with each other in a pass but this is not cast in stone.  You could have a vertex program that can be used by several different fragment programs.  Another situation that arises is that you can mix fixed pipeline and programmable pipeline (shaders) together. You could use the non-programable vertex fixed function pipeline and then provide a fragment_program_ref in a pass ie there would be no vertex_program_ref section in the pass.  The fragment program referenced in the pass must meet the requirements as defined in the related API in order to read from the outputs of the vertex fixed pipeline.  You could also just have a vertex program that outputs to the fragment fixed function pipeline.@*@*

The requirements to read from or write to the fixed function pipeline are similar between rendering API's (DirectX and OpenGL) but how its actually done in each type of shader (vertex or fragment) depends on the shader language.  For HLSL (DirectX API) and associated asm consult MSDN at @url{http://msdn.microsoft.com/library/}. For GLSL (OpenGL), consult section 7.6 of the GLSL spec 1.1 available at @url{http://developer.3dlabs.com/documents/index.htm}.  The built in varying variables provided in GLSL allow your program to read/write to the fixed function pipeline varyings.  For Cg consult the Language Profiles section in CgUsersManual.pdf that comes with the Cg Toolkit available at @url{http://developer.nvidia.com/object/cg_toolkit.html}.  For HLSL and Cg its the varying bindings that allow your shader programs to read/write to the fixed function pipeline varyings.@*@*

@anchor{Program Parameter Specification}
@subheading Parameter specification
Parameters can be specified using one of 4 commands as shown below. The same syntax is used whether you are defining a parameter just for this particular use of the program, or when specifying the @ref{Default Program Parameters}. Parameters set in the specific use of the program override the defaults.
@itemize @bullet
@item @ref{param_indexed}
@item @ref{param_indexed_auto}
@item @ref{param_named}
@item @ref{param_named_auto}
@end itemize

@anchor{param_indexed}
@subheading param_indexed
This command sets the value of an indexed parameter. @*@*

format: param_indexed <index> <type> <value>@*@*
example: param_indexed 0 float4 10.0 0 0 0@*@*

The 'index' is simply a number representing the position in the parameter list which the value should be written, and you should derive this from your program definition. The index is relative to the way constants are stored on the card, which is in 4-element blocks. For example if you defined a float4 parameter at index 0, the next index would be 1. If you defined a matrix4x4 at index 0, the next usable index would be 4, since a 4x4 matrix takes up 4 indexes.@*@*

The value of 'type' can be float4, matrix4x4, float<n>, int4, int<n>. Note that 'int' parameters are only available on some more advanced program syntaxes, check the D3D or GL vertex / fragment program documentation for full details. Typically the most useful ones will be float4 and matrix4x4. Note that if you use a type which is not a multiple of 4, then the remaining values up to the multiple of 4 will be filled with zeroes for you (since GPUs always use banks of 4 floats per constant even if only one is used).@*@*

'value' is simply a space or tab-delimited list of values which can be converted into the type you have specified.

@anchor{param_indexed_auto}
@subheading param_indexed_auto

This command tells Ogre to automatically update a given parameter with a derived value. This frees you from writing code to update program parameters every frame when they are always changing.@*@*

format: param_indexed_auto <index> <value_code> <extra_params>@*@*
example: param_indexed_auto 0 worldviewproj_matrix@*@*

'index' has the same meaning as @ref{param_indexed}; note this time you do not have to specify the size of the parameter because the engine knows this already. In the example, the world/view/projection matrix is being used so this is implicitly a matrix4x4.@*@*

'value_code' is one of a list of recognised values:@*
@table @asis
@item world_matrix
The current world matrix.
@item inverse_world_matrix
The inverse of the current world matrix.
@item transpose_world_matrix
The transpose of the world matrix
@item inverse_transpose_world_matrix
The inverse transpose of the world matrix

@item world_matrix_array_3x4
An array of world matrices, each represented as only a 3x4 matrix (3 rows of 4columns) usually for doing hardware skinning. You should make enough entries available in your vertex program for the number of bones in use, ie an array of numBones*3 float4's.

@item view_matrix
The current view matrix.
@item inverse_view_matrix
The inverse of the current view matrix.
@item transpose_view_matrix
The transpose of the view matrix
@item inverse_transpose_view_matrix
The inverse transpose of the view matrix

@item projection_matrix
The current projection matrix.
@item inverse_projection_matrix
The inverse of the projection matrix
@item transpose_projection_matrix
The transpose of the projection matrix
@item inverse_transpose_projection_matrix
The inverse transpose of the projection matrix

@item worldview_matrix
The current world and view matrices concatenated.
@item inverse_worldview_matrix
The inverse of the current concatenated world and view matrices.
@item transpose_worldview_matrix
The transpose of the world and view matrices
@item inverse_transpose_worldview_matrix
The inverse transpose of the current concatenated world and view matrices.

@item viewproj_matrix
The current view and projection matrices concatenated.
@item inverse_viewproj_matrix
The inverse of the view & projection matrices
@item transpose_viewproj_matrix
The transpose of the view & projection matrices
@item inverse_transpose_viewproj_matrix
The inverse transpose of the view & projection matrices

@item worldviewproj_matrix
The current world, view and projection matrices concatenated.
@item inverse_worldviewproj_matrix
The inverse of the world, view and projection matrices
@item transpose_worldviewproj_matrix
The transpose of the world, view and projection matrices
@item inverse_transpose_worldviewproj_matrix
The inverse transpose of the world, view and projection matrices

@item render_target_flipping
The value use to adjust transformed y position if bypassed projection matrix transform. It's -1 if the render target requires texture flipping, +1 otherwise.

@item light_diffuse_colour
The diffuse colour of a given light; this requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light - note that directional lights are always first in the list and always present). NB if there are no lights this close, then the parameter will be set to black.
@item light_specular_colour
The specular colour of a given light; this requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light). NB if there are no lights this close, then the parameter will be set to black.
@item light_attenuation
A float4 containing the 4 light attenuation variables for a given light. This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light). NB if there are no lights this close, then the parameter will be set to all zeroes. The order of the parameters is range, constant attenuation, linear attenuation, quadric attenuation.
@item spotlight_params
A float4 containing the 3 spotlight parameters and a control value. The order of the parameters is cos(inner angle /2 ), cos(outer angle / 2), falloff, and the final w value is 1.0f. For non-spotlights the value is float4(1,0,0,1). This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light). If there are less lights than this, the details are like a non-spotlight.
@item light_position
The position of a given light in world space. This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light). NB if there are no lights this close, then the parameter will be set to all zeroes. Note that this property will work with all kinds of lights, even directional lights, since the parameter is set as a 4D vector. Point lights will be (pos.x, pos.y, pos.z, 1.0f) whilst directional lights will be (-dir.x, -dir.y, -dir.z, 0.0f). Operations like dot products will work consistently on both.
@item light_direction
The direction of a given light in world space. This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light). NB if there are no lights this close, then the parameter will be set to all zeroes. DEPRECATED - this property only works on directional lights, and we recommend that you use light_position instead since that returns a generic 4D vector.
@item light_position_object_space
The position of a given light in object space (ie when the object is at (0,0,0)). This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light). NB if there are no lights this close, then the parameter will be set to all zeroes.  Note that this property will work with all kinds of lights, even directional lights, since the parameter is set as a 4D vector. Point lights will be (pos.x, pos.y, pos.z, 1.0f) whilst directional lights will be (-dir.x, -dir.y, -dir.z, 0.0f). Operations like dot products will work consistently on both.
@item light_direction_object_space
The direction of a given light in object space (ie when the object is at (0,0,0)). This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light). NB if there are no lights this close, then the parameter will be set to all zeroes.  DEPRECATED, except for spotlights - for directional lights we recommend that you use light_position_object_space instead since that returns a generic 4D vector.
@item light_distance_object_space
The distance of a given light from the centre of the object - this is a useful approximation to per-vertex distance calculations for relatively small objects. This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light). NB if there are no lights this close, then the parameter will be set to all zeroes.  
@item light_position_view_space
The position of a given light in view space (ie when the camera is at (0,0,0)). This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light). NB if there are no lights this close, then the parameter will be set to all zeroes.  Note that this property will work with all kinds of lights, even directional lights, since the parameter is set as a 4D vector. Point lights will be (pos.x, pos.y, pos.z, 1.0f) whilst directional lights will be (-dir.x, -dir.y, -dir.z, 0.0f). Operations like dot products will work consistently on both.
@item light_direction_view_space
The direction of a given light in view space (ie when the camera is at (0,0,0)). This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light). NB if there are no lights this close, then the parameter will be set to all zeroes.  DEPRECATED, except for spotlights - for directional lights we recommend that you use light_position_view_space instead since that returns a generic 4D vector.
@item light_power
The 'power' scaling for a given light, useful in HDR rendering. This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light).
@item light_diffuse_colour_array
As light_diffuse_colour, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item light_specular_colour_array
As light_specular_colour, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item light_attenuation_array
As light_attenuation, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item spotlight_params_array
As spotlight_params, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item light_position_array
As light_position, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item light_direction_array
As light_direction, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item light_position_object_space_array
As light_position_object_space, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item light_direction_object_space_array
As light_direction_object_space, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item light_distance_object_space_array
As light_distance_object_space, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item light_position_view_space_array
As light_position_view_space, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item light_direction_view_space_array
As light_direction_view_space, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item light_power_array
As light_power, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.

@item ambient_light_colour
The colour of the ambient light currently set in the scene.

@item surface_ambient_colour
The ambient colour reflectance properties of the pass (@xref{ambient}). This allows you access to fixed-function pipeline property handily.
@item surface_diffuse_colour
The diffuse colour reflectance properties of the pass (@xref{diffuse}). This allows you access to fixed-function pipeline property handily.
@item surface_specular_colour
The specular colour reflectance properties of the pass (@xref{specular}). This allows you access to fixed-function pipeline property handily.
@item surface_emissive_colour
The amount of self-illumination of the pass (@xref{emissive}). This allows you access to fixed-function pipeline property handily.
@item surface_shininess
The shininess of the pass, affecting the size of specular highlights (@xref{specular}). This allows you bind to fixed-function pipeline property handily.

@item derived_ambient_light_colour
The derived ambient light colour, with 'r', 'g', 'b' components filled with product of surface_ambient_colour and ambient_light_colour, respectively, and 'a' component filled with surface ambient alpha component.
@item derived_scene_colour
The derived scene colour, with 'r', 'g' and 'b' components filled with sum of derived_ambient_light_colour and surface_emissive_colour, respectively, and 'a' component filled with surface diffuse alpha component.

@item derived_light_diffuse_colour
The derived light diffuse colour, with 'r', 'g' and 'b' components filled with product of surface_diffuse_colour and light_diffuse_colour, respectively, and 'a' component filled with surface diffuse alpha component. This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light).
@item derived_light_specular_colour
The derived light specular colour, with 'r', 'g' and 'b' components filled with product of surface_specular_colour and light_specular_colour, respectively, and 'a' component filled with surface specular alpha component. This requires an index in the 'extra_params' field, and relates to the 'nth' closest light which could affect this object (ie 0 refers to the closest light).
@item derived_light_diffuse_colour_array
As derived_light_diffuse_colour, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.
@item derived_light_specular_colour_array
As derived_light_specular_colour, except that this populates an array of parameters with a number of lights, and the 'extra_params' field refers to the number of 'nth closest' lights to be processed. This parameter is not compatible with light-based pass_iteration options but can be used for single-pass lighting.

@item fog_colour
The colour of the fog currently set in the scene.
@item fog_params
The parameters of the fog currently set in the scene. Packed as (exp_density, linear_start, linear_end, 1.0 / (linear_end - linear_start)).
@item camera_position
The current cameras position in world space.
@item camera_position_object_space
The current cameras position in object space (ie when the object is at (0,0,0)).
@item time
The current time, factored by the optional parameter (or 1.0f if not supplied).
@item time_0_x
Single float time value, which repeats itself based on "cycle time" given as an 'extra_params' field
@item costime_0_x
Cosine of time_0_x
@item sintime_0_x
Sine of time_0_x
@item tantime_0_x
Tangent of time_0_x
@item time_0_x_packed
4-element vector of time0_x, sintime0_x, costime0_x, tantime0_x
@item time_0_1
As time0_x but scaled to [0..1]
@item costime_0_1
As costime0_x but scaled to [0..1]
@item sintime_0_1
As sintime0_x but scaled to [0..1]
@item tantime_0_1
As tantime0_x but scaled to [0..1]
@item time_0_1_packed
As time0_x_packed but all values scaled to [0..1]
@item time_0_2pi
As time0_x but scaled to [0..2*Pi]
@item costime_0_2pi
As costime0_x but scaled to [0..2*Pi]
@item sintime_0_2pi
As sintime0_x but scaled to [0..2*Pi]
@item tantime_0_2pi
As tantime0_x but scaled to [0..2*Pi]
@item time_0_2pi_packed
As time0_x_packed but scaled to [0..2*Pi]
@item frame_time
The current frame time, factored by the optional parameter (or 1.0f if not supplied).
@item fps
The current frames per second
@item viewport_width
The current viewport width in pixels
@item viewport_height
The current viewport height in pixels
@item inverse_viewport_width
1.0/the current viewport width in pixels
@item inverse_viewport_height
1.0/the current viewport height in pixels
@item viewport_size
4-element vector of viewport_width, viewport_height, inverse_viewport_width, inverse_viewport_height
@item texel_offsets
Provides details of the rendersystem-specific texture coordinate offsets required to map texels onto pixels. float4(horizontalOffset, verticalOffset, horizontalOffset / viewport_width, verticalOffset / viewport_height).
@item view_direction
View direction vector in object space
@item view_side_vector
View local X axis
@item view_up_vector
View local Y axis
@item fov
Vertical field of view, in radians
@item near_clip_distance
Near clip distance, in world units
@item far_clip_distance
Far clip distance, in world units (may be 0 for infinite view projection)
@item texture_viewproj_matrix
Applicable to vertex programs which have been specified as the 'shadow receiver' vertex program alternative, or where a texture unit is marked as content_type shadow; this provides details of the view/projection matrix for the current shadow projector. The optional 'extra_params' entry specifies which light the projector refers to (for the case of content_type shadow where more than one shadow texture may be present in a single pass), where 0 is the default and refers to the first light referenced in this pass.
@item scene_depth_range
Provides information about the depth range as viewed from the current camera being used to render. Provided as float4(minDepth, maxDepth, depthRange, 1 / depthRange).
@item shadow_scene_depth_range
Provides information about the depth range as viewed from the shadow camera relating to a selected light. Requires a light index parameter. Provided as float4(minDepth, maxDepth, depthRange, 1 / depthRange).
@item texture_size
Provides texture size of the selected texture unit. Requires a texture unit index parameter. Provided as float4(width, height, depth, 1). For 2D-texture, depth sets to 1, for 1D-texture, height and depth sets to 1.
@item inverse_texture_size
Provides inverse texture size of the selected texture unit. Requires a texture unit index parameter. Provided as float4(1 / width, 1 / height, 1 / depth, 1). For 2D-texture, depth sets to 1, for 1D-texture, height and depth sets to 1.
@item packed_texture_size
Provides packed texture size of the selected texture unit. Requires a texture unit index parameter. Provided as float4(width, height, 1 / width, 1 / height). For 3D-texture, depth is ignored, for 1D-texture, height sets to 1.
@anchor{pass_number}
@item pass_number
Sets the active pass index number in a gpu parameter.  The first pass in a technique has an index of 0, the second an index of 1 and so on.  This is usefull for multipass shaders (ie fur or blur shader) that need to know what pass it is.  By setting up the auto parameter in a @ref{Default Program Parameters} list in a program definition, there is no requirement to set the pass number parameter in each pass and lose track. (@xref{fur_example})
@anchor{pass_iteration_number}
@item pass_iteration_number
Usefull for GPU programs that need to know what the current pass iteration number is. The first iteration of a pass is numbered 0.  The last iteration number is one less than what is set for the pass iteration number.  If a pass has its iteration attribute set to 5 then the last iteration number (5th execution of the pass) is 4.(@xref{iteration})
@anchor{animation_parametric}
@item animation_parametric
Useful for hardware vertex animation. For morph animation, sets the parametric value (0..1) representing the distance between the first position keyframe (bound to positions) and the second position keyframe (bound to the first free texture coordinate) so that the vertex program can interpolate between them. For pose animation, indicates a group of up to 4 parametric weight values applying to a sequence of up to 4 poses (each one bound to x, y, z and w of the constant), one for each pose. The original positions are held in the usual position buffer, and the offsets to take those positions to the pose where weight == 1.0 are in the first 'n' free texture coordinates; 'n' being determined by the value passed to includes_pose_animation. If more than 4 simultaneous poses are required, then you'll need more than 1 shader constant to hold the parametric values, in which case you should use this binding more than once, referencing a different constant entry; the second one will contain the parametrics for poses 5-8, the third for poses 9-12, and so on.
@item custom
This allows you to map a custom parameter on an individual Renderable (see Renderable::setCustomParameter) to a parameter on a GPU program. It requires that you complete the 'extra_params' field with the index that was used in the Renderable::setCustomParameter call, and this will ensure that whenever this Renderable is used, it will have it's custom parameter mapped in. It's very important that this parameter has been defined on all Renderables that are assigned the material that contains this automatic mapping, otherwise the process will fail.
@end table

@anchor{param_named}
@subheading param_named
This is the same as param_indexed, but uses a named parameter instead of an index. This can only be used with high-level programs which include parameter names; if you're using an assembler program then you have no choice but to use indexes. Note that you can use indexed parameters for high-level programs too, but it is less portable since if you reorder your parameters in the high-level program the indexes will change.@*@*
format: param_named <name> <type> <value>@*@*
example: param_named shininess float4 10.0 0 0 0@*@*
The type is required because the program is not compiled and loaded when the material script is parsed, so at this stage we have no idea what types the parameters are. Programs are only loaded and compiled when they are used, to save memory.

@anchor{param_named_auto}
@subheading param_named_auto

This is the named equivalent of param_indexed_auto, for use with high-level programs.@*@*
Format: param_named_auto <name> <value_code> <extra_params>@*@*
Example: param_named_auto worldViewProj WORLDVIEWPROJ_MATRIX@*@*

The allowed value codes and the meaning of extra_params are detailed in @ref{param_indexed_auto}.

@anchor{Shadows and Vertex Programs}
@subheading Shadows and Vertex Programs
When using shadows (@xref{Shadows}), 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. @*@*

If you use @strong{stencil shadows}, 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. @*@*

If you use @strong{texture shadows}, 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. Basically you link an alternative vertex program, using exactly the same syntax as the original vertex program link:

@example
shadow_caster_vertex_program_ref myShadowCasterVertexProgram
{
	param_indexed_auto 0 worldviewproj_matrix
	param_indexed_auto 4 ambient_light_colour
}
@end example

When rendering a shadow caster, Ogre will automatically use the alternate program. You can bind the same or different parameters to the program - the most important thing is that you bind @strong{ambiend_light_colour}, since this determines the colour of the shadow in modulative texture shadows. If you don't supply an alternate program, Ogre will fall back on a fixed-function material which will not reflect any vertex deformation you do in your vertex program. @*@*

In addition, when rendering the shadow receivers with shadow textures, Ogre needs to project the shadow texture. It does this automatically in fixed function mode, but if the receivers use vertex programs, they need to have a shadow receiver program which does the usual vertex deformation, but also generates projective texture coordinates. The additional program linked into the pass like this:

@example
shadow_receiver_vertex_program_ref myShadowReceiverVertexProgram
{
	param_indexed_auto 0 worldviewproj_matrix
	param_indexed_auto 4 texture_viewproj_matrix
}
@end example

For the purposes of writing this alternate program, there is an automatic parameter binding of 'texture_viewproj_matrix' which provides the program with texture projection parameters. The vertex program should do it's normal vertex processing, and generate texture coordinates using this matrix and place them in texture coord sets 0 and 1, since some shadow techniques use 2 texture units. The colour of the vertices output by this vertex program must always be white, so as not to affect the final colour of the rendered shadow. @*@*

When using additive texture shadows, the shadow pass render is actually the lighting render, so if you perform any fragmene program lighting you also need to pull in a custom fragment program. You use the shadow_receiver_fragment_program_ref for this:
@example
shadow_receiver_fragment_program_ref myShadowReceiverFragmentProgram
{
	param_named_auto lightDiffuse light_diffuse_colour 0 
}
@end example
You should pass the projected shadow coordinates from the custom vertex program. As for textures, texture unit 0 will always be the shadow texture. Any other textures which you bind in your pass will be carried across too, but will be moved up by 1 unit to make room for the shadow texture. Therefore your shadow receiver fragment program is likely to be the same as the bare lighting pass of your normal material, except that you insert an extra texture sampler at index 0, which you will use to adjust the result by (modulating diffuse and specular components).

@node Vertex Texture Fetch
@subsection Vertex Texture Fetch

@subheading Introduction
More recent generations of video card allow you to perform a read from a texture in the vertex program rather than just the fragment program, as is traditional. This allows you to, for example, read the contents of a texture and displace vertices based on the intensity of the colour contained within.@*@*

@subheading Declaring the use of vertex texture fetching
Since hardware support for vertex texture fetching is not ubiquitous, you should use the uses_vertex_texture_fetch (@xref{Vertex texture fetching in vertex programs}) directive when declaring your vertex programs which use vertex textures, so that if it is not supported, technique fallback can be enabled. This is not strictly necessary for DirectX-targetted shaders, since vertex texture fetching is only supported in vs_3_0, which can be stated as a required syntax in your shader definition, but for OpenGL (GLSL), there are cards which support GLSL but not vertex textures, so you should be explicit about your need for them.

@subheading Render system texture binding differences
Unfortunately the method for binding textures so that they are available to a vertex program is not well standardised. As at the time of writing, Shader Model 3.0 (SM3.0) hardware under DirectX9 include 4 separate sampler bindings for the purposes of vertex textures. OpenGL, on the other hand, is able to access vertex textures in GLSL (and in assembler through NV_vertex_program_3, although this is less popular), but the textures are shared with the fragment pipeline. I expect DirectX to move to the GL model with the advent of DirectX10, since a unified shader architecture implies sharing of texture resources between the two stages. As it is right now though, we're stuck with an inconsistent situation.@*@*

To reflect this, you should use the @ref{binding_type} attribute in a texture unit to indicate which unit you are targetting with your texture - 'fragment' (the default) or 'vertex'. For render systems that don't have separate bindings, this actually does nothing. But for those that do, it will ensure your texture gets bound to the right processing unit.

Note that whilst DirectX9 has separate bindings for the vertex and fragment pipelines, binding a texture to the vertex processing unit still uses up a 'slot' which is then not available for use in the fragment pipeline. I didn't manage to find this documented anywhere, but the nVidia samples certainly avoid binding a texture to the same index on both vertex and fragment units, and when I tried to do it, the texture did not appear correctly in the fragment unit, whilst it did as soon as I moved it into the next unit.

@subheading Texture format limitations
Again as at the time of writing, the types of texture you can use in a vertex program are limited to 1- or 4-component, full precision floating point formats. In code that equates to PF_FLOAT32_R or PF_FLOAT32_RGBA. No other formats are supported. In addition, the textures must be regular 2D textures (no cube or volume maps) and mipmapping and filtering is not supported, although you can perform filtering in your vertex program if you wish by sampling multiple times.

@subheading Hardware limitations
As at the time of writing (early Q3 2006), ATI do not support texture fetch in their current crop of cards (Radeon X1n00). nVidia do support it in both their 6n00 and 7n00 range. ATI support an alternative called 'Render to Vertex Buffer', but this is not standardised at this time and is very much different in its implementation, so cannot be considered to be a drop-in replacement. This is the case even though the Radeon X1n00 cards claim to support vs_3_0 (which requires vertex texture fetch).

@include MaterialScriptCopy.inc

@include CompositorScript.inc

@node Particle Scripts
@section Particle Scripts

Particle scripts allow you to define particle systems to be instantiated in your code without having to hard-code the settings themselves in your source code, allowing a very quick turnaround on any changes you make. Particle systems which are defined in scripts are used as templates, and multiple actual systems can be created from them at runtime.@*@*

@heading Loading scripts

Particle system scripts are loaded at initialisation time by the system: by default it looks in all common resource locations (see Root::addResourceLocation) for files with the '.particle' extension and parses them. If you want to parse files with a different extension, use the ParticleSystemManager::getSingleton().parseAllSources method with your own extension, or if you want to parse an individual file, use ParticleSystemManager::getSingleton().parseScript.@*@*

Once scripts have been parsed, your code is free to instantiate systems based on them using the SceneManager::createParticleSystem() method which can take both a name for the new system, and the name of the template to base it on (this template name is in the script).@*@*

@heading Format

Several particle systems may be defined in a single script. The script format is pseudo-C++, with sections delimited by curly braces ({}), and comments indicated by starting a line with '//' (note, no nested form comments allowed). The general format is shown below in a typical example:
@example
// A sparkly purple fountain
Examples/PurpleFountain
{
    material Examples/Flare2
    particle_width 20
    particle_height 20
    cull_each false
    quota 10000
    billboard_type oriented_self

    // Area emitter
    emitter Point
    {
        angle 15
        emission_rate 75
        time_to_live 3
        direction 0 1 0
        velocity_min 250
        velocity_max 300
        colour_range_start 1 0 0
        colour_range_end 0 0 1
    }

    // Gravity
    affector LinearForce
    {
        force_vector 0 -100 0
        force_application add
    }

    // Fader
    affector ColourFader
    {
        red -0.25
        green -0.25
        blue -0.25
    }
}
@end example
@*@*
Every particle system in the script must be given a name, which is the line before the first opening '{', in the example this is 'Examples/PurpleFountain'. This name must be globally unique. It can include path characters (as in the example) to logically divide up your particle systems, and also to avoid duplicate names, but the engine does not treat the name as hierarchical, just as a string.@*@*

A system can have top-level attributes set using the scripting commands available, such as 'quota' to set the maximum number of particles allowed in the system. Emitters (which create particles) and affectors (which modify particles) are added as nested definitions within the script. The parameters available in the emitter and affector sections are entirely dependent on the type of emitter / affector.@*@*

For a detailed description of the core particle system attributes, see the list below:

@subheading Available Particle System Attributes
@itemize @bullet
@item
@ref{quota}
@item
@ref{particle_material, material}
@item
@ref{particle_width}
@item
@ref{particle_height}
@item
@ref{cull_each}
@item
@ref{billboard_type}
@item
@ref{billboard_origin}
@item
@ref{billboard_rotation_type}
@item
@ref{common_direction}
@item
@ref{common_up_vector}
@item
@ref{particle_renderer, renderer}
@item
@ref{particle_sorted, sorted}
@item
@ref{particle_localspace, local_space}
@item
@ref{particle_point_rendering, point_rendering}
@item
@ref{particle_accurate_facing, accurate_facing}
@item 
@ref{iteration_interval}
@item 
@ref{nonvisible_update_timeout}
@end itemize
See also: @ref{Particle Emitters}, @ref{Particle Affectors}

@node Particle System Attributes
@subsection Particle System Attributes
This section describes to attributes which you can set on every particle system using scripts. All atributes have default values so all settings are optional in your script.@*@*

@anchor{quota}
@subheading quota

Sets the maximum number of particles this system is allowed to contain at one time. When this limit is exhausted, the emitters will not be allowed to emit any more particles until some destroyed (e.g. through their time_to_live running out). Note that you will almost always want to change this, since it defaults to a very low value (particle pools are only ever increased in size, never decreased).@*@*

format: quota <max_particles>@*
example: quota 10000@*
default: 10@*

@anchor{particle_material}
@subheading material

Sets the name of the material which all particles in this system will use. All paticles in a system use the same material, although each particle can tint this material through the use of it's colour property.@*@*

format: material <material_name>@*
example: material Examples/Flare@*
default: none (blank material)@*

@anchor{particle_width}
@subheading particle_width

Sets the width of particles in world coordinates. Note that this property is absolute when billboard_type (see below) is set to 'point' or 'perpendicular_self', but is scaled by the length of the direction vector when billboard_type is 'oriented_common', 'oriented_self' or 'perpendicular_common'.@*

format: particle_width <width>@*
example: particle_width 20@*
default: 100@*

@anchor{particle_height}
@subheading particle_height

Sets the height of particles in world coordinates. Note that this property is absolute when billboard_type (see below) is set to 'point' or 'perpendicular_self', but is scaled by the length of the direction vector when billboard_type is 'oriented_common', 'oriented_self' or 'perpendicular_common'.@*

format: particle_height <height>@*
example: particle_height 20@*
default: 100@*

@anchor{cull_each}
@subheading cull_each

All particle systems are culled by the bounding box which contains all the particles in the system. This is normally sufficient for fairly locally constrained particle systems where most particles are either visible or not visible together. However, for those that spread particles over a wider area (e.g. a rain system), you may want to actually cull each particle individually to save on time, since it is far more likely that only a subset of the particles will be visible. You do this by setting the cull_each parameter to true.@*@*

format: cull_each <true|false>@*
example: cull_each true@*
default: false@*

@anchor{particle_renderer}
@subheading renderer

Particle systems do not render themselves, they do it through ParticleRenderer classes. Those classes are registered with a manager in order to provide particle systems with a particular 'look'. OGRE comes configured with a default billboard-based renderer, but more can be added through plugins. Particle renders are registered with a unique name, and you can use that name in this attribute to determine the renderer to use. The default is 'billboard'.@*@*

Particle renderers can have attributes, which can be passed by setting them on the root particle system.@*@*

format: renderer <renderer_name>@*
default: billboard@*

@anchor{particle_sorted}
@subheading sorted

By default, particles are not sorted. By setting this attribute to 'true', theparticles will be sorted with respect to the camera, furthest first. This can make certain rendering effects look better at a small sorting expense.@*@*

format: sorted <true|false>@*
default: false@*

@anchor{particle_localspace}
@subheading local_space

By default, particles are emitted into world space, such that if you transform the node to which the system is attached, it will not affect the particles (only the emitters). This tends to give the normal expected behaviour, which is to model how real world particles travel independently from the objects they are emitted from. However, to create some effects you may want the particles to remain attached to the local space the emitter is in and to follow them directly. This option allows you to do that.@*@*

format: local_space <true|false>@*
default: false@*

@anchor{billboard_type}
@subheading billboard_type

This is actually an attribute of the 'billboard' particle renderer (the default), and is an example of passing attributes to a particle renderer by declaring them directly within the system declaration. Particles using the default renderer are rendered using billboards, which are rectangles formed by 2 triangles which rotate to face the given direction. However, there is more than 1 way to orient a billboard. The classic approach is for the billboard to directly face the camera: this is the default behaviour. However this arrangement only looks good for particles which are representing something vaguely spherical like a light flare. For more linear effectd like laser fire, you actually want the particle to have an orientation of it's own.@*@*

format: billboard_type <point|oriented_common|oriented_self|perpendicular_common|perpendicular_self>@*
example: billboard_type oriented_self@*
default: point@*

The options for this parameter are:
@table @asis
@item point
	The default arrangement, this approximates spherical particles and the billboards always fully face the camera.
@item oriented_common
	Particles are oriented around a common, typically fixed direction vector (see @ref{common_direction}), which acts as their local Y axis. The billboard rotates only around this axis, giving the particle some sense of direction. Good for rainstorms, starfields etc where the particles will travelling in one direction - this is slightly faster than oriented_self (see below).
@item oriented_self
	Particles are oriented around their own direction vector, which acts as their local Y axis. As the particle changes direction, so the billboard reorients itself to face this way. Good for laser fire, fireworks and other 'streaky' particles that should look like they are travelling in their own direction.
@item perpendicular_common
	Particles are perpendicular to a common, typically fixed direction vector (see @ref{common_direction}), which acts as their local Z axis, and their local Y axis coplanar with common direction and the common up vector (see @ref{common_up_vector}). The billboard never rotates to face the camera, you might use double-side material to ensure particles never culled by back-facing. Good for aureolas, rings etc where the particles will perpendicular to the ground - this is slightly faster than perpendicular_self (see below).
@item perpendicular_self
	Particles are perpendicular to their own direction vector, which acts as their local Z axis, and their local Y axis coplanar with their own direction vector and the common up vector (see @ref{common_up_vector}). The billboard never rotates to face the camera, you might use double-side material to ensure particles never culled by back-facing. Good for rings stack etc where the particles will perpendicular to their travelling direction.
@end table

@anchor{billboard_origin}
@subheading billboard_origin

Specifying the point which acts as the origin point for all billboard particles, controls the fine tuning of where a billboard particle appears in relation to it's position.@*@*

format: billboard_origin <top_left|top_center|top_right|center_left|center|center_right|bottom_left|bottom_center|bottom_right>@*
example: billboard_origin top_right@*
default: center@*

The options for this parameter are:
@table @asis
@item top_left
	The billboard origin is the top-left corner.
@item top_center
	The billboard origin is the center of top edge.
@item top_right
	The billboard origin is the top-right corner.
@item center_left
	The billboard origin is the center of left edge.
@item center
	The billboard origin is the center.
@item center_right
	The billboard origin is the center of right edge.
@item bottom_left
	The billboard origin is the bottom-left corner.
@item bottom_center
	The billboard origin is the center of bottom edge.
@item bottom_right
	The billboard origin is the bottom-right corner.
@end table

@anchor{billboard_rotation_type}
@subheading billboard_rotation_type

By default, billboard particles will rotate the texture coordinates to according with particle rotation. But rotate texture coordinates has some disadvantage, e.g. the corners of the texture will lost after rotate, and the corners of the billboard will fill with unwant texture area when using wrap address mode or sub-texture sampling. This settings allow you specifying other rotation type.@*@*

format: billboard_rotation_type <vertex|texcoord>@*
example: billboard_rotation_type vertex@*
default: texcoord@*

The options for this parameter are:
@table @asis
@item vertex
	Billboard particles will rotate the vertices around their facing direction to according with particle rotation. Rotate vertices guarantee texture corners exactly match billboard corners, thus has advantage mentioned above, but should take more time to generate the vertices.
@item texcoord
	Billboard particles will rotate the texture coordinates to according with particle rotation. Rotate texture coordinates is faster than rotate vertices, but has some disadvantage mentioned above.
@end table

@anchor{common_direction}
@subheading common_direction

Only required if @ref{billboard_type} is set to oriented_common or perpendicular_common, this vector is the common direction vector used to orient all particles in the system.@*@*

format: common_direction <x> <y> <z>@*
example: common_direction 0 -1 0@*
default: 0 0 1@*
@*@*
See also: @ref{Particle Emitters}, @ref{Particle Affectors}

@anchor{common_up_vector}
@subheading common_up_vector

Only required if @ref{billboard_type} is set to perpendicular_self or perpendicular_common, this vector is the common up vector used to orient all particles in the system.@*@*

format: common_up_vector <x> <y> <z>@*
example: common_up_vector 0 1 0@*
default: 0 1 0@*
@*@*
See also: @ref{Particle Emitters}, @ref{Particle Affectors}

@anchor{particle_point_rendering}
@subheading point_rendering

This is actually an attribute of the 'billboard' particle renderer (the default), and sets whether or not the billboardset will use point rendering rather than manually generated quads.@*@*

By default a billboardset is rendered by generating geometry for a textured quad in memory, taking into account the size and orientation settings, and uploading it to the video card. The alternative is to use hardware point rendering, which means that	only one position needs to be sent per billboard rather than 4 and	the hardware sorts out how this is rendered based on the render	state.@*@*

Using point rendering is faster than generating quads manually, but	is more restrictive. The following restrictions apply:
@itemize @bullet
@item Only the 'point' orientation type is supported
@item Size and appearance of each particle is controlled by the material pass (@ref{point_size}, @ref{point_size_attenuation}, @ref{point_sprites})
@item Per-particle size is not supported (stems from the above)
@item Per-particle rotation is not supported, and this can only be controlled through texture unit rotation in the material definition
@item Only 'center' origin is supported
@item Some drivers have an upper limit on the size of points they support - this can even vary between APIs on the same card! Don't rely on point sizes that cause the point sprites to get very large on screen, since they may get clamped on some cards. Upper sizes can range from 64 to 256 pixels.
@end itemize
You will almost certainly want to enable in your material pass both point attenuation and point sprites if you use this option. @*@*


@anchor{particle_accurate_facing}
@subheading accurate_facing

This is actually an attribute of the 'billboard' particle renderer (the default), and sets whether or not the billboardset will use a slower but more accurate calculation for facing the billboard to the camera. Bt default it uses the camera direction, which is faster but means the billboards don't stay in the same orientation as you rotate the camera. The 'accurate_facing true' option makes the calculation based on a vector from each billboard to the camera, which means the orientation is constant even whilst the camera rotates. @*@*

format: accurate_facing on|off@*
default: accurate_facing off 0@*
@*@*


@anchor{iteration_interval}
@subheading iteration_interval
Usually particle systems are updated based on the frame rate; however this can give variable results with more extreme frame rate ranges, particularly at lower frame rates. You can use this option to make the update frequency a fixed interval, whereby at lower frame rates, the particle update will be repeated at the fixed interval until the frame time is used up. A value of 0 means the default frame time iteration. @*@*

format: iteration_interval <secs>@*
example: iteration_interval 0.01@*
default: iteration_interval 0@*
@*@*

@anchor{nonvisible_update_timeout}
@subheading nonvisible_update_timeout
Sets when the particle system should stop updating after it hasn't been visible for a while. By default, visible particle systems update all the time, even when not in view. This means that they are guaranteed to be consistent when they do enter view. However, this comes at a cost, updating particle systems can be expensive, especially if they are perpetual. 
@*@*
This option lets you set a 'timeout' on the particle system, so that if it isn't visible for this amount of time, it will stop updating	until it is next visible. A value of 0 disables the timeout and always updates.@*@*

format: nonvisible_update_timeout <secs>@*
example: nonvisible_update_timeout 10@*
default: nonvisible_update_timeout 0@*
@*@*

@node Particle Emitters
@subsection Particle Emitters
Particle emitters are classified by 'type' e.g. 'Point' emitters emit from a single point whilst 'Box' emitters emit randomly from an area. New emitters can be added to Ogre by creating plugins. You add an emitter to a system by nesting another section within it, headed with the keyword 'emitter' followed by the name of the type of emitter (case sensitive). Ogre currently supports 'Point', 'Box', 'Cylinder', 'Ellipsoid', 'HollowEllipsoid' and 'Ring' emitters.@*@*

It is also possible to 'emit emitters' - that is, have new emitters spawned based on the position of particles. @xref{Emitting Emitters}

@subheading Particle Emitter Universal Attributes
@itemize @bullet
@item
@ref{angle}
@item
@ref{colour}
@item
@ref{colour_range_start}
@item
@ref{colour_range_end}
@item
@ref{direction}
@item
@ref{emission_rate}
@item
@ref{position}
@item
@ref{velocity}
@item
@ref{velocity_min}
@item
@ref{velocity_max}
@item
@ref{time_to_live}
@item
@ref{time_to_live_min}
@item
@ref{time_to_live_max}
@item
@ref{duration}
@item
@ref{duration_min}
@item
@ref{duration_max}
@item
@ref{repeat_delay}
@item
@ref{repeat_delay_min}
@item
@ref{repeat_delay_max}
@end itemize
@*@*
See also: @ref{Particle Scripts}, @ref{Particle Affectors}


@node Particle Emitter Attributes
@subsection Particle Emitter Attributes
This section describes the common attributes of all particle emitters. Specific emitter types may also support their own extra attributes.@*@*

@anchor{angle}
@subheading angle

Sets the maximum angle (in degrees) which emitted particles may deviate from the direction of the emitter (see direction). Setting this to 10 allows particles to deviate up to 10 degrees in any direction away from the emitter's direction. A value of 180 means emit in any direction, whilst 0 means emit always exactly in the direction of the emitter.@*@*

format: angle <degrees>@*
example: angle 30@*
default: 0@*

@anchor{colour}
@subheading colour

Sets a static colour for all particle emitted. Also see the colour_range_start and colour_range_end attributes for setting a range of colours. The format of the colour parameter is "r g b a", where each component is a value from 0 to 1, and the alpha value is optional (assumes 1 if not specified).@*@*

format: colour <r> <g> <b> [<a>]@*
example: colour 1 0 0 1@*
default: 1 1 1 1@*

@anchor{colour_range_start} @anchor{colour_range_end}
@subheading colour_range_start & colour_range_end

As the 'colour' attribute, except these 2 attributes must be specified together, and indicate the range of colours available to emitted particles. The actual colour will be randomly chosen between these 2 values.@*@*

format: as colour@*
example (generates random colours between red and blue):@*
@ @ @ @ colour_range_start 1 0 0@*
@ @ @ @ colour_range_end 0 0 1@*
default: both 1 1 1 1@*

@anchor{direction}
@subheading direction

Sets the direction of the emitter. This is relative to the SceneNode which the particle system is attached to, meaning that as with other movable objects changing the orientation of the node will also move the emitter.@*@*

format: direction <x> <y> <z>@*
example: direction 0 1 0@*
default: 1 0 0@*

@anchor{emission_rate}
@subheading emission_rate

Sets how many particles per second should be emitted. The specific emitter does not have to emit these in a continuous burst - this is a relative parameter
and the emitter may choose to emit all of the second's worth of particles every half-second for example, the behaviour depends on the emitter. The emission rate will also be limited by the particle system's 'quota' setting.@*@*

format: emission_rate <particles_per_second>@*
example: emission_rate 50@*
default: 10@*

@anchor{position}
@subheading position

Sets the position of the emitter relative to the SceneNode the particle system is attached to.@*@*

format: position <x> <y> <z>@*
example: position 10 0 40@*
default: 0 0 0@*

@anchor{velocity}
@subheading velocity

Sets a constant velocity for all particles at emission time. See also the velocity_min and velocity_max attributes which allow you to set a range of velocities instead of a fixed one.@*@*

format: velocity <world_units_per_second>@*
example: velocity 100@*
default: 1@*

@anchor{velocity_min} @anchor{velocity_max}
@subheading velocity_min & velocity_max

As 'velocity' except these attributes set a velocity range and each particle is emitted with a random velocity within this range.@*@*

format: as velocity@*
example:@*
@ @ @ @ velocity_min 50@*
@ @ @ @ velocity_max 100@*
default: both 1@*

@anchor{time_to_live}
@subheading time_to_live

Sets the number of seconds each particle will 'live' for before being destroyed. NB it is possible for particle affectors to alter this in flight, but this is the value given to particles on emission. See also the time_to_live_min and time_to_live_max attributes which let you set a lifetime range instead of a fixed one.@*@*

format: time_to_live <seconds>@*
example: time_to_live 10@*
default: 5@*

@anchor{time_to_live_min} @anchor{time_to_live_max}
@subheading time_to_live_min & time_to_live_max
As time_to_live, except this sets a range of lifetimes and each particle gets a random value inbetween on emission.@*@*

format: as time_to_live@*
example:@*
@ @ @ @ time_to_live_min 2@*
@ @ @ @ time_to_live_max 5@*
default: both 5@*
@*

@anchor{duration}
@subheading duration

Sets the number of seconds the emitter is active. The emitter can be started again, see @ref{repeat_delay}. A value of 0 means infinite duration. See also the duration_min and duration_max attributes which let you set a duration range instead of a fixed one.@*@*

format: duration <seconds>@*
example:@*
@ @ @ @ duration 2.5@*
default: 0@*
@*

@anchor{duration_min} @anchor{duration_max}
@subheading duration_min & duration_max

As duration, except these attributes set a variable time range between the min and max values each time the emitter is started.@*@*

format: as duration@*
example:@*
@ @ @ @ duration_min 2@*
@ @ @ @ duration_max 5@*
default: both 0@*
@*

@anchor{repeat_delay}
@subheading repeat_delay

Sets the number of seconds to wait before the emission is repeated when stopped by a limited @ref{duration}. See also the repeat_delay_min and repeat_delay_max attributes which allow you to set a range of repeat_delays instead of a fixed one.@*@*

format: repeat_delay <seconds>@*
example:@*
@ @ @ @ repeat_delay 2.5@*
default: 0@*
@*

@anchor{repeat_delay_min} @anchor{repeat_delay_max}
@subheading repeat_delay_min & repeat_delay_max

As repeat_delay, except this sets a range of repeat delays and each time the emitter is started it gets a random value inbetween.@*@*

format: as repeat_delay@*
example:@*
@ @ @ @ repeat_delay 2@*
@ @ @ @ repeat_delay 5@*
default: both 0@*
@*

See also: @ref{Standard Particle Emitters}, @ref{Particle Scripts}, @ref{Particle Affectors}


@node Standard Particle Emitters 
@subsection Standard Particle Emitters 
Ogre comes preconfigured with a few particle emitters. New ones can be added by creating plugins: see the Plugin_ParticleFX project as an example of how you would do this (this is where these emitters are implemented).

@itemize @bullet
@item
@ref{Point Emitter}
@item
@ref{Box Emitter}
@item
@ref{Cylinder Emitter}
@item
@ref{Ellipsoid Emitter}
@item
@ref{Hollow Ellipsoid Emitter}
@item
@ref{Ring Emitter}
@end itemize
@*@*
@anchor{Point Emitter}
@subheading Point Emitter

This emitter emits particles from a single point, which is it's position. This emitter has no additional attributes over an above the standard emitter attributes.@*@*

To create a point emitter, include a section like this within your particle system script:
@example

emitter Point
{
    // Settings go here
}
@end example
@*
Please note that the name of the emitter ('Point') is case-sensitive.

@anchor{Box Emitter}
@subheading Box Emitter

This emitter emits particles from a random location within a 3-dimensional box. It's extra attributes are:@*@*
@table @asis
@item width
Sets the width of the box (this is the size of the box along it's local X axis, which is dependent on the 'direction' attribute which forms the box's local Z).@*
format: width <units>@*
example: width 250@*
default: 100@*
@item height
Sets the height of the box (this is the size of the box along it's local Y axis, which is dependent on the 'direction' attribute which forms the box's local Z).@*
format: height <units>@*
example: height 250@*
default: 100@*
@item depth
Sets the depth of the box (this is the size of the box along it's local Z axis, which is the same as the 'direction' attribute).@*
format: depth <units>@*
example: depth 250@*
default: 100@*
@end table
@*
To create a box emitter, include a section like this within your particle system script:
@example
emitter Box
{
    // Settings go here
}
@end example

@anchor{Cylinder Emitter}
@subheading Cylinder Emitter

This emitter emits particles in a random direction from within a cylinder area, where the cylinder is oriented along the Z-axis. This emitter has exactly the same parameters as the @ref{Box Emitter} so there are no additional parameters to consider here - the width and height determine the shape of the cylinder along it's axis (if they are different it is an ellipsoid cylinder), the depth determines the length of the cylinder. 

@anchor{Ellipsoid Emitter}
@subheading Ellipsoid Emitter
This emitter emits particles from within an ellipsoid shaped area, ie a sphere or squashed-sphere area. The parameters are again identical to the @ref{Box Emitter}, except that the dimensions describe the widest points along each of the axes.

@anchor{Hollow Ellipsoid Emitter}
@subheading Hollow Ellipsoid Emitter
This emitter is just like @ref{Ellipsoid Emitter} except that there is a hollow area in the centre of the ellipsoid from which no particles are emitted. Therefore it has 3 extra parameters in order to define this area:

@table @asis
@item inner_width
The width of the inner area which does not emit any particles.
@item inner_height
The height of the inner area which does not emit any particles.
@item inner_depth 
The depth of the inner area which does not emit any particles.
@end table

@anchor{Ring Emitter}
@subheading Ring Emitter
This emitter emits particles from a ring-shaped area, ie a little like @ref{Hollow Ellipsoid Emitter} except only in 2 dimensions.

@table @asis
@item inner_width
The width of the inner area which does not emit any particles.
@item inner_height
The height of the inner area which does not emit any particles.
@end table
@*@*

See also: @ref{Particle Scripts}, @ref{Particle Emitters}

@subheading Emitting Emitters
@anchor{Emitting Emitters}

It is possible to spawn new emitters on the expiry of particles, for example to product 'firework' style effects. This is controlled via the following directives:

@table @asis
@item emit_emitter_quota
This parameter is a system-level parameter telling the system how many emitted emitters may be in use at any one time. This is just to allow for the space allocation process.
@item name
This parameter is an emitter-level parameter, giving a name to an emitter. This can then be referred to in another emitter as the new emitter type to spawn when an emitted particle dies.
@item emit_emitter
This is an emitter-level parameter, and if specified, it means that when particles emitted by this emitter die, they spawn a new emitter of the named type.
@end table


@node Particle Affectors
@subsection Particle Affectors

Particle affectors modify particles over their lifetime. They are classified by 'type' e.g. 'LinearForce' affectors apply a force to all particles, whilst 'ColourFader' affectors alter the colour of particles in flight. New affectors can be added to Ogre by creating plugins. You add an affector to a system by nesting another section within it, headed with the keyword 'affector' followed by the name of the type of affector (case sensitive). Ogre currently supports 'LinearForce' and 'ColourFader' affectors.@*@*

Particle affectors actually have no universal attributes; they are all specific to the type of affector.@*@*

See also: @ref{Standard Particle Affectors}, @ref{Particle Scripts}, @ref{Particle Emitters}

@node Standard Particle Affectors
@subsection Standard Particle Affectors
Ogre comes preconfigured with a few particle affectors. New ones can be added by creating plugins: see the Plugin_ParticleFX project as an example of how you would do this (this is where these affectors are implemented).

@itemize @bullet
@item 
@ref{Linear Force Affector}
@item 
@ref{ColourFader Affector}
@item
@ref{ColourFader2 Affector}
@item
@ref{Scaler Affector}
@item
@ref{Rotator Affector}
@item
@ref{ColourInterpolator Affector}
@item
@ref{ColourImage Affector}
@item
@ref{DeflectorPlane Affector}
@item
@ref{DirectionRandomiser Affector}
@end itemize

@anchor{Linear Force Affector}
@subheading Linear Force Affector

This affector applies a force vector to all particles to modify their trajectory. Can be used for gravity, wind, or any other linear force. It's extra attributes are:@*@*
@table @asis
@item force_vector
Sets the vector for the force to be applied to every particle. The magnitude of this vector determines how strong the force is.@*
@ @ @ @ format: force_vector <x> <y> <z>@*
@ @ @ @ example: force_vector 50 0 -50@*
@ @ @ @ default: 0 -100 0 (a fair gravity effect)@*
@item force_application

Sets the way in which the force vector is applied to particle momentum.@*
@ @ @ @ format: force_application <add|average>@*
@ @ @ @ example: force_application average@*
@ @ @ @ default: add@*
The options are:
@table @asis
@item average
	The resulting momentum is the average of the force vector and the particle's current motion. Is self-stabilising but the speed at which the particle changes direction is non-linear.
@item add
	The resulting momentum is the particle's current motion plus the force vector. This is traditional force acceleration but can potentially result in unlimited velocity.
@end table
@end table
@*
To create a linear force affector, include a section like this within your particle system script:
@example
affector LinearForce
{
    // Settings go here
}
@end example
Please note that the name of the affector type ('LinearForce') is case-sensitive.

@anchor{ColourFader Affector}
@subheading ColourFader Affector

This affector modifies the colour of particles in flight. It's extra attributes are:
@table @asis
@item red
Sets the adjustment to be made to the red component of the particle colour per second.@*
@ @ @ @ format: red <delta_value>@*
@ @ @ @ example: red -0.1@*
@ @ @ @ default: 0@*
@item green
Sets the adjustment to be made to the green component of the particle colour per second.@*
@ @ @ @ format: green <delta_value>@*
@ @ @ @ example: green -0.1@*
@ @ @ @ default: 0@*
@item blue
Sets the adjustment to be made to the blue component of the particle colour per second.@*
@ @ @ @ format: blue <delta_value>@*
@ @ @ @ example: blue -0.1@*
@ @ @ @ default: 0@*
@item alpha
Sets the adjustment to be made to the alpha component of the particle colour per second.@*
@ @ @ @ format: alpha <delta_value>@*
example: alpha -0.1@*
default: 0@*
@end table
To create a colour fader affector, include a section like this within your particle system script:
@example
affector ColourFader
{
    // Settings go here
}
@end example

@anchor{ColourFader2 Affector}
@subheading ColourFader2 Affector

This affector is similar to the @ref{ColourFader Affector}, except it introduces two states of colour changes as opposed to just one. The second colour change state is activated once a specified amount of time remains in the particles life.
@table @asis
@item red1
Sets the adjustment to be made to the red component of the particle colour per second for the first state.@*
@ @ @ @ format: red <delta_value>@*
@ @ @ @ example: red -0.1@*
@ @ @ @ default: 0@*
@item green1
Sets the adjustment to be made to the green component of the particle colour per second for the first state.@*
@ @ @ @ format: green <delta_value>@*
@ @ @ @ example: green -0.1@*
@ @ @ @ default: 0@*
@item blue1
Sets the adjustment to be made to the blue component of the particle colour per second for the first state.@*
@ @ @ @ format: blue <delta_value>@*
@ @ @ @ example: blue -0.1@*
@ @ @ @ default: 0@*
@item alpha1
Sets the adjustment to be made to the alpha component of the particle colour per second for the first state.@*
@ @ @ @ format: alpha <delta_value>@*
example: alpha -0.1@*
default: 0@*
@item red2
Sets the adjustment to be made to the red component of the particle colour per second for the second state.@*
@ @ @ @ format: red <delta_value>@*
@ @ @ @ example: red -0.1@*
@ @ @ @ default: 0@*
@item green2
Sets the adjustment to be made to the green component of the particle colour per second for the second state.@*
@ @ @ @ format: green <delta_value>@*
@ @ @ @ example: green -0.1@*
@ @ @ @ default: 0@*
@item blue2
Sets the adjustment to be made to the blue component of the particle colour per second for the second state.@*
@ @ @ @ format: blue <delta_value>@*
@ @ @ @ example: blue -0.1@*
@ @ @ @ default: 0@*
@item alpha2
Sets the adjustment to be made to the alpha component of the particle colour per second for the second state.@*
@ @ @ @ format: alpha <delta_value>@*
example: alpha -0.1@*
default: 0@*
@item state_change
When a particle has this much time left to live, it will switch to state 2.@*
@ @ @ @ format: state_change <seconds>@*
example: state_change 2@*
default: 1@*
@end table
To create a ColourFader2 affector, include a section like this within your particle system script:
@example
affector ColourFader2
{
    // Settings go here
}
@end example

@anchor{Scaler Affector}
@subheading Scaler Affector

This affector scales particles in flight. It's extra attributes are:
@table @asis
@item rate
The amount by which to scale the particles in both the x and y direction per second.
@end table
To create a scale affector, include a section like this within your particle system script:
@example
affector Scaler
{
    // Settings go here
}
@end example

@anchor{Rotator Affector}
@subheading Rotator Affector

This affector rotates particles in flight. This is done by rotating the texture. It's extra attributes are:
@table @asis
@item rotation_speed_range_start
The start of a range of rotation speeds to be assigned to emitted particles.@*
@ @ @ @ format: rotation_speed_range_start <degrees_per_second>@*
example: rotation_speed_range_start 90@*
default: 0@*
@item rotation_speed_range_end
The end of a range of rotation speeds to be assigned to emitted particles.@*
@ @ @ @ format: rotation_speed_range_end <degrees_per_second>@*
example: rotation_speed_range_end 180@*
default: 0@*
@item rotation_range_start
The start of a range of rotation angles to be assigned to emitted particles.@*
@ @ @ @ format: rotation_range_start <degrees>@*
example: rotation_range_start 0@*
default: 0@*
@item rotation_range_end
The end of a range of rotation angles to be assigned to emitted particles.@*
@ @ @ @ format: rotation_range_end <degrees>@*
example: rotation_range_end 360@*
default: 0@*
@end table
To create a rotate affector, include a section like this within your particle system script:
@example
affector Rotator
{
    // Settings go here
}
@end example

@anchor{ColourInterpolator Affector}
@subheading ColourInterpolator Affector

Similar to the ColourFader and ColourFader2 Affector?s, this affector modifies the colour of particles in flight, except it has a variable number of defined stages. It swaps the particle colour for several stages in the life of a particle and interpolates between them. It's extra attributes are:
@table @asis
@item time0
The point in time of stage 0.@*
@ @ @ @ format: time0 <0-1 based on lifetime>@*
example: time0 0@*
default: 1@*
@item colour0
The colour at stage 0.@*
@ @ @ @ format: colour0 <r> <g> <b> [<a>]@*
example: colour0 1 0 0 1@*
default: 0.5 0.5 0.5 0.0@*
@item time1
The point in time of stage 1.@*
@ @ @ @ format: time1 <0-1 based on lifetime>@*
example: time1 0.5@*
default: 1@*
@item colour1
The colour at stage 1.@*
@ @ @ @ format: colour1 <r> <g> <b> [<a>]@*
example: colour1 0 1 0 1@*
default: 0.5 0.5 0.5 0.0@*
@item time2
The point in time of stage 2.@*
@ @ @ @ format: time2 <0-1 based on lifetime>@*
example: time2 1@*
default: 1@*
@item colour2
The colour at stage 2.@*
@ @ @ @ format: colour2 <r> <g> <b> [<a>]@*
example: colour2 0 0 1 1@*
default: 0.5 0.5 0.5 0.0@*
@item [...]
@end table
The number of stages is variable. The maximal number of stages is 6; where time5 and colour5 are the last possible parameters.
To create a colour interpolation affector, include a section like this within your particle system script:
@example
affector ColourInterpolator
{
    // Settings go here
}
@end example

@anchor{ColourImage Affector}
@subheading ColourImage Affector

This is another affector that modifies the colour of particles in flight, but instead of programmatically defining colours, the colours are taken from a specified image file. The range of colour values begins from the left side of the image and move to the right over the lifetime of the particle, therefore only the horizontal dimension of the image is used. Its extra attributes are:
@table @asis
@item image
The start of a range of rotation speed to be assigned to emitted particles.@*
@ @ @ @ format: image <image_name>@*
example: image rainbow.png@*
default: none@*
@end table
To create a ColourImage affector, include a section like this within your particle system script:
@example
affector ColourImage
{
    // Settings go here
}
@end example


@anchor{DeflectorPlane Affector}
@subheading DeflectorPlane Affector
This affector defines a plane which deflects particles which collide with it. The attributes are:
@table @asis
@item plane_point
A point on the deflector plane. Together with the normal vector it defines the plane.@*
default: plane_point 0 0 0@*
@item plane_normal
The normal vector of the deflector plane. Together with the point it defines the plane.@*
default: plane_normal 0 1 0@*
@item bounce
The amount of bouncing when a particle is deflected. 0 means no deflection and 1 stands for 100 percent reflection.@*
default: bounce 1.0
@end table


@anchor{DirectionRandomiser Affector}
@subheading DirectionRandomiser Affector
This affector applies randomness to the movement of the particles. Its extra attributes are:
@table @asis
@item randomness
The amount of randomness to introduce in each axial direction.@*
example: randomness 5@*
default: randomness 1@*
@item scope
The percentage of particles affected in each run of the affector.@*
example: scope 0.5@*
default: scope 1.0@*
@item keep_velocity
Determines whether the velocity of particles is unchanged.@*
example: keep_velocity true@*
default: keep_velocity false@*
@end table

@node Overlay Scripts
@section Overlay Scripts

Overlay scripts offer you the ability to define overlays in a script which can be reused easily. Whilst you could set up all overlays for a scene in code using the methods of the SceneManager, Overlay and OverlayElement classes, in practice it's a bit unwieldy. Instead you can store overlay definitions in text files which can then be loaded whenever required.@*@*

@heading Loading scripts

Overlay scripts are loaded at initialisation time by the system: by default it looks in all common resource locations (see Root::addResourceLocation) for files with the '.overlay' extension and parses them. If you want to parse files with a different extension, use the OverlayManager::getSingleton().parseAllSources method with your own extension, or if you want to parse an individual file, use OverlayManager::getSingleton().parseScript.@*@*

@heading Format

Several overlays may be defined in a single script. The script format is pseudo-C++, with sections delimited by curly braces ({}), comments indicated by starting a line with '//' (note, no nested form comments allowed), and inheritance through the use of templates. The general format is shown below in a typical example:
@example
// The name of the overlay comes first
MyOverlays/ANewOverlay
{
    zorder 200

    container Panel(MyOverlayElements/TestPanel)
    {
        // Center it horzontally, put it at the top
        left 0.25
        top 0
        width 0.5
        height 0.1
        material MyMaterials/APanelMaterial

        // Another panel nested in this one
        container Panel(MyOverlayElements/AnotherPanel)
        {
             left 0
             top 0
             width 0.1
             height 0.1
             material MyMaterials/NestedPanel
        }
    }

}
@end example

The above example defines a single overlay called 'MyOverlays/ANewOverlay', with 2 panels in it, one nested under the other. It uses relative metrics (the default if no metrics_mode option is found).@*@*

Every overlay in the script must be given a name, which is the line before the first opening '{'. This name must be globally unique. It can include path characters (as in the example) to logically divide up your overlays, and also to avoid duplicate names, but the engine does not treat the name a hierarchical, just as a string. Within the braces are the properties of the overlay, and any nested elements. The overlay itself only has a single property 'zorder' which determines how'high' it is in the stack of overlays if more than one is displayed at the same time. Overlays with higher zorder values are displayed on top.@*@*

@heading Adding elements to the overlay

Within an overlay, you can include any number of 2D or 3D elements. You do this by defining a nested block headed by:
@table @asis
@item 'element' 
if you want to define a 2D element which cannot have children of it's own
@item 'container'
if you want to define a 2D container object (which may itself have nested containers or elements)
@end table
@*
The element and container blocks are pretty identical apart from their ability to store nested blocks.

@heading 'container' / 'element' blocks

These are delimited by curly braces. The format for the header preceding the first brace is:@*@*

[container | element] <type_name> ( <instance_name>) [: <template_name>]@*
{ ...@*@*
@table @asis
@item type_name
Must resolve to the name of a OverlayElement type which has been registered with the OverlayManager. Plugins register with the OverlayManager to advertise their ability to create elements, and at this time advertise the name of the type. OGRE comes preconfigured with types 'Panel', 'BorderPanel' and 'TextArea'.
@item instance_name
Must be a name unique among all other elements / containers by which to identify the element. Note that you can obtain a pointer to any named element by calling OverlayManager::getSingleton().getOverlayElement(name).
@item template_name
Optional template on which to base this item. See templates.
@end table

The properties which can be included within the braces depend on the custom type. However the following are always valid:
@itemize @bullet
@item 
@ref{metrics_mode}
@item 
@ref{horz_align}
@item 
@ref{vert_align}
@item 
@ref{left}
@item 
@ref{top}
@item 
@ref{width}
@item 
@ref{height}
@item 
@ref{overlay_material, material}
@item
@ref{caption}
@end itemize


@heading Templates

You can use templates to create numerous elements with the same properties. A template is an abstract element and it is not added to an overlay. It acts as a base class that elements can inherit and get its default properties. To create a template, the keyword 'template' must be the first word in the element definition (before container or element). The template element is created in the topmost scope - it is NOT specified in an Overlay. It is recommended that you define templates in a separate overlay though this is not essential. Having templates defined in a separate file will allow different look & feels to be easily substituted.@*@*

Elements can inherit a template in a similar way to C++ inheritance - by using the : operator on the element definition. The : operator is placed after the closing bracket of the name (separated by a space). The name of the template to inherit is then placed after the : operator (also separated by a space).@*@*

A template can contain template children which are created when the template is subclassed and instantiated. Using the template keyword for the children of a template is optional but recommended for clarity, as the children of a template are always going to be templates themselves.@*@*
@example
template container BorderPanel(MyTemplates/BasicBorderPanel)
{
    left 0
    top 0
    width 1
    height 1

// setup the texture UVs for a borderpanel

// do this in a template so it doesn't need to be redone everywhere
    material Core/StatsBlockCenter
    border_size 0.05 0.05 0.06665 0.06665
    border_material Core/StatsBlockBorder
    border_topleft_uv 0.0000 1.0000 0.1914 0.7969
    border_top_uv 0.1914 1.0000 0.8086 0.7969
    border_topright_uv 0.8086 1.0000 1.0000 0.7969
    border_left_uv 0.0000 0.7969 0.1914 0.2148
    border_right_uv 0.8086 0.7969 1.0000 0.2148
    border_bottomleft_uv 0.0000 0.2148 0.1914 0.0000
    border_bottom_uv 0.1914 0.2148 0.8086 0.0000
    border_bottomright_uv 0.8086 0.2148 1.0000 0.0000
}
template container Button(MyTemplates/BasicButton) : MyTemplates/BasicBorderPanel
{
    left 0.82
    top 0.45
    width 0.16
    height 0.13
    material Core/StatsBlockCenter
    border_up_material Core/StatsBlockBorder/Up
    border_down_material Core/StatsBlockBorder/Down
}
template element TextArea(MyTemplates/BasicText)
{
    font_name Ogre
    char_height 0.08
    colour_top 1 1 0
    colour_bottom 1 0.2 0.2
    left 0.03
    top 0.02
    width 0.12
    height 0.09
}

MyOverlays/AnotherOverlay
{
    zorder 490
    container BorderPanel(MyElements/BackPanel) : MyTemplates/BasicBorderPanel
    {
        left 0
        top 0
        width 1
        height 1

        container Button(MyElements/HostButton) : MyTemplates/BasicButton
        {
            left 0.82
            top 0.45
            caption MyTemplates/BasicText HOST
        }

        container Button(MyElements/JoinButton) : MyTemplates/BasicButton
        {
            left 0.82
            top 0.60
            caption MyTemplates/BasicText JOIN
        }
    }
}
@end example
The above example uses templates to define a button. Note that the button template inherits from the borderPanel template. This reduces the number of attributes needed to instantiate a button.@*@*

Also note that the instantiate of a Button needs a template name for the caption attribute. So templates can also be used by elements that need dynamic creation of children elements (the button creates a TextAreaElement in this case for its caption).@*@*

@xref{OverlayElement Attributes}, @ref{Standard OverlayElements}

@node OverlayElement Attributes
@subsection OverlayElement Attributes

These attributes are valid within the braces of a 'container' or 'element' block in an overlay script. They must each be on their own line. Ordering is unimportant.@*@*

@anchor{metrics_mode}
@subheading metrics_mode

Sets the units which will be used to size and position this element.@*@*

Format: metrics_mode <pixels|relative>@*
Example: metrics_mode pixels@*

This can be used to change the way that all measurement attributes in the rest of this element are interpreted. In relative mode, they are interpreted as being a parametric value from 0 to 1, as a proportion of the width / height of the screen. In pixels mode, they are simply pixel offsets.@*@*

Default: metrics_mode relative@*

@anchor{horz_align}
@subheading horz_align

Sets the horizontal alignment of this element, in terms of where the horizontal origin is.@*@*

Format: horz_align <left|center|right>@*
Example: horz_align center@*@*

This can be used to change where the origin is deemed to be for the purposes of any horizontal positioning attributes of this element. By default the origin is deemed to be the left edge of the screen, but if you change this you can center or right-align your elements. Note that setting the alignment to center or right does not automatically force your elements to appear in the center or the right edge, you just have to treat that point as the origin and adjust your coordinates appropriately. This is more flexible because you can choose to position your element anywhere relative to that origin. For example, if your element was 10 pixels wide, you would use a 'left' property of -10 to align it exactly to the right edge, or -20 to leave a gap but still make it stick to the right edge.@*@*

Note that you can use this property in both relative and pixel modes, but it is most useful in pixel mode.@*@*

Default: horz_align left@*

@anchor{vert_align}
@subheading vert_align

Sets the vertical alignment of this element, in terms of where the vertical origin is.@*@*

Format: vert_align <top|center|bottom>@*
Example: vert_align center@*@*

This can be used to change where the origin is deemed to be for the purposes of any vertical positioning attributes of this element. By default the origin is deemed to be the top edge of the screen, but if you change this you can center or bottom-align your elements. Note that setting the alignment to center or bottom does not automatically force your elements to appear in the center or the bottom edge, you just have to treat that point as the origin and adjust your coordinates appropriately. This is more flexible because you can choose to position your element anywhere relative to that origin. For example, if your element was 50 pixels high, you would use a 'top' property of -50 to align it exactly to the bottom edge, or -70 to leave a gap but still make it stick to the bottom edge.@*@*

Note that you can use this property in both relative and pixel modes, but it is most useful in pixel mode.@*@*

Default: vert_align top@*

@anchor{left}
@subheading left

Sets the horizontal position of the element relative to it's parent.@*@*

Format: left <value>@*
Example: left 0.5@*@*

Positions are relative to the parent (the top-left of the screen if the parent is an overlay, the top-left of the parent otherwise) and are expressed in terms of a proportion of screen size. Therefore 0.5 is half-way across the screen.@*@*

Default: left 0@*

@anchor{top}
@subheading top

Sets the vertical position of the element relative to it's parent.@*@*

Format: top <value>@*
Example: top 0.5@*@*

Positions are relative to the parent (the top-left of the screen if the parent is an overlay, the top-left of the parent otherwise) and are expressed in terms of a proportion of screen size. Therefore 0.5 is half-way down the screen.@*@*

Default: top 0@*

@anchor{width}
@subheading width

Sets the width of the element as a proportion of the size of the screen.@*@*

Format: width <value>@*
Example: width 0.25@*@*

Sizes are relative to the size of the screen, so 0.25 is a quarter of the screen. Sizes are not relative to the parent; this is common in windowing systems where the top and left are relative but the size is absolute.@*@*

Default: width 1@*

@anchor{height}
@subheading height

Sets the height of the element as a proportion of the size of the screen.@*@*

Format: height <value>@*
Example: height 0.25@*@*

Sizes are relative to the size of the screen, so 0.25 is a quarter of the screen. Sizes are not relative to the parent; this is common in windowing systems where the top and left are relative but the size is absolute.@*@*

Default: height 1@*

@anchor{overlay_material}
@subheading material

Sets the name of the material to use for this element.@*@*

Format: material <name>@*
Example: material Examples/TestMaterial@*@*

This sets the base material which this element will use. Each type of element may interpret this differently; for example the OGRE element 'Panel' treats this as the background of the panel, whilst 'BorderPanel' interprets this as the material for the center area only. Materials should be defined in .material scripts.@*@*
Note that using a material in an overlay element automatically disables lighting and depth checking on this material. Therefore you should not use the same material as is used for real 3D objects for an overlay.@*@*

Default: none@*

@anchor{caption}
@subheading caption

Sets a text caption for the element.@*@*

Format: caption <string>@*
Example: caption This is a caption@*@*

Not all elements support captions, so each element is free to disregard this if it wants. However, a general text caption is so common to many elements that it is included in the generic interface to make it simpler to use. This is a common feature in GUI systems.@*@*

Default: blank@*


@anchor{rotation}
@subheading rotation

Sets the rotation of the element.@*@*

Format: rotation <angle_in_degrees> <axis_x> <axis_y> <axis_z>
Example: rotation 30 0 0 1

Default: none 

@node Standard OverlayElements
@subsection Standard OverlayElements

Although OGRE's OverlayElement and OverlayContainer classes are designed to be extended by applications developers, there are a few elements which come as standard with Ogre. These include:
@itemize @bullet
@item
@ref{Panel}
@item 
@ref{BorderPanel}
@item
@ref{TextArea}
@end itemize
@*
This section describes how you define their custom attributes in an .overlay script, but you can also change these custom properties in code if you wish. You do this by calling setParameter(paramname, value). You may wish to use the StringConverter class to convert your types to and from strings.

@anchor{Panel}
@subheading Panel (container)

This is the most bog-standard container you can use. It is a rectangular area which can contain other elements (or containers) and may or may not have a background, which can be tiled however you like. The background material is determined by the material attribute, but is only displayed if transparency is off.@*@*

Attributes:
@table @asis
@item transparent <true | false>
If set to 'true' the panel is transparent and is not rendered itself, it is just used as a grouping level for it's children.
@item tiling <layer> <x_tile> <y_tile>
Sets the number of times the texture(s) of the material are tiled across the panel in the x and y direction. <layer> is the texture layer, from 0 to the number of texture layers in the material minus one. By setting tiling per layer you can create some nice multitextured backdrops for your panels, this works especially well when you animate one of the layers.
@item uv_coords <topleft_u> <topleft_v> <bottomright_u> <bottomright_v>
Sets the texture coordinates to use for this panel.
@end table

@anchor{BorderPanel}
@subheading BorderPanel (container)

This is a slightly more advanced version of Panel, where instead of just a single flat panel, the panel has a separate border which resizes with the panel. It does this by taking an approach very similar to the use of HTML tables for bordered content: the panel is rendered as 9 square areas, with the center area being rendered with the main material (as with Panel) and the outer 8 areas (the 4 corners and the 4 edges) rendered with a separate border material. The advantage of rendering the corners separately from the edges is that the edge textures can be designed so that they can be stretched without distorting them, meaning the single texture can serve any size panel.@*@*

Attributes:
@table @asis
@item border_size <left> <right> <top> <bottom>
The size of the border at each edge, as a proportion of the size of the screen. This lets you have different size borders at each edge if you like, or you can use the same value 4 times to create a constant size border.
@item border_material <name>
The name of the material to use for the border. This is normally a different material to the one used for the center area, because the center area is often tiled which means you can't put border areas in there. You must put all the images you need for all the corners and the sides into a single texture.
@item border_topleft_uv <u1> <v1> <u2> <v2>
[also border_topright_uv, border_bottomleft_uv, border_bottomright_uv]; 
The texture coordinates to be used for the corner areas of the border. 4 coordinates are required, 2 for the top-left corner of the square, 2 for the bottom-right of the square. 
@item border_left_uv <u1> <v1> <u2> <v2>
[also border_right_uv, border_top_uv, border_bottom_uv];
The texture coordinates to be used for the edge areas of the border. 4 coordinates are required, 2 for the top-left corner, 2 for the bottom-right. Note that you should design the texture so that the left & right edges can be stretched / squashed vertically and the top and bottom edges can be stretched / squashed horizontally without detrimental effects.
@end table


@anchor{TextArea}
@subheading TextArea (element)

This is a generic element that you can use to render text. It uses fonts which can be defined in code using the FontManager and Font classes, or which have been predefined in .fontdef files. See the font definitions section for more information.@*@*

Attributes:
@table @asis
@item font_name <name>
The name of the font to use. This font must be defined in a .fontdef file to ensure it is available at scripting time.
@item char_height <height>
The height of the letters as a proportion of the screen height. Character widths may vary because OGRE supports proportional fonts, but will be based on this constant height. 
@item colour <red> <green> <blue>
A solid colour to render the text in. Often fonts are defined in monochrome, so this allows you to colour them in nicely and use the same texture for multiple different coloured text areas. The colour elements should all be expressed as values between 0 and 1. If you use predrawn fonts which are already full colour then you don't need this.
@item colour_bottom <red> <green> <blue> / colour_top <red> <green> <blue>
As an alternative to a solid colour, you can colour the text differently at the top and bottom to create a gradient colour effect which can be very effective.
@item alignment <left | center | right>
Sets the horizontal alignment of the text. This is different from the horz_align parameter.
@item space_width <width>
Sets the width of a space in relation to the screen.
@end table

@node Font Definition Scripts
@section Font Definition Scripts

Ogre uses texture-based fonts to render the TextAreaOverlayElement. You can also use the Font object for your own purpose if you wish. The final form of a font is a Material object generated by the font, and a set of 'glyph' (character) texture coordinate information.@*@*

There are 2 ways you can get a font into OGRE:
@enumerate
@item Design a font texture yourself using an art package or font generator tool
@item Ask OGRE to generate a font texture based on a truetype font
@end enumerate

The former gives you the most flexibility and the best performance (in terms of startup times), but the latter is convenient if you want to quickly use a font without having to generate the texture yourself. I suggest prototyping using the latter and change to the former for your final solution.@*@*

All font definitions are held in .fontdef files, which are parsed by the system at startup time. Each .fontdef file can contain multiple font definitions. The basic fomat of an entry in the .fontdef file is:
@example
<font_name>
{
    type <image | truetype>
    source <image file | truetype font file>
    ...
    ... custom attributes depending on type
}
@end example

@heading Using an existing font texture

If you have one or more artists working with you, no doubt they can produce you a very nice font texture. OGRE supports full colour font textures, or alternatively you can keep them monochrome / greyscale and use TextArea's colouring feature. Font textures should always have an alpha channel, preferably an 8-bit alpha channel such as that supported by TGA and PNG files, because it can result in much nicer edges. To use an existing texture, here are the settings you need:
@table @asis
@item type image
This just tells OGRE you want a pre-drawn font.
@item source <filename>
This is the name of the image file you want to load. This will be loaded from the standard TextureManager resource locations and can be of any type OGRE supports, although JPEG is not recommended because of the lack of alpha and the lossy compression. I recommend PNG format which has both good lossless compression and an 8-bit alpha channel.
@item glyph <character> <u1> <v1> <u2> <v2>
This provides the texture coordinates for the specified character. You must repeat this for every character you have in the texture. The first 2 numbers are the x and y of the top-left corner, the second two are the x and y of the bottom-right corner. Note that you really should use a common height for all characters, but widths can vary because of proportional fonts.@*@*

'character' is either an ASCII character for non-extended 7-bit ASCII, or for extended glyphs, a unicode decimal value, which is identified by preceding the number with a 'u' - e.g. 'u0546' denotes unicode value 546. 
@end table

A note for Windows users: I recommend using BitmapFontBuilder (@url{http://www.lmnopc.com/bitmapfontbuilder/}), a free tool which will generate a texture and export character widths for you, you can find a tool for converting the binary output from this into 'glyph' lines in the Tools folder.@*

@heading Generating a font texture

You can also generate font textures on the fly using truetype fonts. I don't recommend heavy use of this in production work because rendering the texture can take a several seconds per font which adds to the loading times. However it is a very nice way of quickly getting text output in a font of your choice.@*@*

Here are the attributes you need to supply:
@table @asis
@item type truetype
Tells OGRE to generate the texture from a font
@item source <ttf file>
The name of the ttf file to load. This will be searched for in the common resource locations and in any resource locations added to FontManager.
@item size <size_in_points>
The size at which to generate the font, in standard points. Note this only affects how big the characters are in the font texture, not how big they are on the screen. You should tailor this depending on how large you expect to render the fonts because generating a large texture will result in blurry characters when they are scaled very small (because of the mipmapping), and conversely generating a small font will result in blocky characters if large text is rendered.
@item resolution <dpi>
The resolution in dots per inch, this is used in conjunction with the point size to determine the final size. 72 / 96 dpi is normal.
@item antialias_colour <true|false>
This is an optional flag, which defaults to 'false'. The generator will antialias the font by default using the alpha component of the texture, which will look fine if you use alpha blending to render your text (this is the default assumed by TextAreaOverlayElement for example). If, however you wish to use a colour based blend like add or modulate in your own code, you should set this to 'true' so the colour values are anitaliased too. If you set this to true and use alpha blending, you'll find the edges of your font are antialiased too quickly resulting in a 'thin' look to your fonts, because not only is the alpha blending the edges, the colour is fading too. Leave this option at the default if in doubt.
@item code_points nn-nn [nn-nn] ..
This directive allows you to specify which unicode code points should be generated as glyphs into the font texture. If you don't specify this, code points 33-166 will be generatedby default which covers the basic Latin 1 glyphs. If you use this flag, you should specify a space-separated list of inclusive code point ranges of the form 'start-end'. Numbers must be decimal.
@end table
@*@*
You can also create new fonts at runtime by using the FontManager if you wish.

@node Mesh Tools
@chapter Mesh Tools
There are a number of mesh tools available with OGRE to help you manipulate your meshes.
@table @asis
@item @ref{Exporters}
For getting data out of modellers and into OGRE.
@item @ref{XmlConverter}
For converting meshes and skeletons to/from XML.
@item @ref{MeshUpgrader}
For upgrading binary meshes from one version of OGRE to another.
@end table

@node Exporters
@section Exporters

Exporters are plugins to 3D modelling tools which write meshes and skeletal animation to file formats which OGRE can use for realtime rendering. The files the exporters write end in .mesh and .skeleton respectively.@*@*

Each exporter has to be written specifically for the modeller in question, although they all use a common set of facilities provided by the classes MeshSerializer and SkeletonSerializer. They also normally require you to own the modelling tool.@*@*

All the exporters here can be built from the source code, or you can download precompiled versions from the OGRE web site.@*@*

@heading A Note About Modelling / Animation For OGRE
There are a few rules when creating an animated model for OGRE:
@itemize @bullet
@item You must have no more than 4 weighted bone assignments per vertex. If you have more, OGRE will eliminate the lowest weighted assignments and renormalise the other weights. This limit is imposed by hardware blending limitations.
@item All vertices must be assigned to at least one bone - assign static vertices to the root bone.
@item At the very least each bone must have a keyframe at the beginning and end of the animation.
@end itemize
If you're creating unanimated meshes, then you do not need to be concerned with the above.

Full documentation for each exporter is provided along with the exporter itself, and there is a list of the currently supported modelling tools in the OGRE Wiki at @url{http://www.ogre3d.org/wiki/index.php/Exporters}.

@node XmlConverter
@section XmlConverter

The OgreXmlConverter tool can converter binary .mesh and .skeleton files to XML and back again - this is a very useful tool for debugging the contents of meshes, or for exchanging mesh data easily - many of the modeller mesh exporters export to XML because it is simpler to do, and OgreXmlConverter can then produce a binary from it. Other than simplicity, the other advantage is that OgreXmlConverter can generate additional information for the mesh, like bounding regions and level-of-detail reduction. @*@*

Syntax:
@example
Usage: OgreXMLConverter sourcefile [destfile]
sourcefile = name of file to convert
destfile   = optional name of file to write to. If you don't
             specify this OGRE works it out through the extension
             and the XML contents if the source is XML. For example
             test.mesh becomes test.xml, test.xml becomes test.mesh
             if the XML document root is <mesh> etc.
@end example
When converting XML to .mesh, you will be prompted to (re)generate level-of-detail(LOD) information for the mesh - you can choose to skip this part if you wish, but doing it will allow you to make your mesh reduce in detail automatically when it is loaded into the engine. The engine uses a complex algorithm to determine the best parts of the mesh to reduce in detail depending on many factors such as the curvature of the surface, the edges of the mesh and seams at the edges of textures and smoothing groups - taking advantage of it is advised to make your meshes more scalable in real scenes.

@node MeshUpgrader
@section MeshUpgrader
This tool is provided to allow you to upgrade your meshes when the binary format changes - sometimes we alter it to add new features and as such you need to keep your own assets up to date. This tools has a very simple syntax:
@example
OgreMeshUpgrade <oldmesh> <newmesh>
@end example
The OGRE release notes will notify you when this is necessary with a new release.

@include vbos.inc
@include texturesource.inc
@include shadows.inc
@include animation.inc

@bye

