------------------------------------------ | spritegen: packaging sprites for Quake | ------------------------------------------ Overview of sprite generation and use ------------------------------------- Using a sprite consists of making the bitmaps for the sprite, packaging them up in a form Quake can use, and invoking the sprite while Quake is running. Making the bitmaps is simple: Draw them in Deluxe Paint or something else that generates .lbm files. Store the bitmaps in any directory you like. There can be multiple images, even shared between different sprites, in a single lbm, and you can have as many lbms as you want. Put them in any directory. Packaging up a sprite requires first making a script file that describes the contents of the sprite. The script file should be in /raid/quake/id1_/sprites, and should have the name .txt, as in s_test.txt. ( can be any valid filename, and is not required to start with 's'. The extension actually need not be "txt", but it's a useful convention so it's easy to identify sprite scripts.) The script file consists of two sorts of commands: sprite characteristic commands and sprite content commands. All sprite characteristic commands must precede any sprite content commands in the script file (in other words, characteristics must come first). Sprite characteristic commands are all optional; there must be enough sprite content commands to define at least one sprite frame. The sprite characteristic commands are: $type - specify sprite orientation type $beamlength - specify sprite offset from model origin for rotation purposes $sync - specify per-entity synchronization of group cycling The sprite characteristic commands are: $load - load an lbm containing sprite pixels $frame - specify a sprite frame $groupstart - start grouping frames for automatic cycling $groupend - stop grouping frames Detailed descriptions of the commands are below. Here's a simple script: ------------------------------------------------------------------------ $type vp_parallel $load /raid/quake/id1_/sprites/spr11.lbm $frame 24 80 32 32 $frame 56 80 32 32 $frame 88 80 32 32 $frame 120 80 32 32 ------------------------------------------------------------------------ This script specifies that the sprite is always drawn parallel to the viewplane, and contains four frames (numbered 0-3), with the pixels for the frames loaded from rectangles (24,80)-(56,112), (56,80)-(88,112), (88,80)-(120,112), and (120,80)-(152,112) in the file spr11.lbm. Another example is: ------------------------------------------------------------------------ $type vp_parallel_upright $beamlength 16 $sync $load /raid/quake/id1_/sprites/spark.lbm $groupstart $frame 16 48 8 8 .2 $frame 32 48 8 8 .2 $frame 48 48 8 8 .2 $groupend ------------------------------------------------------------------------ This script specifies that the sprite is always drawn pointing up in the world, but otherwise rotates to parallel the viewplane as closely as possible. The sprite has a non-zero beamlength, specifying that its center for drawing purposes is to be offset from the model origin by that distance after the sprite is rotated according to the model orientation. The automatic cycling of the group of frames is to be synchronized for all instances of this sprite. The first three commands, which specify the information described so far, are all sprite characteristic commands; the next command, $load, is the first sprite content command. $load specifies the source bitmap, and the group of commands following $load specify an automatic cycling group of three frames, each of which is to be displayed for 0.2 seconds before switching to the next. There may be any number of $load and $frame commands, and there may be multiple cycling groups and mixtures of cycling groups and single (ungrouped) frames. Each group has a single frame number that identifies it, as does each individual frame; frame numbers start at 0 and increment linearly. Another example: ------------------------------------------------------------------------ $load /raid/quake/id1_/sprites/spr11.lbm $frame 24 80 32 32 // frame #0 $frame 56 80 32 32 // frame #1 $load /raid/quake/id1_/sprites/spark.lbm $groupstart // frame #2 $frame 16 48 8 8 .2 $frame 32 48 8 8 .2 $frame 48 48 8 8 .2 $groupend $frame 56 80 32 32 // frame #3 $load /raid/quake/id1_/sprites/spark2.lbm $groupstart // frame #4 $frame 16 48 8 8 .2 $frame 32 48 8 8 .2 $frame 48 48 8 8 .2 $groupend ------------------------------------------------------------------------ This example script has 5 frames; these frame numbers, 0-4, are the numbers by which a .qc program controls the appearance of the sprite. The frames within the two groups in this script cycle automatically, transparently to .qc programs. This allows objects that are in constant motion, such as torches, to animate without any .qc processing or server-client bandwidth. Note that the above example uses "//" for comments. Scripts are passed through the C preprocessor before being processed, so all preprocessor features, such as comments and #defines and #ifdefs, can be used in sprite scripts. When you have your script file done, make sure you're in /raid/quake/id1_/sprites, and type: spritegen .txt. The finished sprite package is placed in /raid/quake/id1/sprites/.spr. (Actually, it's put in the directory with the same name as the current directory when spritegen is invoked, but with the last underscore ('_') removed from the path. So "/raid/quake/id1_/sprites" turns into "/raid/quake/id1/sprites".) Now, to invoke the sprite in Quake, just set the model field for an entity to . Sprite script command reference ------------------------------- ------------ $beamlength ------------ Specifies the length, in world coordinates, of the distance the sprite center is to be offset from the model origin, after rotation, in world space along the direction of model orientation, for drawing purposes. Used for things like swirling sparks. A zero value means no offset. If $beamlength not specified, defaults to zero. ------------ $frame [ [ ]] ------------ Generates a sprite frame. and are the coordinates of the upper left corner of the sprite frame's pixels in the currently loaded lbm, and and are the dimensions of the sprite frame's pixels in the lbm. is optional; if specified, it specifies how long, in seconds, group cycling should spend in this frame before going on to the next frame in the group (ignored for single (non-group) frames). If not specified, defaults to 0.1 seconds. and are optional; if specified, they describe the number of pixels to the origin from the left and top edges of the sprite, respectively. If these are not specified, the origin is placed at the center of the sprite. must be specified, at least as a placeholder, if and are specified. Basically, $load selects the lbm containing the sprite pixels, and $frame specifies the location of the new frame's pixels in the lbm, and size, and optionally group cycling time in this frame and/or the location of the origin relative to the sprite bitmap. ------------ $groupend ------------ Marks the end of a cycling group. ------------ $groupstart ------------ Marks the start of a cycling group. All frames specified between $groupstart and $groupend are considered part of the same cycling group, referred to with a single frame number and cycled on the basis of the interval values for the frames. Otherwise, group frames behave the same way as single (non-group) frames. ------------ $load ------------ Makes the lbm stored at the current lbm, from which the pixels specified by $frame commands are taken. ------------ $sync ------------ Indicates that all instances of this sprite are to cycle through groups synchronously. If not specified, cycle phase will be random for each instance. ------------ $type ------------ This commands specifies the orientation with which the sprite will be drawn. controls the orientation and can be: vp_parallel_upright: upright, but otherwise always drawn parallel to the viewplane (nothing right now, but could be, say, torches). Multiple sprites with this type all line up nicely in parallel, but pivot visibly as you turn from side to side; facing_upright: upright, but otherwise always facing directly toward the viewer (torches). Multiple sprites with this type don't line up nicely, but they seem much solider as you turn from side to side. The choice between this as vp_parallel_upright is totally a matter of taste; vp_parallel: completely parallel to the viewplane (fireballs, globes); oriented: drawn according to each sprite entity's orientation; orientation does not vary with viewing position or angle (not use for anything right now, but could be decals on walls). vp_parallel_oriented: drawn parallel to the viewplane, but the orientation on that plane is determined by the entity's roll angle.