https://www.anim8or.com/learn/specs/an8_format.txt File: an8_format.txt Date: 21-Sep-03 Format of Anim8or .an8 Files - V0.85 ------------------------------------ This document describes the .an8 file format used by Anim8or to save project data between sessions. Overview: --------- A .an8 file is stored as a text file and can be viewed and edited by a simple text editor such at Notepad. Files are free format much like those used by popular programming languages like C. At the text level they are similarly composed of scanner tokens such as identifiers, numbers, strings and punctutation. Tokens are organized into nested "chunks" that contain specific data used by each specific chunk. Chunks share a common format so that a parser can easily skip over unrecognized or unneeded data. The .an8 format is designed to be both forward and backward compatible to a large degree largely due to chunks. Tokens: ------- The basic tokens use by the .an8 format are: <$ident> - identifiers similar to those used by C. They may begin with letters and the under score character "_" and may contain letters, digits, and underscores. Case is important so a capital "A" is different from a lower case "a". No spaces may appear within an . <$int> - integer constants. One or more digits "0" though "9", A basic <$int> does not include a sign. <$float> - floating point constants. The usual C style floating point numbers are allowed. Again a <$float> cannot contain a leading sign. <$string> - string constants. C style strings beginning and ending with a double quote ". Internal spaces are allowed. The backslash character "\" is used to escape special characters such as a double quote " so they may be use in a string. For example the string: "He said, \"What do you want?\"" would have the value: He said, "What are you want?" Similarly back slashes are escaped by a backslash. "{" and "}" - braces. Used to enclose the body of a chuck. These never appear anywhere else in a .an8 file (except within a string) and are used as the basic parsing tokens. "+" and "-" - plus and minus. Used in signed numeric values. "(", ")", ",", etc. - delimiters. Various special characters are used as delimiters through out. Chunk Format: ------------- The basic format of a chunk is an identifier, followed by an open brace, the body of the chunk, and a closing brace: <$ident> "{" "}" The format of the body depends on which chunk it is in. It may contain a fixed amount of data, a variable amount, more chunks, or be empty. Examples of a chunk are: size { 12 } color { 0.5, 0.75, 0.33333 } closed {} texture { "checks" blend { 1 } } File Layout: ------------ An .an8 file is one or more chunks. Any specific chunk is optional, and the chunks aren't required to be in any specific order. However it's advisable to include the
chunk, and to put it first, to help the Anim8or parser deal with any incompatibles that are introduced between different versions. The order of the top level chunks is:
- Contains version number and related data. - String with user's description of the file. - Frame rate and ground grid settings. * - Description of texture files used. * - Global materials. * - Objects.
* - Figures. * - Sequences. * - Scenes. In the syntax descriptions below, items with an asterisk "*" after them may be appear any number of times, including none. Those with a plus "+" must appear once but can be repeated. Tokens within square brackets "[" and "]" are optional. Finally things within angle brackets "<" and ">" are described by other syntax rules. Headers: ========
::= header { } ::= version { <$string> } The version string has the form "." such as "0.85". It can have additional information at the end as well such as "0.85beta" ::= build { <$string> } The build string is used to identify the build number of the Anim8or executable that created the .an8 file. Description: ============ ::= description { <$string>* } Normally description strings represent a single line of text and are terminated with a : "This is my alien model.\0d\0a" Anim8or truncates descriptions to 4096 characters when reading them. Environment: ============ ::= environment { } ::= grid { } Specifies the modeling grid's behavior. If the first int is non-zero then auto-grid is enabled and the grid size is automatically determined by the view. If it's zero then the three following values set the modeling grid spacing, the Scene editor's grid spacing, and the ground floor's grid size. An of the later values may be omitted and a default value will be used. ::= framerate { } Sets the Scene and Sequence playback frame rate. Ignored unless the chunk also appears. ::= limitplayback { } Limits the playback frame rate to the value in , or to a default value if no chunk is present. Texture: ======== ::= texture { +6 } Define a texture name and bind it to an image file or files. The string is the name used within Anim8or for this texture. is an optional empty chunk. If present then the image(s) for this texture are inverted top to bottem before they are used. is an optional empty chunk. It indicates that this texture is a cube map. The chunks contain a single string for the name of the files that hold the texture image. Only one chunk is used for normal textures and six chunks are used for cube map textures. Material: ========== ::= material { } The name of the material is given by and the front and back surfaces are described by the other chunks. Single sided materials don't have the chunk while two sided materials do. ::= surface { ... ... * ... ... } , , and chunks describe the respective colors and constant weights, and if there is a corresponding texture what it is. Yes, I know is misspelled. is a int-const chunk that sets the overall transparency of the material. 255 is opaque and 0 is completely transparent. Values are clamped to this range. is a float chunk that sets the brilliance factor. is a float chunk that sets the phong roughness factor. * is one of multiple chunks that describe a texture map used for things other than the four colors: ambient, diffuse, specular, and emissive. Currently supported uses are for transparency, bump map, and environment map. is an empty chunk that, if present, uses the diffuse values for both the diffuse and ambient color properties. ::= backsurface { ... same values as surface chunk ... } ::= ambiant { } is the basc color. is a float chunk with the ambient weighting factor. is a string containing the name of the texture used in the diffuse color. This is not the file name but the internal name. describe how the texture is blended with the base color. ::= diffuse { ---- same as ---- } ::= diffuse { ---- same as ---- } ::= diffuse { ---- same as ---- } ::= rgb { <$int> <$int> <$int> } Three integer values representing the red, green and blue components of a color. They are clamped to 0 to 255, then scaled so to the range 0.0 to 1.0 representing the darkest and brightest values. ::= textureparams { } and specifies how that a texture will be combined with the base color. holds a single signed integer pecentage that is used to blend the overall strength of the texture. If it is 100 then the combined result is used as the final color. If it is 50 percent then the combined color is averaged with the base color. For bumpmaps is the strength of the bumps and can go from -100 to 100 perxent. ::= blendmode { [ decal darken lighten ] } The blendmode chunk hold a single identifier from the list above. darken means that the texture's color is multiplied by the base color, decal means that the texture color replaces the base color, and lighten adds the texture color. ::= { [ none layer final ] } The alphamode chuck also holds a single identifier. None means that the alpha component is ignored, layer blends the texture color with the base color proportional to the value of the alpha component, and final uses the texture's alpha component as the transparency value for the final material color. Note: alphamode only applies to the diffuse color and is overridden by the transparency texture if it is present. ::= map { } The chunk defines a texture image usage that is used for things other than a simple color, such as in the ambient, diffuse, specular, or emissive attributes. The chunk says how it will be used. The chunk names which texture it is, and the specify the strength, etc. ::= kind { <$string> } The <$string> parameter can be "transparency", "bumpmap" or "environment", or it can be one of the four color textures "ambiant", "diffuse", "specular", and "emissive". Other values are ignored. If a color texture is specified in both a color component such as the chunk and in a component the last one in the file will be used. Object: ======== ::= object { * * } The object's name is given by . chunks in an chunk are local to that object and cannot be used in other objects. There can be any number of and chunks in any order. Normally the chunks are output first by Anim8or. ::= [ ... ... ... ... ] A is any one of the listed chunk types. All types of chunks have a string as the first value. They also may have both a and a chunk. components can only appear inside of a chunk as part of a
. ::= base { [ ] [ ] } A chunk can have either an , an , or both. This chunk gives the location and orientation of the component relative to it's parent. If the component is in a group then the group is it's parent, otherwise it is the Object. ::= pivot { [ ] [ ] } The chunk specifies the location and orientation of the pivot, the coordinate system used when you interactively scale and rotate a component in the Object editor. ::= origin { } This chunk represents the location of the component. If not present then the component is located at (0, 0, 0). ::= orientation { } This chunk holds the orientation of the component as a quaternion. If not present the it is unrotated, with the X coordinate pointing to the right, the Y pointing up, and the Z pointing out of the screen in a front view of an object. For a description of the wonders of quaternions, see a good graphics text, or the original paper by Ken Shoemaker. ::= mesh { ... ... ... ... is the material used for new faces when they are added to a mesh. Even though a chunk may contain a full material description, only the name component is used here. The material should be defined elsewhere, either in the global materials of the Object's local materials. := smoothangle { } This is the threshold angle in degrees that determines if an edge is as a crease or is smooth. Angles larger than the threshold are shown as creases or corners; those equal or smaller are shown as smooth. The default value is 45 degrees. ::= materiallist { * } This is a list of material in a Mesh. They are numbered from 0. Material 0 is the default material. ::= materialname { <$string> } The value of <$string> is a material name. It should be defined either as a global material or as a material local to this Object. ::= { * } These points are the basic vertices used to form the Mesh. They are numbered from 0. ::= { * } The normals are stored as unit length vectors. This chunk is not usually present and is ignored by Anim8or. It will be output if the Options->Debug->OutputNormals flag has been set for use by other applications. ::= { * } A list of edges. Edges are not normally output by Anim8or as this information is already present in the chunk. When an edge either 1) isn't used in any face, or 2) has some special properties set by the user, it will be listed here. Optionally, all edges can be output with the Options->Debug->OutputEdges flag. ::= ( <$int> <$int> [ ] ) The first two values in an edge are indices into the points array for the ends of the edge. The index of the first point is always less than that of the second. The third value, if present, is the user set sharpness value. If this Mesh is subdivided then this edge will not be smoothed with the adjacent edges for this number of times, creating a relative sharp corner in the surface. If the value is -1 then it is always shown as Creased despite the actual angle is makes. ::= texcoords { * } The UV values used for texture coordinates. These are indexed starting at zero. ::= ( ) The values represent the U and V texture coordinates. ::= faces { * } One set of data is listed for each face. ::= NUMPOINTS FLAGS MATNO FLATNORMAL ... ... ( (POINTDATA-1) (POINTDATA-2) ... (POINTDATA-N) ) NUMPOINTS is an giving the number of sides in this face. It must be at least 3. Each face can have a different number of sides. FLAGS is an with each bit as a flag describing what kinds of data this face has, and other properties of the face: 1 - SF_SHOW_BACK - Don't backface cull this face. 2 - SF_HAS_NORMALS - This face has normal data in this file. 4 - SF_HAS_TEXTURE - This face has texture coordinates. MATNO is an for which material to use on this face. It is an index into the materials listed in the chuck for this Mesh. FLATNORMALNO - The index of the faces normal in the normal array for this Mesh. This value is normally set to -1 indicating that there is no face normal stored in the file. POINTDATA - This is one or more s, depending on the value of FLAGS. The first value, which is always present, is an index into the array for the location of the vertex. If the SF_HAS_NORMALS bit is on then it is followed by the index on the point's normal in the array. Note: this normal data is not used by Anim8or. It can optionally be exported, however, to help other programs use Anim8or data more easily. Finally if the SF_HAS_TEXTURE bit is set then a texture coordinate is present as the last value. For example: faces { 3 5 0 -1 ( (2 6) (0 5) (1 7) ) 3 5 2 -1 ( (3 8) (0 5) (2 3) ) 4 5 2 -1 ( (4 9) (5 10) (1 7) (2 6) ) } shows a Mesh with 3 faces. The first two have 3 sides and the third one has 4. They all have texture coordinates (bit 4 is set in the flags field) and no face normals (the face normal value is -1). The first face uses material number 0 and the other two use material number 2. ::= sphere { ... ... } A has either a or a chunk, but not both. ::= longlat { <$int> <$int> } The two integers are the number of divisions used to make the Sphere in the vertical and horizontal directions. ::= geodesic { <$int> } A geodesic sphere is built from a octahedron whose faces are divided into smaller triangles. Each original edge is divide into <$int> edges and the faces are split accordingly into smaller triangles. The vertices are then projected onto a Shpere. ::= cylinder { ... ... ... ... [ ] [ ] } ::= length { <$float> } This is the length of the cylinder, ::= diameter { <$float> } This is the diameter of the start of the cylinder. It is also the diameter of the end if the chunk is not present. If one of thee values is 0 then that end of the cylinder is collapsed into a single point resulting is a Cone. ::= topdiameter { <$float> } The diameter of the end of the cylinder. ::= capstart { } ::= capend { } Cap the start and/or end of the cylinder if these chunks are present. ::= cube { } ::= { <$float> <$float> <$float> } The dimensions of the cube in the X, Y and Z directions. ::= { <$int> <$int> <$int> } The number of divisions along the X, Y and Z axis. ::= subdivision { ... ... ... ... ... ... A chunk is similar to a chunk but has two additional sub-chunks that control how many times it will be subdivided. ::= working { <$int> } The number of times a that this component will be subdivided in the working views. ::= divisions { <$int> } The number of times a that this component will be subdivided in the rendered views. This value is currently not used by Anim8or. ::= path { [ ] * } A is built from one or more Bezier splines. Multiple splines can be used to cut holes or to define separate, unconnected regions. ::= bezier { [ ] * } ::= closed { } If this chunk is present the first and last knots in the spline are connected to form a closed loop. Otherwise they are not. ::= knot { [ <$int> ] [ ] } The first is the location of the knot. The next two are the forward and reverse direction vectors. If present the <$int> value is the number of segments in the segment that begins with this knot. If not then the number is automatically determined when it is used. ::= corner { } If this is present the knot is a corner knot and can have a discontinuous first derivative. If it is not present then the values of the forward and reverse direction vectors should be the negation of each other. ::= textcom { ... [ ] [ ] } A is a True-Type string represented by one or more splines. ::= string { L<$string> } This is a Unicode string. Values outside of the 7 bit printable ASCII character set are escaped by a backslash "\" and are written as either 3 or 6 octal digits representing the value of the Unicode character. Six octal digits are used if either the value is greater than decimal 255 or the following letter is a digit. When reading these strings in the digits following a back slash are read and converted into an octal value until either the next character is not an octal digits or 6 digits have been read. For example, the Euro currency symbol could be represented by: L"\020254" since it has a hexadecimal value of 0x20ac which is the octal value of 020254. Note: Unicode symbols are not supported in Win95, Win98, WinSE or WinME. ::= modifier { ... ... [ ] } A chunk defines the size, location and kind of a modifier and any that it is bound to. ::= segments { <$int> } The number of vertical segments that the modifier is divided into. ::= method { <$string> * } The kind of modifier. <$string> names the modifier function and the define how it behaves. For example a taper modifier with a strength of 0.5 would look like: method { modifier "taper" parameter { "taper" 0.5 } } since it has a single parameter. ::= parameter { <$string> <$float> } A named parameter to a modifier. <$string> is the name of the parameter and <$float> is its value. ::= image { <$string> } A reference image. The <$string> value is the name of the file with the image, or an empty string if it is undefined. ::= size { <$int> <$int> } The int values are the size of the image in x and y dimensions. ::= namedobject { <$string> ... ... * } A is a reference to an from within another part of Anim8or, such as a
. is the default material for this object but is currently ignored by Anim8or. s can only appear inside a definition. ::= weightedby { <$string> } This object's shape is determined partially by the bone <$string>'s position in this figure. ::= group { * } A is a collection of zero of more . Figure: =======
::= figure { <$string> * } A figure. <$string> is the name of the figure and is the root bone, which contains all other bones. Any defined materials are local to this figure. ::= bone { <$string> [ ] [ ] ... ... [ ] * [ ] ... ... * * } is the length of the bone. is the relative diameter of the bone when it is shown in the working views. ::= locked { } If this chunk is present then the bone joint cannot be edited. ::= dof { <$string> ... ... [ ] [ ] } This chunk defines a degree of freedom for this done. There can be up to 3 instances of this chunk is a bone. The value of <$string> is the axis and must be "X", "Y", or "Z". The three s are the minimum, default, and maximum angles that this angle may take on. If the chunk is present then this axis of rotation cannot be edited. If the chunk is present then there are no limits to this axis's rotation angle. ::= unlimited { } ::= influence { ... ... } If this chunk is present then the bone has a defined influence region and may be used in skinning. The size floating point values are: center0 - The location along the bone of the center of the lower end of the influence volume. inRadius0 - The radius of the inner layer at center0. outRadius0 - The radius of the outer layer at center0. center1 - The location along the bone of the center of the uppper end of the influence volume. inRadius1 - The radius of the inner layer at center1. outRadius1 - The radius of the outer layer at center1. These six values defines two hierarchical "capsules", or a cylinders with hemispherical caps on the ends. When used in a skinning operation the relative weight of this bone on a point depends on where the point lies inside these capsules. If it is inside the inner capsule the relative weight is 1.0. If it is inside the outer capsule but not the inner one then the relative weight varies linearly between 0.0 at the outer capsule wall to 1.0 at the inner capsule wall. Outside the outer capsule the weight is 0.0. The final weight on a point is found by dividing the relative weight by the sum of all the relative weights for all bones. If this sum is 0.0 then a default weight of 1.0 is given to the parent bone of the point. Sequence: ========= ::= sequence { <$string> [ ] ... ... * } The name of the sequence is given by <$string>. ::= figure { <$string> } The name of the figure that this sequence applies to is defined by <$string>. ::= frames { <$int> } This chunk is the length of the sequence in frames. ::= jointangle { <$string> <$string> } The two strings give the names of the bone that it applies to, and the axis. The ais must be "X", "Y", or "Z". Tracks: ------- ::= track { + } ::= floatkey { <$int> <$float> <$string> } <$int> is the frame number for this key. <$float> is the value. <$string> is a string used to modify the behavior of this knot. It is currently ignored. ::= track { + } ::= pointkey { <$int> <$string> } <$int> is the frame number for this key. The first is the value, the second is the forward direction vector and this know, and the third is the reverse direection vector. <$string> is a string used to modify the behavior of this knot. It is currently ignored. ::= track { + } ::= qkey { <$int> <$string> } <$int> is the frame number for this key. is the value. <$string> is a string used to modify the behavior of this knot. It is currently ignored. ::= track { + } ::= booleankey { <$int> <$int> <$string> } The first <$int> is the frame number for this key. The second <$int> is the value. It must be 0 or 1. 0 means False and 1 means True. <$string> is a string used to modify the behavior of this knot. It is currently ignored. Scene: ====== ::= scene { <$string> .. ... [ ] [ ] [ ] ... ... [ ] * } The name of the scene is in <$string>. ::= frames { <$int> } The number of frames. Must be greater than zero. ::= groundgrid { <$int> } If the value of <$int> is one the ground grid is drawn. If it is zero then it isn't. ::= shadowbias { <$float> } The value used for shadow bias when drawing shadows. The nominal value is 0.001. ::= background { <$int> <$int> <$int> } The color used for the background. The three values are the red, green, and blue color values. 255 represents full brightness and 0 represents black. If not present the default color of 102, 102, 153 is used. ::= image { <$string> [ ] } The name of a file used for the background image. If the panorama chunk is present then it is a panoroma, otherwise it is a fixed background. ::= panorama { ... ... } The four values are the left and right longitude angles and the bottom and top latitude angles of the image. Looking into the screen in the front view is directly at <0, 0>. <-90, 0> is to the left, <+90, 0) the right. ::= fog { [ ] [ ] } The chunk is the color of the fog in 3 ints, from 0 to 255. and are float chunks giving the starting and ending distance from the camera of the fog transition zone. is an int chunk for the maximum fog level, if it is less that 100. is an empty chunk. If present then the fog distance is computed as the radial distance from the camera, otherwise it is the distance from the z = 0 plane. ::= znear { <$float-const> ::= zfar { <$float-const> If present, these set the distance of the near and far clip planes. ::= | | | | These form the element of a scene. They share several common subchunks described here: <$string> - The first thing is the name of the element. - A for the element's location. - A chunk for the orientation, normally this is relative to it's parent's orientation. [ ] - An int chunk with a value of 1 if the element's orientation can "roll" off the vertical, and 0 if it can't. [ | | ] - One of these three optional chunks may be present. They control whether the element's orientation is relative to 1) the direction of it's path of motion, 2) the direction to another element, or 3) the same orientation as another element. [ ] - The name of the other element that this one is oriented to, if it has the facestarget or orientedtarget chunk. [ ] - A scale factor applied to the object before rendering. - An int chunk with the value of 1 if this element is "locked" from being edited, and a value of 0 otherwise. * - Zero or more chunks. * - Zero or more child elements, whose movement is relative to this element's coordinate system. ::= camera { <$string> [ ] ... ... [ | | ] ... ... [ ] [ ] ... ... * * } ::= fov { <$float> } The field of view in degrees of the camera's view from left to right. ::= light { <$string> [ ] ... [ | | ] ... ... [ ] [ ] ... ... [ | | ] ... ... [ ] [ ] ... ... [ raytraceshadow> ] [ ] ... ... * * } ::= color { } The three values in represent the red, green and blue components of the light's color. A value of 1.0 is maximum and 0.0 is minimum. ::= infinite { } ::= local { } ::= spotlight { } One of these three empty chunks must be present. They define the kind of light. ::= inradius { <$float> } ::= outradius { <$float> } Spotlights and local lights can have a different intensity depending on the distance from an object. By default the intensity is the same. If these chunks are present then the intensity drops off linearly from full intensity at a distance of to zero at a distance of . ::= inangle { <$float> } ::= outangle { <$float> } Spotlights also have a cone of influence. Within an angle of to the direction of the light the intensity is full value. Between and it drops off linearly to zero. Outside this range it is zero. ::= castshadow { } If present this light casts a shadow. ::= raytraceshadow { } This chunk enables ray tracing of shadows for this light. ::= soft { } If is present and the light casts a ray traced shadow the the shadow is rendered with soft edges. ::= softsize { <$float> } The size of the soft shadow. For infinite lights this is the apparent width of the light source in degrees. For spotlights and local lights it represents the apparent diameter of the light as viewed by an illuminated surface. ::= minsamples { <$int> } ::= maxsamples { <$int> } Set the minimum and maximum number of samples used to calculate a soft shadow. An adaptive algorithm is used to speed up rendering when not in a "soft" region of the shadow. ::= montecarlo { } Use true Monte Carlo sampling instead of pseudo-Monte Carlo sampling. This results in a grainer look in the shadows transition region. ::= objectelement { <$string> <$string> ... ... [ ] ... [ | | ] ... ... [ ] [ ] [ ] ... ... [ ] [ ] ... ... * * } Objects that are in a scene are defined by an chunk. The first <$string> is the name of this element and the second is the name of the object that it references. ::= visibility { <$int> } This chunk has a value of 1 of the element is visible, and a value of zero if it is hidden. The default value is 1. ::= castshadow { } If present this object casts a shadow. ::= receiveshadow { } If present this object shows shadows on its surface from lights that cast them. ::= figureelement { <$string> <$string> ... ... [ ] ... [ | | ] ... ... [ ] [ ] [ ] ... ... [ ] [ ] ... ... * * * } Figures that are in a scene are defined by a chunk. The first <$string> is the name of this element and the second is the name of the figure that it references. ::= namedsequence { <$string> <$int> } This chunk specifies the name and starting frame of a sequence that is applied to this figure. ::= null { <$string> [ ] ... [ | | ] ... ... [ ] [ ] ... ... * * } A chunk, also referred to as a "target" element in Anim8or, defines a new coordinate system. They can contain child elements and their location and orientation is fully animatable. They do not render in camera views. Misc. Items: ------------ ::= [ + - ] <$int> ::= [ + - ] <$float> ::= ::= ( ) A is three possibly signed floating point or integer numbers enclosed in parenthesis. These normally represent a point in space or a direction vector but can also represent a color or any value made from three floating point values. There are no comma separators. ::= ( ) A is four possibly signed floating point or integer constants enclosed in parenthesis. There are no comma separators. Quaternions represent rotations or orientations. They should be normalized (so that the sum of the squares of the four values is equal to 1.0) to insure correct behavior in Anim8or. ::= name { <$string> } A is chunk containing a string. Its value is used as a name within a particular chunk. There is normally no limit to what the string can be. ----- End of File -----