 =============================================================================
             POV-Ray triangle mesh compressor v2.1 by Warp.
 =============================================================================
                                                    Last modified: 11-Dec-1999
                                                 Modifications marked with '+'

CONTENTS:
  1.0 OVERVIEW
  2.0 QUICK START
  3.0 SYNTAX
    3.1 OPTIONS
    3.2 INPUT AND OUTPUT FILES
    3.3 TRANSFORMATIONS
  4.0 EXAMPLES
  5.0 TIPS AND TRICKS
  6.0 COMPILING THE PROGRAM
  7.0 THE PCM FORMAT
  8.0 CONTACTING THE AUTHOR


1.0 OVERVIEW
    =========================================================================

    The triangle mesh compressor is a program which reads POV-Ray script
  files, searches for triangle meshes or bicubic patches and outputs them
  in a much more compact format, which can be read with the POV-Ray
  Compressed Mesh (PCM) macro by Chris Colefax.
    The resulting files are usually much more smaller than the original
  ones (usually about 20-30% of the original size). They are in ascii
  format, so they are fully portable from one platform to another.
    With the PCM macro you can also make things not possible with ordinary
  meshes (like deforming, morphing, hair growing, etc).
    To use the PCM macro, you have to convert the meshes or bicubic patches
  to the PCM format first with this program.

    Various options are available to fine-tune the output, resulting in even
  further compression.  In addition you can transform the mesh to scale,
  rotate, translate, centre, swap coordinate systems, etc.

    The source code is pure ANSI C++ and should be compilable in almost any
  system with a C++ compiler which supports the latest standard.
    Precompiled DOS (djgpp) and Windows9x (BCB4) versions are included.


2.0 QUICK START
    =========================================================================

  - For the command line version:

    To use the default compression settings, simply run the program with the
  name of the POV-Ray file to compress and the name of the compressed mesh
  file to create, eg:

meshcomp MyMesh.inc MyMesh.pcm

    To compress bicubic patches, use the -b flag:

meshcomp -b MyPatch.inc MyPatch.pcm

    If you don't specify an output file, the compressed data is outputted to
  stdout.

  - For the Win9x version:

    Select the desired input and output files in the text fields at the
  top of the window (browsing with the browse button may be the easiest
  way; the program also proposes a default output file name when you set
  an input file name).
    Then select the type of input and output from the "Input file is a" and
  "Output file is a" sections if they are different from the default values.
    Then just hit the "Go" button.

    The text area at the bottom of the window should simulate what happens
  if you were using the command line version.


3.0 SYNTAX
    =========================================================================

    The following parts describe mainly the command line version of the
  program. The description of options and transformations is applicable
  to both versions.

    If you start the program without parameters, you will see a short
  version of this help.
    The syntax of the program is the following:

  meshcomp [<options>] <infile> [<outfile>] [<transformations>]

    The different command line parameters are explained below.


3.1 OPTIONS
    =======

    All the options must be placed before the input and output file names
  and the transformations.

  -b    : Input is a Bicubic Patch instead of a triangle mesh

    By default, the program searches for triangle meshes (which are inside
  the "mesh { ... }" block of the POV-Ray language). With this option you
  can tell the program to search for bicubic patches instead.

  -c    : Assume that input file is a PCM file instead of a POV-Ray file

    By default, the program assumes that the input file is a POV-Ray file.
  With this option you can tell the program to read a PCM file instead. If
  you specify this option, the option -b is obsolete, since the program
  will automatically detect the content type of the PCM file.
    This option is useful if you only have the PCM version of the mesh and
  you want to apply transformations to it or output it in POV-Ray format
  (see the option -p).

+ -x    : Use extra compression

+   This option will have effect only if the input is a triangle mesh and
+ the output format is PCM. It will make the program to calculate and output
+ a special format of the PCM which is more compressed than the default one
+ (see the 'Whatsnew.txt' file for examples). Reading the extra compressed
+ mesh with the PCM macros should not be noticeably slower.
+   Note: The extra compression calculations may take quite long with huge
+ meshes (more than about 50000 triangles).

  -y    : Overwrite destination file without confirmation

    If the destination file exists, the program asks before overwriting
  it. You can stop the program from asking with this flag. This flag is
  needed with the -i flag if the destination file exists.

  -i    : Read from stdin instead of <infile> (assume <infile>=stdin).

    By default the program expects to find the input file name in the
  command line. You can make the program to read from the standard input
  instead with this flag. If the destination file exists, you have to use
  the -y flag to overwrite it (this is because the program can't read
  both the input file and the user input from stdin).
    NOTE: If you use this flag, it must be the last option (before the
  output file name and transformations). When the program finds this
  option, it stops parsing more options and begins searching for the
  output file name and transformations. This is necessary because there
  are some transformations which have the same names as some options
  (for example -c).

  -p    : Output ordinary POV-Ray file instead of PCM file

    This option will tell the program to output the mesh or bicubic patches
  in POV-Ray format.
    You can convert a PCM file to a POV-Ray file using both -p and -c
  options.

  -p2   : Output in uv-pov mesh2 format (only if input is a mesh)

    This is similar to -p but it will output in the mesh2 format of UV-Pov.

  -r[n] : Round float values to the nth decimal. If n is not specified,
          the default value of 5 is used

    If you specify this flag, the program will round all float values. This
  is often handy when no big accuracy is needed. Rounding with a small
  value will often compress the mesh more (the numbers become shorter and
  more repetitions can be found).
    If you don't specify any value, the default is 5 (ie. 5 decimal in all
  numbers at max).
    Example: -r2

  -d    : Try to remove degenerate triangles

    With this flag the program will try to remove degenerate triangles from
  a triangle mesh. With bicubic patches it does nothing.

  -e[f] : Set epsilon value to f (by default no epsilon value is used).
          Example: -e0.00001

    By default the program compares floating point values with the statement
  "if(f1==f2)". If you don't like this, you can specify an epsilon value with
  this option. If you specify it, the comparations will be made with the
  statement "if(fabs(f1-f2)<epsilon)".

  -q    : Quiet mode. No status text is output to stderr.

    If you specify this flag, no status report will be printed to stderr.
  It doesn't affect error messages.

  -u    : Transform meshes independently

    By default, all the meshes in the input file are transformed as if they
  were a union of meshes. You can turn this feature off with this flag so
  that all meshes are transformed independently.
    Has no effect if you don't use transformations.

  -m    : Ignore keyword 'mesh'

    When reading a mesh, the program will search for the keyword 'mesh' in
  the input file and then read the following block as one mesh.
    If you specify this flag, the 'mesh' keyword is ignored and all triangles
  that appear in the file are read into one mesh.
    You can use this to read a union of triangles (POV2.2 style).


  The following options work only with smooth triangles:

  -n[f] : Normalize all normal vectors (make them equal in length) with
          length 'f' (a float value). If 'f' is not specified, the default
          value of 10 is used. (If '-r' option is specified, the values
          are also rounded)

    With this flag you can scale all the normal vectors to equal length thus
  increasing the possibility of repetition. The default length is 10.
    Example: -n2

  -o[f] : Try to optimize normal vectors with error tolerance 'f'. If 'f' is
          not specified, the default value of 0.001 is used

    This flag tells the program to search for repetitions more aggressively.
  If a point is pointing at the same direction as a normal vector (but
  they are of different length) the program will find it and set them equal
  (ie. eliminating one normal vector). With the tolerance value you can set
  how much may the direction of the point differ from the direction of the
  normal vector before it is considered different. Larger values will
  eliminate more normal vectors.
    Optimizing is not available when using transformations. This is because
  the optimizing process (if successful) will set some normal vectors to
  point at the vertex vectors. Since most of the transformations have to
  be performed differently on vertex vectors than on normal vectors (for
  example vertex vectors are translated but normal vectors aren't), it would
  screw up the optimized normal vectors.
    If you want to optimize and transform, you can do it in two steps: First
  apply the transformations and save to a temporary file and then optimize
  this temporary file and save it to the final file.
    With the command line version you can also do it without using a
  temporary file this way:
    meshcomp mesh.pov -b5 -t1,2,3 | meshcomp -c -o0.1 -i mesh.pcm


3.2 INPUT AND OUTPUT FILES
    ======================

    After the options come the input and output file names. The input file
  name is mandatory (unless you specify the -i flag) and the output file
  name is optional. If you don't specify an output file name, the program
  will output to standard out (ie. usually the screen).


3.3 TRANSFORMATIONS
    ===============

    You can specify several transformations that are applied to the mesh or
  bicubic patches before they are output. You have to specify these
  transformations after the options and the file names.
    In the Windows version of the program you can type the transformations
  in the "transformations"-field. The syntax is the same as with the
  command line version.

  -s<float>

    Scale. Multiplies all points by <float>. Normals are unaffected.
    Example: -s2.5

  -t<x>,<y>,<z>

    Translate. Translates the mesh by (<x>,<y>,<z>) (float values) from the
  current position. Normals are unaffected.
    Example: -t1,-5,2.5

  -c

    Center. Translates all points so that the mesh is centered to <0,0,0>.
  It's equivalent to specifying the -t transformation with appropriate values.

  -cb

    Center Bottom. Translates all points so that the bottom of the mesh is
  centered to <0,0,0> (the y-axis is considered up). It's equivalent to
  specifying the -t transformation with appropriate values.


  -b[<float>]

    Scale to Bound. Centers the mesh and then scales all points so that the
  mesh gets bounded by a box of size <float>. This is equivalent to applying
  -c and then -s with an appropriate value. If <float> is not specified, the
  default value of 2 is used (ie. the box extends from <-1,-1,-1> to <1,1,1>).
    Example: -b10

  -b-

    Outputs the minimum and maximum values (ie. Boundaries) of the mesh to
  stderr (later transformations may change this).

  -b+

    Like -b- but outputs also the boundaries of all the submeshes when there
  are multiple meshes in the input file (identical to -b- if option -u
  specified)

  -swap(x|y|z)(x|y|z)

    Swap coordinates. For example, -swapxz swaps all x and z coordinates.
  If you specify the same coordinate as both parameters, that coordinate is
  negated, ie. -swapxx will change the sign of all x coordinates (the mesh
  is mirrored about the yz-plane).

  -r<angle>,<x1>,<y1>,<z1>,<x2>,<y2>,<z2>

    Rotate. The parameter is followed by 7 float values separated by commas.
  The first value is the rotation angle, and the next 6 values define two
  points. The points are rotated <angle> radians around the axis defined by
  the two points.
    Example: -r3.14,0,0,0,10,-5,2.5


4.0 EXAMPLES
    =========================================================================

    The simplest way to use the program is:

meshcomp mymesh.pov mymesh.pcm

    This just reads triangle meshes from a file named 'mymesh.pov' and
  outputs the result to a file named 'mymesh.pcm'.
    If you want to compress a bicubic patch instead of a triangle mesh, you
  have to specify the -b flag:

meshcomp -b mypatch.pov mypatch.pcm

    If you want to convert the compressed file back to a POV-Ray file:

meshcomp -c -p mymesh.pcm mymesh.pov

  or:

meshcomp -c -p mypatch.pcm mypatch.pov

    The -c flag tells the program that the input file is a PCM file and the
  -p flag that it should output to a POV-Ray file. Note that you don't need
  to specify the -b flag when the input is a PCM file.

    Often automatic mesh creation programs output float numbers in a very
  large format (eg. "0.10000000" instead of just ".1"). You can use the
  program to clean this kind of files. Just specify both input and output
  as POV-Ray files:

meshcomp -p mymesh.pov cleanmsh.pov

    (Note that the program outputs just the meshes, and nothing else
  in the input file.)

    This makes the program to round all float values to the 4th decimal, to
  optimize the normal vectors with tolerance 0.1, to swap all y and z
  coordinates together, to scale the mesh so that it gets bounded by a box
  of size 10 and to translate it so that the bottom of the mesh is at the
  origin:

meshcomp -r4 -o0.1 mymesh.pov mymesh.pcm -swapyz -b10 -cb


5.0 TIPS AND TRICKS
    =========================================================================

+ * "Commenting out" part of the input file:

+   Sometimes it's useful to "comment out" part of the input file so that
+ the program will not read it. You can achieve this by putting quotation
+ marks (ie. ") around the part you want to be skipped. This way the program
+ will think that it's a string and just ignore it.
+   This may be used, for example, for compressing different bicubic patches
+ inside the same file to different pcm files. After that you can join those
+ pcm files into one. Then the patches will be handled as separated objects
+ (for example when applying textures to them).
+   Note: This doesn't work with PCM files since strings are meaningful there.


6.0 COMPILING THE PROGRAM
    =========================================================================

    If you are using DOS or Windows, you don't need to compile the program
  since compiled executables are included.
    If you are using other platforms, you have to compile the program before
  you can use it.
    The program follows the ANSI C++ standard. Most of the old C++
  compilers do not support it. The program has been successfully compiled
  with the latest versions of djgpp, egcs and Borland C++ Builder. (The
  latter one is the strictest about the standard.)

    In UNIX you usually should be able to compile the program with egcs
  this way:

g++ -O3 *.cpp -o meshcomp -lm


7.0 THE PCM FORMAT
    =========================================================================

    The PCM format is defined as follows:

  * For triangle meshes:
    -------------------

"PCM1",
<number of points in mesh>,
<point1.x>,<point1.y>,<point1.z>,
<point2.x>,<point2.y>,<point2.z>,
...
<number of triangles in mesh>,<number of smooth triangles in mesh>,
<index to tri1 pnt1>,<index to tri1 pnt2>,<index to tri1 pnt3>,
<index to tri2 pnt1>,<index to tri2 pnt2>,<index to tri2 pnt3>,
...
<index to smoothtri1 pnt1>,<index to smoothtri1 normalpnt1>,
<index to smoothtri1 pnt2>,<index to smoothtri1 normalpnt2>,
<index to smoothtri1 pnt3>,<index to smoothtri1 normalpnt3>,
<index to smoothtri2 pnt1>,<index to smoothtri2 normalpnt1>,
<index to smoothtri2 pnt2>,<index to smoothtri2 normalpnt2>,
<index to smoothtri2 pnt3>,<index to smoothtri2 normalpnt3>,
...

    All values are separated with commas.
    The values are (in order):
    - "PCM1" which indicates that a triangle mesh follows.
    - The number of points in the mesh (integer). Let's call it N.
    - N*3 float numbers specifing N points.
    - Number of triangles (T) (integer)
    - Number of smooth triangles (S) (integer)
    - T*3 integer numbers which are indexes to the points (0 is the first
      point, 1 is the second and so on). Each group of three indexes specify
      the three points of a triangle.
    - S*6 integer numbers which are indexes to the points. Each group of
      6 indexes specify a triangle. They are in the order:
      Point1,Normal1,Point2,Normal2,Point3,Normal3

    If another "PCM1" follows the last value, another mesh follows as well.


  * For bicubic patches:
    -------------------

"PCM2",
<number of points>,
<point1.x>,<point1.y>,<point1.z>,
<point2.x>,<point2.y>,<point2.z>,
...
<number of patches>,
<patch1.type>,<patch1.flatness>,<patch1.u_steps>,<patch1.v_steps>,
<index to pnt1>,<index to pnt2>,...,<index to pnt16>,
<patch2.type>,<patch2.flatness>,<patch2.u_steps>,<patch2.v_steps>,
<index to pnt1>,<index to pnt2>,...,<index to pnt16>,
...
  A patch can also be defined as:
-1,<index to pnt1>,<index to pnt2>,...,<index to pnt16>,

    The values are (in order):
    - "PCM2" which indicates that bicubic patches follow.
    - The number of points (N) (integer).
    - N*3 float numbers specifing N points.
    - The number of bicubic patches (P) (integer).
    - P times:
       - Type (integer).
         If 'Type' is not -1, then these values follow:
       - Flatness (float).
       - u_steps (integer).
       - v_steps (integer).
         If 'type' is -1, then 'Type', 'Flatness', 'u_steps' and 'v_steps'
         for this patch are the same as in the previous patch. The 'Type'
         of the first patch can't be -1.
       - 16 indexes to points.

    If another "PCM2" follows the last value, another group of bicubic
  patches follows as well. (The program doesn't generate this kind of files,
  but you can create them by joining several PCM files.)


+ * For extra compressed meshes:
    ---------------------------

+   The extra compressed mesh is much like the regular "PCM1" mesh but there
+ are some differences.
+   The identifier string is "PCM3" to distinguish it from the "PCM1" type.
+ The number of points, the point data and the number of triangles and
+ smooth triangles are like in the "PCM1" format.
+   After this come the index blocks for the triangles and then the smooth
+ triangles. The differences with "PCM1" are the following:

+   - The indexing is shifted by one, ie. '1' is the index to the first
+     point, '2' to the second and so on. Thus, when reading the data, they
+     should be decremented before indexing. The value '0' has a special
+     meaning described below.
+   - The smooth triangle indices are listed in the order:
+     p1,p2,p3,n1,n2,n3 (instead of p1,n1,p2,n2,p3,n3 of "PCM1") (it just
+     saves a bit of trouble in the meshcomp code with this ordering).
+   - The indices of the first triangle are listed as usual (ie. 3 values
+     if it's a triangle or 6 values if it's a smooth triangle). After this
+     one of these two may happen:

+     - If the next value is not 0 then the next triangle indices are the
+       two latter indices of the previous triangle plus this index. When
+       reading smooth triangles, the value following this will be the
+       index to the normal vector of the point.
+     - If the next value is 0 it means that regular triangle indices will
+       follow (it's a kind of 'reset' value).

+     The triangle and smooth triangle blocks are separated (ie. the first
+   triangle of the smooth triangle set doesn't use any indices from the
+   previous triangle block (if there was one)).

+   Important: When reading a compressed triangle (ie. a triangle which
+   uses the last two points from the previous one) you should swap the
+   points from the previous triangle for the 1st, 3rd, 5th, etc. (ie. the
+   odd) compressed triangle. This is necessary to preserve the order of
+   the triangle vertices (ie. clockwise or counter-clockwise). When a
+   triangle is specified entirely (ie. after a 0) the counting of the odd
+   triangles has to be reset.
+   (This is important only when the ordering of the triangle vertices is
+    important, for example when calculating the normal of the triangle)

+     Example:

+       8,3,
+       1,2,3,4,5,6,0,7,8,9,10,11,0,12,13,14,
+       15,16,17,18,19,20,21,22,23,24

+       Triangle  Indices     Corrected     Final
+       --------  -------     ---------     -----
+             1:  1,2,3    =>  1,2,3    =>  0,1,2
+             2:  2,3,4    =>  3,2,4    =>  2,1,3
+             3:  3,4,5    =>  3,4,5    =>  2,3,4
+             4:  4,5,6    =>  5,4,6    =>  4,3,5
+             5:  7,8,9    =>  7,8,9    =>  6,7,8
+             6:  8,9,10   =>  9,8,10   =>  8,7,9
+             7:  9,10,11  =>  9,10,11  =>  8,9,10
+             8:  12,13,14 =>  12,13,14 =>  11,12,13

+     (vert)  9:  15,16,17 =>  15,16,17 =>  14,15,16
+     (norm)      18,19,20 =>  18,19,20 =>  17,18,19
+     (vert) 10:  16,17,21 =>  17,16,21 =>  16,15,20
+     (norm)      19,20,22 =>  20,19,22 =>  19,18,21
+     (vert) 11:  17,21,23 =>  17,21,23 =>  16,20,22
+     (norm)      20,22,24 =>  20,22,24 =>  19,21,23



+   "PCM1", "PCM2" and "PCM3" type blocks can co-exist in the same pcm-file.
+ They are handled equally by the macros and the mesh compressor.



8.0 CONTACTING THE AUTHOR
    =========================================================================

    Comments, suggestions, and bug reports should be sent by email
  to <warp@iki.fi>.
