tagap: the developer's handbook

37
The Developer's Handbook Copyright © Penguin Development Team. All rights reserved.

Upload: penguin-development-team

Post on 08-Mar-2015

134 views

Category:

Documents


2 download

DESCRIPTION

Developer's editing guide to the first TAGAP: The Apocalyptic Game About Penguins released by Penguin DT in 2007.Written by Jouni Lahtinen, created with OpenOffice.orgTAGAP and TAGAP 2 (c) Penguin DT. TAGAP (R) is a registered trademark of Jouni Lahtinen. All rights reserved.

TRANSCRIPT

Page 1: TAGAP: The Developer's Handbook

The Developer's Handbook

Copyright © Penguin Development Team. All rights reserved.

Page 2: TAGAP: The Developer's Handbook

Introduction

About this documentThe name says it all; “The Developer's Handbook”. Origins of this manual go as far as the very first code snippets of TAGAP itself, as rather than being user guide to editing, this was developer's journal about the technology and development progress. However, I realized quite soon that this thorough journal could be used, with few additions, as complete guide to the engine and to make lives of Modders a lot easier. Thus I polished it a bit and added few extra sections trying to translate my otherwise cryptic nonsense and here it is.

But it's still “The Developer's Handbook”; If you're not going to make any levels or game modifications for TAGAP, you can quit reading now. If you dare to continue, I sincerely hope you find this documentation at least remotely useful during your quest for fun gameplay.

File typesWhile many modern games are made of dozens of formats, we kept TAGAP as simple and clearly oriented as possible to ease working on it. In case you lack some software to work on the specified formats, we have listed most most freeware tools used to create TAGAP (see: Appendix D: Essential Software).

TAGAP_ScriptTAGAP_Script is simple external scripting system created for TAGAP Engine. Everything from system configurations and entity scripts to levels and even cut-scenes are made of this “language”. The extensions vary so you can right away see what they are used for; Level files are .map, configurations .cfg and scripts simply .txt. They are all simple ASCII text, so any Notepad-styled program works fine for scripting, while for making levels TAGAP features built-in level editor. Usage of TAGAP_Script is explained more in section Basics of Scripting and you can find complete list of TAGAP_Script commands from the Appendices section (see: Appendix B: TAGAP_Script Syntax).

GraphicsAll TAGAP graphics are in Targa TGA format (.tga), with either 24bit (solid) or 32bit (with transparency) colors. Note that OpenGL needs textures and some effects to have “power of two” dimensions (i.e. 16, 32, 64, 128, 256...), but there isn't such restriction with sprites, particles etc. TAGAP supports RLE compression and usage of it is strongly recommended; The files are remarkably smaller and there is no image data loss.

AudioTAGAP Engine uses 8 and 16 bit samples of 22050 Hz, ambient and cinematic stereo streams of 22050 Hz and streamed music of 16 bits and 44100 Hz. Samples should be mono as the engine handles all the stereo panning according to sound source, but global streams (like music and ambients) can (and should) be stereo. Preferred audio format is OGG Vorbis codec (.ogg) of any compression rate. Windows Wave (.wav) is also supported, but as it results very large files it's recommended to use Vorbis instead in your distributions.

You can add loops into music files via id-tags. Tag “START” defines where the loop starts and “END” defines the endpoint, both in milliseconds. Start of the file is 0 and end of the file is sound file length in milliseconds minus one milliseconds (i. e. end of 1.5 second sound is 1499, not 1500).

[ 2 / 37 ]

Page 3: TAGAP: The Developer's Handbook

Audio of TAGAP_Engine is powered by magnificent FMOD Ex Sound Engine from Firelight Technologies, used under their freeware terms (for more info visit official FMOD site at http://www.fmod.org).

General editing guidelinesTAGAP game modifications fall into two categories; Extra levels and Mods. To keep things as user-friendly as possible, it would be appreciated that you won't do anything in between.

Levels should be strictly that – levels. I know many of level makers would love to add new textures, but if you do, make it a Mod instead. If every level author out there just slaps their textures into game's main texture folder, players soon end up with TAGAP loading 200 Mb pile textures only one or two levels use.

When creating Mods, you can do whatever you wish, just don't alter the files in TAGAP data folder; If you want Pablo to have a “Hello Kitty” tattoo on his belly, don't add it to the original sprite, but make a duplicate of it into your Mod-folder and edit that duplicate. This way the original game never gets broken and users can easily add and remove Mods.

TAGAP itself can be run with relatively low amounts of memory, at least when compared to other games of today. That isn't, however, an engine limitation. If you want to make a Mod with super-hyper-high-resolution content, it's all possible, but given TAGAP's low-end roots it would be appreciated that such case is clearly stated in Mod's documentation.

[ 3 / 37 ]

Page 4: TAGAP: The Developer's Handbook

Creating Levels

Linedefs1. Selected linedef appears as bright, thick line with

arrows showing the facing.2. Linedef index.3. Selects the type of the linedef.4. Nudge linedef around by one pixel.5. Coordinates of the line's starting point.6. Coordinates of the line's end point.7. Length and vector components of the linedef as

both pixels and grid units.

Linedefs, short for “line definitions”, represent the basic physical world; Vertical linedefs act as floor or ceiling, while vertical linedefs are walls. The facing, shown as arrows, tells from which direction the line is blocking. In example horizontal line defined “Floor” stops movement from above and as vertical it will block anything attempting to pass it from left.

Lines are defined in Geometry mode and it couldn't be simpler. Just point at the starting point and hit [Space], then point at the end point and hit [Space] again. Once the line is defined you can drag it around as a whole by clicking it and moving mouse, or you can move it's points independently. Setting the line facing is important and can be done with selector or by pressing [C]. In addition to “Floor” and “Ceiling”, there's “M-Floor” and “M-Ceiling”; Those work physically the same, but act as metal when shot. Also, in game “M-Floor” appears as thinner metal plate floor (i. e. top of a transport crate).

Entities1. Selected entity is bright and has visible bounding box.2. Preview and description of selected entity (not all

entities are available for preview).3. Green dots are game characters.4. Turquoise dots are items.5. Miscellaneous objects appear as white dots.6. Player start point appears as yellow dot.7. Name of current entity (click to change the entity)8. Changes the facing and/or starting angle.9. Entities can start as active or inactive.10. Nudge entity around by one pixel.

Entities represent most characters and objects in the game and range from player character and enemies to items and decoration. You can also select and edit properties of multiple entities at the same time. To add an entity, hit the either [E] (for actor entities), [I] for items or [D] for miscellaneous objects and decoration. The entity appears as red “undefined” entity at first, but you can select the right from the entity list. The player start point is relocated with [Insert]. You can also copy the currently selected entity by pressing [G]. You can have one entity for each three entity “classes” copied, use [E], [I] or [D] to paste. Entities can start the game either as active or inactive. Inactive entities require a trigger impulse to be awaken. Solid entity dots represent active entities and hollow dots are the inactive ones.

[ 4 / 37 ]

Page 5: TAGAP: The Developer's Handbook

Triggers1. Selected trigger appears as bright and bold.2. Functional triggers are purple.3. Decorative triggers are green.4. Sound emitters are turquoise.5. Exit trigger appears yellow.6. Water areas are shown blue.7. Name of the trigger and it's index number (click to

change the trigger type)8. Coordinates of the trigger's upper left corner.9. Coordinates of trigger's lower right corner.10. Width and height of trigger in pixels.11. Normalizes trigger field dimensions to defaults.12. Nudge trigger around by one pixel.13. Each trigger style has it's own, unique set of options

to modify their attributes.

Triggers form the functional core of TAGAP. Their purpose varies from simply appearing as decoration to triggering complex scripted events. In this chapter we talk about the basics of handling trigger fields, for thorough explanation of all trigger types, see Using Triggers. For TAGAP_Script syntax of triggers see: TRIGGER.

All trigger fields are rectangles, so to define one you need to give it two points, just like with linedefs, only this time press [T] to add corners. Also like linedefs, triggers can be dragged around as whole or resized by dragging the corners.

Some triggers, i.e. trigger or terminal, will require a target link. To define one for currently selected trigger, simply point the desired entity or area inside desired trigger and press [L]. Not all triggers can be linked, though. Also note that overlapping linkable triggers may require you to temporarily move the other one away. Most link-using triggers can be linked to multitaps; If so, there is ‘Select multitap’ option available. Note that triggers not yet linked to anything will appear red.

Multitaps1. Number of links in current multitap.2. Multitap index and selection.3. Adds a new, empty multitap.4. Deletes current multitap.5. List of linked objects with their indexes.6. Removes link from multitap.7. When selecting multitap for a trigger, the list shows

multitap index followed by it's link quantity.

Multitaps, named after the retro console accessory of the same function, allow you to connect multiple objects into one trigger. Each multitap can have up to eight links and as each linked object may also be linked to multitap, you practically add unlimited events for one trigger. To bring up multitap editor, press [M] while in Geometry mode. To add a new multitap, click “Add” or browse through available multitaps to select previously defined one – hold shift to leap faster through the inventory. Linking objects to multitap works just like with triggers; Point the entity or trigger you want to link and press [L]. If there are overlapping trigger fields you may have to link them both first and remove the incorrect one afterwards with “DEL” button. Triggers that can be linked to multitaps will have “Select multitap” option in their settings.

[ 5 / 37 ]

Page 6: TAGAP: The Developer's Handbook

Textures1. White border outlines the selected polygon.2. Zoom window helps texture placement.3. Name of current polygon's texture (click to bring up

the texture list)4. Rendering order; Larger the index, more front it is.5. Moves to the back of the rendering list.6. Moves to the front of the rendering list.7. Polygon point used as texture offset.8. Toggles texture shading on/off.9. Nudge polygon around by one pixel.10. Information on all the polygon's points (corners).

Texture polygons are the basic graphical building elements. The shapes can be anything from a triangle to hexagon and hold any of the texture images found in the game's texture folder. Drawing shapes is simple; Just point with mouse and press [Space] to start polygon and hit [Space] again to add a polygon point. To close polygon either hit [Enter] or point at the first point and press [Space]. All polygons can naturally be dragged around as a whole or by individual points.

When creating large levels you'll really start to appreciate the quick tools. First is rectangle tool, with which you can define rectangular polygons just by defining two corners (press [T] or [R] two times). All shapes can also be copied and pasted ([G] gets the the current polygon and [P] pastes) and flipped horizontally ([H]) or vertically ([V]). You can also get the current polygon's texture ([D]) and fill some other shape with it ([D]). To change the order of polygons faster than with the selector, hold [Shift] and press [PgUp] or [PgDown].

One of the most important things to observe is usage of shaded textures; Shaded ones should be used as for things in background, while bright ones should represent either the foreground or things of importance. This gives the scenery certain illusion of depth. Also note that overdose effect uses these values to pick the colors, so not paying attention to balance of things will definitely look awkward. You can check the overdose view in editor by holding [Ctrl].

There's one special texture called “(fade)”; Like the name says, it's used to fade scenery from bright to black or just to dimmed. Easiest way to control fading is to draw a rectangle by starting with the line representing the side that will be bright, completing the polygon and setting texture offset to “2” (press [2]). Shaded fade is rendered as “shade” instead of solid gradient and is ideal for making shadows to add illusion of dimensions.

Setting up propertiesIn Properties mode you can edit various global attributes that define how the level looks, sounds and above all, plays. Always remember that many of these options serve as start-up details and can be manipulated on the fly during play.

Basically the main window is split into three sections. At the very top are the obligatory basics; Title of the level shown in the beginning (use “Untitled” for no title), level filename, filename of the next level, sequence to load between the levels and the filename of the music to play. You don't need to type them in, use “Browse” buttons to bring up lists of available files.

Next up are the three first image layers. These are the ones used as parallax backgrounds and screen monitors (see: screen) unless they are disabled from them. First is image layer index (which is referred to by triggers like layer) followed by the image filename (in folder “data/art/layers/”). Below are the options to manipulate how image will appear. Scroll defines how well parallax image follows movement of the view. Offset is pixel interval between the image and the top of the view. The two move values give the image constant scroll on x and/or y axis. Finally theres additional rendering flag; “Normal” means it's handled as standard parallax, “Gloom”

[ 6 / 37 ]

Page 7: TAGAP: The Developer's Handbook

makes that layer emit light when seen through windows, “Fading” fades the image from solid to completely transparent and “Disabled” prevents the layer from being rendered to parallaxes or screens. Only the three first image layers can have these values, the rest will always be “Disabled”. Simply click “More layers...” to add and edit the rest of the image layers.

Next section has options to edit level setting and gameplay. First button defines background image rendering method, indicating either full parallax, or as interior background rendered only when seen through windows and doors. Scheme defines the default level theme used at level start (see: THEME_START). Below these are the cannon fodder settings. First selects the default cannon fodder, next is starting spawning interval and the direction of spawning. Enemies can be set to spawn from sides (by default), fall from sky or from all around the player.

At the bottom of the main window there are two editor tools. First one centers the level to according to the most far left linedef and makes level dimensions to start from the x coordinate 0. This comes very handy while creating level data for sequences, as in them view is centered to point x400 y300, making x0 the left edge of the screen. The other option, start map from scratch, does exactly that; Wipes all level data from memory allowing you start a new map from the beginning.

The bottom window can be set to view either the contents of default cannon fodder or the level statistic. It's always good to keep checking the stats so you don't find yourself surprisingly running out level size. There's plenty of room and the levels can be quite darn huge, don't worry about that.

[ 7 / 37 ]

Page 8: TAGAP: The Developer's Handbook

Using TriggersNow you know how to create and modify triggers, but what are they for? Each type of trigger field has it's own specific purpose and in this section you'll find introductions to them all. Under the description is trigger's 'on use' function – thats what the trigger does when it is fired by another trigger or a multitap.

alwaysdescription: Works just like field, only this one isn’t turned inactive after being used. If you want some

object or multitap to be fired multiple times without need of adding restore for each toggle, use always.

on use: Triggers it’s target, stays active.

breakawaydescription: Works as static texture block that can be solid or non-solid.

on use: Texture block explodes with rubble flying around.

brickdescription: Solid or non-solid moving block that can be set to use either a texture or an image layer. If

texture has ‘damage texture’ defined (see: TEXDAMAGE), it will be used instead after the first toggle. By default brick will move and sound like elevator, but if it stops to floor height when moving down, it will fall faster and shakes the screen on impact with floor. Texture brick can also be set to look like plain texture, metal plated block or fully detailed floor block; The types of the brick linedefs will be automatically set accordingly. The moving radius is shown in editor by thin line drawn from the bottom of the brick. It will move to the other end of the line when triggered, and back when triggered again.

on use: Activates and starts to move to it’s other position.

clockdescription: Adds a clock to the level. It takes its time from system clock, so it should be on time when

the level starts. However, cause time in TAGAP isn’t a constant, time shown will ultimately be incorrect.

on use: –

counterdescription: Counter monitor displaying numeric value, which can be either time counting down or index

number counting up.

on use: Add or subtract one from the counter value.

delaydescription: Like field, but fires the target after a defined time. The delay time is given in milliseconds.

More complex scripted events always requires use of delayed events, so mastering use of these is a must.

on use: Triggers it’s target, turns inactive until it’s restored (see: restore).

doordescription: Door can be set to slide either up (default) or down when opened. If there are two doors, one

moving up and one moving down, with their ends connected, it will appear as large double-

[ 8 / 37 ]

Page 9: TAGAP: The Developer's Handbook

doordoor.

on use: Opens or closes the door.

doorstatedescription: State light can be linked to door, platform or brick. When linked object is opened, light is

green, otherwise its red. If no link is defined, doorstate will remain red all the time. You can also set doorstate alignment, so it will be rendered on left or right, connecting either ceiling or floor.

on use: –

elevatordescription: Guess what; It’s an elevator! It can start in top or bottom position and be set to make a

sound or move silently. Silent elevator also won’t have elevator tracks automatically set on wall, so if use that if you want to create custom elevators. Normally elevators can be activated by pressing [Use] while standing on them, but if it’s target of some other trigger – expect always – it can’t be activated that way.

on use: Activates and starts to move to it’s other position.

envdamagedescription: A decorative block of texture that will break when damaged or hit by a ricochet. When

damaged, the texture will change to damage texture (see: TEXDAMAGE) – or if no damage texture is defined, the block will get crack texture overlay (see: Editing variables). You can set both texture dimming and block material from the editor.

on use: Breaks the block.

exitdescription: End of a level area. Exit can be invisible field that activates when entered or triggered, or a

door. When door opens, it can be set to show either textures behind it or background layers. Like window, depending on current level theme, open ‘exterior’ door will result audible ambient sounds (like thunder or falling rain). By default the exit use ending sequence and following level as defined in properties (see: Setting up properties) with string NULL, but you can define some other sequence to be loaded as well, i. e. if you want to create exit leading to a secret level or something like that. Like many fields, exit can start either active or inactive.

on use: Either unlocks the exit door or activates exit.

fandescription: Fan is standard rotating device you can control through various options like spinning speed

and sprite frame. Amount of possible devices is defined simply by frames in fan sprite (“art/sprites/world/fan_*”), in TAGAP there are two possible devices, standard ventilation fan and small gear. Frame 0 works always as standard fan, emitting fan loop sound and spawning bubbles and smoke puffs if it’s in water or inside gas area. Fan can start on or off.

on use: Toggles fan on/off.

fielddescription: Standard all-round triggering field can be activated either by other trigger or by playing

stepping into the field area. Field can also be set to start inactive, requiring restoration (see: restore) before it will fire.

[ 9 / 37 ]

Page 10: TAGAP: The Developer's Handbook

fieldon use: Triggers it’s target, turns inactive until it’s restored (see: restore).

fishtankdescription: Clone tank with an entity floating inside. Clone tanks can be set to either make the entity

break free or to kill the entity inside. By default fishtanks emit bubbling sound, but you can turn it off if you have multiple tanks turning game into cacophony.

on use: Depending options either spawns the entity to the game or kills it.

focusdescription: Focus is used to create in-game cinematics where view is focused on something else than

player and actual gameplay pauses. View is centered to the origin of trigger field for defined period of milliseconds.

on use: Pauses gameplay and centers view on the trigger for a moment.

fodderdescription: Changes cannon fodder to another (see: CANNONFODDER). You’ll see a preview of that

fodder, so the right one is easy to pick. Use trigger tempo to change fodder spawning interval. This trigger can be fired unlimited times.

on use: Change cannon fodder

forbiddescription: Forbids area from player access, cannon fodder spawning, or both. Very necessary,

especially so when player has flying movement and can go beyond all level bounds.

on use: Toggles forbid on/off.

forcewalldescription: Energy force field blocks all fire and blocks movement. Force walls can be either vertical or

horizontal, which is defined by the field dimensions. They can also start active or inactive.

on use: Toggles forcefield on/off.

gasdescription: Area of lethal gas will damage everything organic.

on use: Toggles gas on/off.

guidedescription: Most dynamic way of rendering an entity to the background, guide is used to add lamps,

monitors, guide arrows and other similar decoration to the levels. Guides can be toggled on/off and destroyed. If used entity has corpse defined (see: CORPSE) it will be used as broken entity.

on use: Toggles entity on/off.

hologramdescription: Something between guide and envdamage, with hologram you can render entities either as

full entities that break like envdamage, or as holographic representations. Hologram entities are a lot more simplistic and you have less control over them, but they work great for decoration. Hologram can also be set to appear in background.

[ 10 / 37 ]

Page 11: TAGAP: The Developer's Handbook

hologramon use: –

infocompdescription: InfoComp is used for all dialog, monologue and info terminals. If InfoComp is link target of

some field trigger, it will appear invisible in-game and it's message is shown as player comment, otherwise it will be info terminal. In sequences also the info terminals appear invisible and their messages show up as non-player comment, while player comments are 'said' by player stand-in entity (see: AI_STANDIN of STAT). For player one-liners you can also define which voice over audio group will be used (see: VOICEOVER).

on use: Shows InfoComp message either as info text or as an entity dialog.

layerdescription: Renders image layer as part of the world. You can set the layer dimming and material like

with envdamage, but you can also make layer unbreakable if you wish. Also, layers can be set to be rendered ‘in background’, back between parallaxes and textures.

on use: Breaks the block or, in case of unbreakable ones, just disables it.

lockdescription: Works exactly like trigger, but requires a keycard to be activated.

on use: Triggers target if player has a keycard.

monitordescription: Monitor fill tool can be set to appear as standard sized or large wall monitor. Tracking

monitor will, well, track player and white noise is exactly that, white noise. In entity mode you can select the entity to be used, a bit like with guide or hologram, only the monitors will fill the entire trigger field instead of rendering just one. Monitors can be set to appear silent or noisy; Noisy monitors will play idle sound when active and flatlining beep when off.

on use: Toggles between tracking and white noise screens, entity monitor is first turned off, then swapped to white noise on the second toggle.

musicdescription: Change music on the fly. You can define the transition to be an instant cut, power-down fade

or basic fade out. Use string “off” to turn the music off.

on use: Changes or stops music.

platformdescription: It’s platform moving sideways, kind of like vertical door that is hidden inside a wall when it’s

off. Width of the platform isn’t fixed, but it can’t be longer than 128 pixels (8 grid units). Platform can also be used to create telescopic bridges, as it’s totally invisible and non-blocking when it’s off.

on use: Turn the platform on/off.

pulsedescription: Pulse is sort of a constant delay that fires its target in every defined milliseconds. As an

example, pulse with 1000 millisecond delay linked to an elevator will make the elevator go up and down, changing its direction on every second. As all this kind of triggers function only when they are in visibility radius, it’s strongly recommended that you make pulse as wide as

[ 11 / 37 ]

Page 12: TAGAP: The Developer's Handbook

pulsethe area it affects. Pulse can start either active or inactive, requiring restoration before starting the loop (see: restore).

on use: –

quakedescription: Shakes the screen by defined factor.

on use: Shakes the screen.

relocatedescription: This trigger can be used in sequences only. This is the key of creating complex entity events.

During sequences the AI still works, trying to aim and follow the player, even though player entity appears invisible. With changing player’s location via relocation, you can have entities change their aim, movement, etc. Feel free to experiment with this one.

on use: Relocates player instantly (sequences only).

restoredescription: Tool to restore inactive triggers – triggers that either have been already fired or ones set on

purpose inactive before some event occurs. If restore is linked to multitap, it will attempt to restore all trigger fields linked within.

on use: Makes target trigger active again or resets it to starting values.

rotawaydescription: Again pretty much like field, but requires defined times of activation before actually firing.

Like, if you make it require 5 activations, it won’t fire it’s target until on 5th activation.

on use: Triggers it’s target after defined times of activation, then turns inactive.

screendescription: Large monitor screen which uses background layers for graphics instead of entities. Screen

can be set to show only one of the layers, all of them as frame-by-frame animation or render the layers same way as the background parallaxes.

on use: If screen is set to show one of the frames, toggling changes the frame.

secretdescription: This field defines a secret area, which adds to your score when entered.

on use: Must be entered by player to activate.

sfxdescription: Plays sound effect, either positioned to trigger origin or as global, full-volume sample. Sound

effect must’ve been loaded somewhere within the TAGAP_Scripts before it can be played.

on use: Plays the sound effect.

signdescription: Electric light sign or one of standard letters. You can set the text yourself.

on use: –

[ 12 / 37 ]

Page 13: TAGAP: The Developer's Handbook

sounddescription: Emits sound loop from trigger. Sound loops are defined in TAGAP_Scripts (see:

SOUNDLOOP).

on use: Toggles sound on/off.

spawnerdescription: Spawns an entity to the game. You can choose any entity you wish and select between

standard teleportation effect or no effect at all. Spawner can be triggered unlimited times.

on use: Spawns the defined entity.

streamdescription: This trigger plays defined ambient stream. The default folder for these streams is

“data/sound/world/”. To stop the stream, use string “off”.

on use: Plays or stops audio stream

teleportdescription: Teleport device. If linked to other teleport, it can be used to travel to that teleport instantly. If

no link is set for current teleport, it can be used only as destination, not as transporter.

on use: Uses the teleport.

tempodescription: Changes the spawning speed of cannon fodder. Smaller the spawning interval, more frantic

waves of slaughter you’ll get. Use trigger fodder the change the actual cannon fodder.

on use: Changes the tempo.

terminaldescription: Computer terminal that works like trigger and can also be defined to start on or off. If no link

is defined, terminal will work as monitor with computer code running on screen.

on use: Triggers it’s target.

texblockdescription: Another texture block utility this time textures can be scrolled vertically or horizontally, i. e.

creating moving chains or conveyors. You can set the speed from editor.

on use: Toggles texture movement on/on.

themedescription: Trigger to switch the default level environment theme in-game (see: THEME_START).

on use: Switches level environment theme.

tickerdescription: Different kind of counter that counts either from zero to defined value or the other way

around. Ticker can be set to appear as counter monitor or gauge meter. You can also set the counting speed. Use restore to revert ticker back to its starting value.

on use: Start counting from/to zero.

[ 13 / 37 ]

Page 14: TAGAP: The Developer's Handbook

triggerdescription: Basic trigger mounted to a wall. Trigger can be defined to start either on or off. If trigger is

linked to always, it will appear as simple button that can be used unlimited times, like i. e. elevator call button.

on use: Triggers it’s target.

waterdescription: Well, it’s water. Water can be crystal clear, green toxic waste, burning lava or life-

regenerating clone fluid. Since edges of water area are faded, it’s strongly recommended to make water areas consist of only one trigger field instead of multiple ones. If you want to make completely flooded level, use level theme with UNDERWATER environment setting (see: THEME_START, ENVIRONMENT).

on use: –

waterfalldescription: Surprisingly it’s a waterfall. It’s mainly for decoration and to be used in context with related

water area. Like water, waterfalls can also be water, toxic waste, lava or clone fluid.

on use: –

windowdescription: Kind of a specialized version of envdamage, window is used to render windows only. You

can either use the default window texture by using string NULL, select a texture from list and use it like envdamage or make it appear as skybox only with string NONE. Windows can also be dimmed and forced to the background like layers, but then they can't be broken. Broken windows act accordingly to current level theme, i. e. if it's thunderstorm outside, raindrops will spatter through and raining sound and thunder are louder.

on use: –

[ 14 / 37 ]

Page 15: TAGAP: The Developer's Handbook

Basics of Scripting

Introduction to scriptingThough TAGAP_Script is intentionally left very simplistic, its still the most complex aspect of TAGAP editing. There are so many things you can do with basic commands, all sorts of hacks and combination of both, that in handbook we're not even trying to cover it all. Instead we'll focus on a couple of most asked-about subjects to get you started. Note that only a small fraction of TAGAP_Script commands are mentioned and explained here, so it's strongly recommended you'll scan through Appendix B: TAGAP_Script Syntax for the whole scripting language specs at least once.

So what makes a TAGAP_Script file? They are plain text ASCII text files that start with line “//TAGAP_START” and end with “TAGAP_END”. The code is written in the between. You can add comments in C-way by placing “//” at the beginning of the line. Script is being read line-by-line, so splitting script command to two lines isn't allowed. Note that strings don't support spaces, so replace them with “_”, which will appear as space in-game. That's the very basics, now let's look at what we can do with it.

Weapons scriptingNew weapons. No matter what game we're talking about, thats what people want to do first. To make a new weapon, you need to start with creating the weapon projectile entity. In TAGAP_Script, entities are defined with code block starting with ENTITY_START <entity name> and ending with ENTITY_END. Missiles have AI set to AI_MISSILE with projectile movement speed as speed value (see: THINK). Now with the graphics. The projectile needs a sprite defined (see: SPRITE) in order to appear as moving entity, otherwise it will be handled as traceline projectile, like bullets, beams and lightnings. Entity projectiles are flying by default, but you can set them ballistic, too (see: MOVETYPE). For good gameplay's sake projectiles should never have range greater than screen dimensions. To tune the range, use TEMPMISSILE relative to missile speed for entity projectiles and AI_RANGE for tracelines (for both, see: STAT).

Once the weapon projectile entity has been made there are two ways to assign it for an entity; via weapon slot (see: WEAPON) or as entity missile (see: MISSILE). Weapon slots work like player's weapons and every entity can use one, all you need to do is add STAT S_WEAPON <slot> variable for them (see: STAT). As weapon slots are global, many entities can use the same exact slot, so modifications to the weapon affect every entity using the slot. Missile is handy in many occasions too, like if you want multiple entities to use the very same projectile, but handle it in different manner. This is cause non-weapon slot missiles use rate-of-fire and charge values of the attacking entity, not ones of the projectile. Note that weapon projectile that is used as a weapon slot can also be used as missile – and an entity can have both weapon slot and missile defined.

Weapon slots have one significant advantage; You can have more control over them. Weapon slots 0–9 are available for player use and use ammunition unless defined otherwise. Other entities can naturally use these slots, too. Player can also use slots beyond that, but those act as non-ammo eating mounted weapons, like minigun of a chopper and when player entity uses such weapon, player can't access standard weapons. Other cool thing is, that unlike with defined missiles, entities can swap weapons too, if they're allowed to. Entity can be set to respond to each weapon individually (see: WEAPON_RESPONSE) or forced to always use the same weapon player is wielding (see: AI_COPY_PLAYER_GUN in STAT). You should think carefully which entities you'll allow to do this, however, as though it's makes cool combat situations with bosses, it goes a waste in run 'n gun levels.

And don't even dare to think it's over once the weapon is slapped to the game! Oh no, now the hard part begins; Whatever weapon you choose to make, remember to balance it well. Make it

[ 15 / 37 ]

Page 16: TAGAP: The Developer's Handbook

have weaknesses and strengths and keep testing and testing and testing until its perfect.

Sprites and animationsNow that your main scripting urge has been dealt with, it's time to look at sprite handling. It doesn't take long for you to notice how dull non-animated, non-interactive graphic blocks look like.

First off, there are two ways of loading sprites, static and dynamic loading. Static loading means the sprite is stored in memory at all times and can be accessed at all times, while dynamic means the sprite is loaded during initialization of the level in which the object is used and flushed when that level is completed. It's strongly recommended to use dynamic loading for entities and objects used only in certain specific locations of the game, like big bosses, for instance. This way you'll save a lot of precious memory from going a waste. A word of warning, though; Never use both methods for a one sprite! If the sprite is used in one entity as static and as dynamic in another, you'll end up confusing the engine on how to handle the sprite, which may result in game crash.

The main way TAGAP uses to animate entities is called parametric animation. Way more common with polygonal objects than sprites, this means that instead of animating object by displaying frame-by-frame, portions of the object are moved mathematically according to the entity's movement. An example to simplify the concept; When player runs, his legs are not animated by showing a new frame 24 times a second, but actually moving the legs. As a result the movement looks a lot smoother – especially so in slow-motion – and eats a lot less memory. This also allows combination of nearly infinite amount of animations, as player can aim any wanted direction without it affecting the running animation.

More specific parametric animations, like weapon or leg movement, are set in sprite definition itself (see: SPRITE). In addition to these “base” animation styles, there are sprite variables (see: SPRITEVAR). These can be used for both additionally expand the base animation or to define more simplistic animations (rotation, scrolling, frame-by-frame animation, etc.). Read the documentation of both ways carefully and start bringing your creations to life. And, as always, feel free to experiment.

SequencesSequences are toughest part of scripting and really hard to describe, as they are more or less based on exploiting the game routines in every possible way imaginable. Instead, this chapter describes the basic concept of doing animation sequences in TAGAP.

Perhaps the best way to start scripting a sequence is by first adding all the relevant configuration variables, or CVars (see: Appendix C: Configuration Variables, CVAR), most notably music to be played, save game allowance and level theme. Note that there's no sense in adding an audio stream at this point, as there's nothing to sync it with yet. Next, to make testing a lot easier, you should add a temporary sequence button, that restarts the sequence. This way you can run TAGAP in window and write the script and/or edit its graphics at the same time, just reloading the script in-game. To do this, use SEQUENCE and make it a sequence button, with the filename of that sequence as a target. Simple.

Now once the framework is done, its time to start creating the content. Basically sequences fall into three categories; in-engine animations with entities and level objects, image layer based animations and complex combinations of both. Image layer based ones are the easier, I guess, so let's start with those. Once you have the graphics, add them in with LAYER command. The image manipulation is done with image flags (see: SEQFLAG). Scaling, moving, rotating, it's all done with those. There's no need to go into details how to do some particular trick, as you're bound to learn more from just messing around and experimenting with the flags. Just note that most of the flags can be set to affect whole scene instead of an image by using index pointer -1.

Making in-engine animations is more complex and requires some experience in scripting already

[ 16 / 37 ]

Page 17: TAGAP: The Developer's Handbook

under your belt. First you naturally need to make the level data and it's obviously easier to do with the level editor. Start a new map and go to geometry mode. As very first thing add two linedefs, starting from coordinates x0 y0, first vertical and 608 pixels long, other horizontal and 800 pixels long. As you must have guessed, those represent the screen dimensions for the scene to fit your scene in. You can move view, sure, but it always comes back to origin. The entities used for sequence scripting aren't shown in editor, so add something you remember to replace in their place. Save the level and open it in text editor. Now copy all the contents except CVars from the level file to the sequence script and restart TAGAP to that sequence (see: Appendix C: Configuration Variables). In the text editors swap the entities to the ones you wanted by replacing their names – the positions you set in editor should be right. Save the file and hit that reload button you made first. And enjoy the show. I'm sure what you'll see as far from cool action scene you wanted to make, but it's a start.

By default, the dynamic graphics are flushed every time a new script is loeaded. This is fine with simple animations of one script frame, but if you want to do more complex cinematics with timed music and audio streams, it's strongly recommended to use “noreload” (see: Editing Variables). Enabling that prevents graphics from being unloaded from memory, allowing loading all the graphics on starting frame, making the cinematic smoothly flow through multiple frames without any load times in between. Variable “noreload” reverts back to zero after each script load for obvious security reasons, so you have to enable it again before every transition beyond which you want to keep the graphics. Dynamic sprites of entities (see: ENTITY_START, SPRITE) are also not flushed, so to preload an entity, define a “spawner” trigger (see: Using Triggers, TRIGGER) with the entity you need; It won't show-up if you don't activate the trigger, but it's graphics are still loaded.

In creating sequences its pretty much “everything goes as long as it works”. If it can't be done directly, it can be hacked with workaround. And if it can't done with workaround, it can be faked. While creating the game, every time I started doing a new sequence I was surprised by the flexibility of the system, as it's simple but offers so many options. All you need is imagination and too much spare time.

[ 17 / 37 ]

Page 18: TAGAP: The Developer's Handbook

Appendices

Appendix A: Editor ControlsGUI controls

F1 – F3F5F6F7F8Ctrl + SCtrl + LCtrl + XCtrl + Shift + HomeCtrl + Shift + EndAlt + ArrowsAlt + Arrows + Shift

[Switch editor mode][Next level * / **][Toggle between game and the editor][Restart level *][Editor setup][Save level][Load level][Instant quit][Delete all objects before mouse cursor][Delete all objects after mouse cursor][Nudge object by one pixel][Nudge object by a half grid unit]

General editor controlsArrowsHomeEndShiftAltPgUp / PgDownTABDEL

[Move view position][Center view on player start position][Center view on level exit trigger][Moves entire object instead of a point][Hold for grid-free movement][Select next / previous object in the list][Center view on the current object][Deletes current object]

Geometry modeSpaceBackspaceCE / I / DGPTLFOMInsert

[Adds a linedef][Cancels linedef / trigger field][Changes style of current linedef][Adds an actor / item / decoration entity][Copies entity or trigger, use E, I, D or P to paste][Pastes the copied trigger][Adds a trigger field][Links currently pointed entity or trigger][Select target of the current trigger][Select owner / user of the current trigger][Multitap editor][Relocates the player start point]

Texture modeR / TSpaceBackspaceEnterGPDFHV1 – 8CtrlShift + PgUp / PgDown

[Adds rectangular polygon][Starts drawing custom polygon][Cancels the previous polygon point][Completes the polygon][Copies the selected polygon][Pastes the copied polygon][Grab texture to fill tool][Use fill tool on polygon][Flip polygon horizontally][Flip polygon vertically][Set polygon texture offset point][Hold for Overdose view][Change the rendering order of polygons]

*) only available in-game; **) only available when cheats are allowed

[ 18 / 37 ]

Page 19: TAGAP: The Developer's Handbook

Appendix B: TAGAP_Script SyntaxTake note that not all script commands are always accessible, like you cannot set an entire world into a sprite. Don’t worry, though, all invalid script lines will be ignored by the parser and are reported in the user log.

Each actual command line starts with id string that tells the script parser the form of the current command. Here is the complete list of script commands (read: [id string] <variable input type>).

Entity commandsAMMO <int #1> <int#2>

description: Player ammunition for specific weapon slot.

syntax: <int #1> weapon slot index ; <int #2> ammo amount

notes: Player can have up to 10 weapon slots only weapon slots 1-9 can have ammunition (see: WEAPON). Weapon 0 doesn’t use ammo. However, ammo slot 1 of weapon entity is used to define clip size for weapon slot 0.

CLONE <string>

description: Clones all info of an existing entity.

syntax: <string> the name of the entity to clone

notes: Entity to be cloned must be defined before the clone. Useful when creating multiple similar entities, like containers spawning different goods – modifications made to the original entity affects all clones.

COLLECTIVE <string>

description: Defines the collective membership for an entity.

syntax: <string> the name of the collective leader entity

notes: All collective members will relate to the first leader entity in the list thus allowing only one collective of each type per-map. Collective leader cannot be damaged until the members are killed. Use this if you want to do, say, generator-powered boss monster or something like that. Use GROUP for other entity grouping options (see: GROUP).

CORPSE <string> <int>

description: Defines a corpse for an entity to be thrown upon death.

syntax: <string> the name of the corpse entity ; <int> y-wise throwing offset (from entity origin)

notes: Corpse must be defined before it can be assigned. Most of the corpse handling is done engine-side, so you don't have to worry about how it spins etc.. Corpses can also be “detailed” by assigning a kill effect to damage inflicter (see: KILLFX).

DESCRIBE <string>

description: Defines a description for an entity.

syntax: <string> short description

notes: Descriptions are not necessary, but they aid level editing a lot. Naturally entities that can’t be used in editor won’t obviously need descriptions.

EFFECT <string #1> <string #2>

description: Adds event effects to an entity.

syntax: <string #1> event tag ; <string #2> effect to add

notes: The amount of debris is defined by the size of the entity (see: OFFSET). Event effects can also be added to kill effects (see: KILLFX). Weapon-specific effects like muzzle flashes and shell casings are controlled via effect stats (see: STAT). Possible event tags:

DYING = entity falling apart before actually dyingGIB = entity blows apartWEAPON = entity attacks via shooting

Possible effects:

[ 19 / 37 ]

Page 20: TAGAP: The Developer's Handbook

EFFECT <string #1> <string #2>

EXPLOSION = an explosion, refers to splash damage for size (see: STAT)EXPLOSION_PLASMA = energy explosion, refers to light colors (see: LIGHT) and splash damage (see: STAT).DEBRIS_CONCRETE = throws concrete rubble and dustDEBRIS_GLASS = throws loads of glass debris and a few metal fragmentsDEBRIS_METAL = throws metal fragments and smokeFORCEFIELD = creates effect of force field shutting downGORE_BLOOD = spews out bloodGORE_GIBS = throws lots of blood and the severed eyeballsLIQUID_CLONE = throw drops of clone embryo liquidLIQUID_LAVA = throw drops of lavaLIQUID_SLIME = throw drops of radioactive gooLIQUID_WATER = throw drops of clear waterPAPER = spew some paper debris and some metal fragmentsSPARKS = electric sparkIMPACT = laser-styled projectile impact, refers to entity light (see: LIGHT)TELEIN = teleport effect for entity appearingTELEOUT = teleport effect for entity disappearing

ENTITY_ENDdescription: Stops parsing values for entity and adds the entity to the list.

syntax: –

notes: Always end entities with ENTITY_END.

ENTITY_START <string>

description: Starts parsing values for a new entity.

syntax: <string> name of the entity

notes: Keeps parsing entity variables until entity is closed (see: ENTITY_END).

FLASHLIGHT <int #1> <int #2> <int #3> <int #4> <byte #1> <byte #2> <byte #3>

description: Adds flashlight to the entity.

syntax: <integer #1> flashlight origin x-axis offset ; <integer #2> flashlight y-axis offset ; <integer #3> light halo radius (in percents) ; <integer #4> light beam length (in percents) ; <bytes> light color in RGB

notes: Flashlight won’t appear in fully lit levels (read: darkness set to 0, see: DARKNESS). Only one flashlight can be defined per entity, but it can bee multiplied with FX_MULTITORCH (see: STAT).

GROUP <string #1> <string #2> <int #1> <int #2>

description: Adds other entity to current entity’s group.

syntax: <string #1> name of the entity ; <string #2> relation id ; <int #1> origin x-offset ; <int #2> origin y-offset

notes: Setting up a group affects pretty much everything in an entity, so to ensure everything works set groups at the very end of entity definition. You can also define collectives that are level-bound instead of group-bound (see: COLLECTIVE). Possible relation ids:

COLLECTIVE = creates collective union between current entity and the memberMEMBER = member's death doesn't affect current entityUSER = death of member immobilizes current entity

GUNENTITY <string>

description: Sets an entity to be drawn as entity's weapon.

syntax: <string> name of the entity to be used

notes: Entity must be defined before it can be used. You can define weapon entity for both weapon slots (see: WEAPON) or directly for an entity. By default the gun entity will be drawn after (read: in front of) it's owner; Use FX_RENDERFIRST to draw it before the owner (see: STAT).

GIB <string> <int>

description: Defines an entity thrown as special debris on death.

syntax: <string> name of the entity to be used ; <int> amount of debris to throw

notes: Entity must be defined before it can be used. You can define just one debris per entity. This works for items, too, but there is another, more specific function to do just that (see: ITEM).

[ 20 / 37 ]

Page 21: TAGAP: The Developer's Handbook

ICON <string>

description: Makes entity appear as different, separate object when used in status bar.

syntax: <string> name of the entity

notes: Icon entity must be defined before using. If no icon is defined, the entity will be rendered to status bar as-is. Boss gauge of AI_BOSS (see: STAT) requires that entity has an icon.

ITEM <string> <int>

description: Defines an entity to be dropped when the current entity dies.

syntax: <string> name of the entity to be spawned ; <int> item dropping y-offset (from spawner origin)

notes: To-be-spawned entity must be defined before the spawner. ITEM can also be used to spawn other entities than just items, like smoke generators for flamethrower or ejecting pilot for destroyed chopper. You can define up to three items per entity. If that isn't enough, you can use gibs for more flying debris (see: GIB).

KILLFX <string>

description: Defines kill effect entity for weapon entity. Used in weapon definition scripts.

syntax: <string> the name of the effect entity

notes: The basics are as follows; When entity (projectile or a character) with assigned kill effect kills an actor with assigned corpse (see: CORPSE), that corpse will inherit special effects of the kill effect. For example if kill effect creates smoke, then the flying corpse will also create smoke. Use STATs and EFFECTs to add effects to kill effect (see: STAT, EFFECT). Effect must be defined before it can be assigned.

LIGHT <int #1> <int #2> <byte #1> <byte #2> <byte #3>

description: Lits the entity with RGB-colored light.

syntax: <int #1> light radius (in percents) ; <int #2> light intensity (in percents) ; <bytes> light color in RGB

notes: Lights with radius or intensity of 0 or lower are considered invalid. Light is emitted from the entity origin. Only one light can be defined per entity. The light is halo by default, but it can be turned into beam with FX_LIGHTBEAM (see: STAT).

MISSILE <string>

description: Sets a projectile to be spawned on attack.

syntax: <string> name of the entity to be spawned

notes: To-be-spawned entity must be defined before the spawner. Can also be used to spawn other entities than just missiles. Use offset variable WEAPON_MISSILE (see: OFFSET) to set the launching offsets different than the engine default and status variable MISSILE_OFFSETRADIUS to define the aiming radius (see: STAT). You can randomize the fired entity with MISSILE_RANDOMIZER (see: STAT). To add multiple weapons combine projectile definition with weapon slots (see: STAT and WEAPON).

MOVETYPE <string> <float>

description: Sets movement type for an entity.

syntax: <string> movement style tag ; <float> speed of movement

notes: Everything is NONE by default, except missiles, which are FLY. Possible movement styles:NONE = staticFLY = flying movementWALK = affected by gravity.

OFFSET <string> <float #1> <float #2>

description: Defines a offset value for an entity.

syntax: <string> variable name ; <float #1> x-offset ; <float #2> y-offset

notes: Be careful with missile offset values – values outside entity physical size will allow it to fire through walls. For non-weapon slot based missiles use STAT MISSILE_OFFSETRADIUS (see: STAT) to define radius distance different from entity's size. For effect offset based on entity facing use status variable FX_OFFSXFACE (also see: STAT). Variable references:

CONST_VELOCITY = constant velocities (not very practical for in-game AI, but useful in creating sequences)FX_CONSTANT_FLOAT = time and range modifier for constant, non-origin related floating

[ 21 / 37 ]

Page 22: TAGAP: The Developer's Handbook

OFFSET <string> <float #1> <float #2>

FX_DEATHEFFECT = debris spawning area of large entities dying (default is entity size)FX_OFFSET = fixed special effect offset (from entity origin)MODEL_OFFSET = offset when used as a weapon model (from entity origin) SIZE = entity dimensions (collision sphere size and height) WEAPON_CASING = shell casing / bazooka debris offset (from weapon origin) WEAPON_MISSILE = missile launching offset (from entity origin) WEAPON_OFFSET = muzzle flash offset (from weapon origin) WEAPON_ORIGIN = weapon sprite offset (from entity origin)

SCISSORS <int #1> <int #2> <int #3> <int #4>

description: Adds scissor area rectangle that will cut out portions of sprite that exceed the defined area.

syntax: <int #1> area start x-offset ; <int #2> area start y-offset ; <int #3> area width ; <int #4> area height

notes: Scissor usage is toggled with STAT FX_SCISSOR (see: STAT). If entity is part of a group, scissor area of group originator is used instead. Area doesn’t affect weapon sprites during their normal state, preventing them from getting oddly clipped during aiming.

SOUND <string #1> <string #2>

description: Defines a sound for an entity action.

syntax: <string #1> sound event ; <string #2> sample name

notes: Name of S_VOICEOVER doesn't refer to a sample, but to a predefined voiceover group (see: VOICE, VOICEOVER, VOICEOVER_END). Only one sound can be defined per event. Non-moving, static entities won’t naturally make a movement sounds. You can make all entity's sounds global instead of positional with FX_GLOBAL_AUDIO (see: STAT). S_SONG_DIE can be made to use music transitions (see: FX_TRANSITION in STAT), by default it instantly cuts to new song. Possible event references:

S_ATTACK = entity attacksS_COUGH = coughing for airS_DIE = entity diesS_DYING = large entity falling apart just before dyingS_IDLE = idle sound to play looped when awake and activeS_MOVE = sound of movementS_PHYSICS = physics impact soundS_RESPAWN = resurrection effectS_SLEEP = entity deactivatesS_SONG_DIE = sound played on death (“resume” resumes level music)S_SONG_WAKE = sound played on awakeningS_VOICEOVER = player voice-over on deathS_WAKE = entity activates / kill effect fraggin'' sound

SPRITE <string #1> <bool> <string #2> <int #1> <int #2> <string #4>

description: Defines a sprite for an entity.

syntax: <string #1> sprite loading parameter (STATIC or DYNAMIC) ; <bool> sprite full bright flag ; <string #2> animation style ; <int #1> sprite x-offset from entity origin ; <integer #2> sprite y-offset from entity origin ; <string #4> sprite name

notes: If sprite is used frequently in the game, it should be set STATIC (it's loaded once). If, however, it's huge and / or part of a boss used in only one level, make it DYNAMIC (it will be loaded only when it's used and flushed after) or use layer for a sprite (see: SPRITEVAR). Remember, though, that the same sprite should never be loaded as both dynamic and static, as it ultimately makes the engine confused and messes up the rendering. Sprites with pan animation are handled like textures and must be sized “power of two” (see: TAGAP Engine Introduction: File types) to be rendered. For more sprite handling parameters, see: SPRITEVAR. Possible animation flags:

ANIM_FACE = head movement and eye animationANIM_PANFORWARD(/BACK/UP/DOWN) = constant panning forward (/back/up/down)ANIM_PANATTF (/B/U/D) = attack panning forward (/back/up/down)ANIM_ROLLATT = attack rotationANIM_ROLLHIDE = hatch rotation animationANIM_ROLLVEL = velocity based rotationANIM_WEAPON = weapon animation with parametric recoilANIM_WEAPON2 = defines sprite a akimbo-only weaponNONE = no animation

SPRITEVAR <int #1> <string> <int #2>

description: Additional sprite variable.

syntax: <int #1> index of the sprite ; <string> variable name ; <int #2> value (not used with variables marked as [toggle]).

notes: Status variable references:ACTIVE = rendered only when entity is active [toggle]AIM = uses standard aiming angle for sprite angle [toggle]

[ 22 / 37 ]

Page 23: TAGAP: The Developer's Handbook

SPRITEVAR <int #1> <string> <int #2>

ANGLEFACTOR = sprite angle multiplier in percents (default is 100)ANIMATE = standard frame-by-frame animation (value is speed in percents)ANIMATE_TO = same as ANIMATE, but stops when to the final frame (value is speed in percents)BIAS = walk movement angleBOB = up ‘n down walk movementCHARGE = weapon charge animation [toggle]DIM = dimming transparency [toggle]FACE = flip sprite according to specified boolean face (doesn't flip offset coordinates)FLICKER = flickering transparency [toggle]HIDE_MOVE = entity moves y-wise by defined amount upon activationINACTIVE = rendered only when entity is inactive [toggle]INVERTFACE = draws sprite using inverted face[toggle]KEEPFRAME = uses defined frame instead of animation defaults (value -1 disables previously defined KEEPFRAME)LAYER= use defined image layer instead of sprite graphics (see: LAYER)PULSE = pulse animation, value works as speed modifier (for hearts, speakers, etc.)NOGROUND = ignores ground angle with BIAS [toggle]NOFACE = ignores sprite face (also affects offset coordinates) [toggle]ROLL = simplistic roll animationSCALE = sprite scale in percents (default is 100)

STAT <string> <int>

description: The common way of defining a value for an entity.

syntax: <string> status variable name ; <int> value (not used with variables marked as [toggle]).

notes: Status variable references:AI_ACID = makes entity an acid trip hallucination [toggle]AI_AIM_OWNER = keeps aiming at owner instead of player [toggle]AI_AMMO_ALL = spends all remaining ammo [toggle]AI_AMMO_PICKUP = can be picked up by pressing [Use], thus adding it's AMMOLIFE to defined weapon slotAI_AMMO_SPEND = defines how many rounds of ammo the weapon will spend (default is 1)AI_AMMOLIFE = ammo equals life [toggle]AI_BOSS = defines the entity a boss (boss gauge requires an icon, see: ICON) [toggle]AI_BURST = amount of rounds per fired burstAI_BURST_TIME = time between bursts (in milliseconds)AI_COPY_PLAYER_GUN = always uses same weapon as player [toggle]AI_DARKNESS_ACTIVE = when set, entity is active only when theme darkness is equal or less than this valueAI_DEATHJUMP = Super Mario styled dying jump [toggle]AI_DEATHJUMP_NULL = makes entity perform death jump instead of dying when it expires [toggle]AI_ENDING = end-level-on-death [toggle]AI_EXPO = item is handled as “pill” for achievements (items only) [toggle]AI_FINALE = final boss death effects [toggle]AI_FIRE_ON_ACTIVE = performs an attack on activation [toggle]AI_IGNORE_ONEUPS = kills the opponent regardless of any one-ups it may have [toggle]AI_INHERIT_ANGLE = for spawned entities, makes them always user owner's angles [toggle]AI_INHERIT_FACE = for spawned entities, makes them always use owner's facing [toggle]AI_INVULACTIVE = invulnerable when inactive [toggle]AI_HIDE = enables hide AI with visibility (time in milliseconds)AI_HIDETIME = hide AI hiding time (in milliseconds)AI_KEEP_IN_WATER = entity stays in water area [toggle]AI_KEEPANGE = sets constant, user-defined angleAI_KEEPACTIVE = keeps active, ignoring engine deactivation and no-aim [toggle]AI_KEEPACTIVE_FODDER = toggles AI_KEEPACTIVE if the entity is spawned as cannon fodder [toggle]AI_KEEPFACE = keeps own or group leader’s face when aiming [toggle]AI_LIMIT_ANGLE = limits aiming angleAI_LIST_ALIAS = show entity in non-default entity list (1=actor, 2=item, 3=decoration)AI_LOCK_ON_FIRING = stops aiming while attacking [toggle]AI_NOBOUNCE = makes falling missiles to blow on contact instead of bouncing (see: MOVETYPE) [toggle]AI_NUMB = stays numb on activation (time in milliseconds)AI_RANDOMIZE_SPEED = walking / flying speed randomizer (in movement units times 100)AI_RANGE = pattern movement range from origin / range of trace attackAI_REPEL = makes zombies turn away from the entity on collision [toggle]AI_SIZE = AI size modifier (affects damage knock back, falling effects, etc.; default is 0)AI_SLOWMOVE = defines movement animation speed (in percents)AI_SPAWNLIMIT = maximum amount of entities allowed to be spawnedAI_SPINAIM = spins aiming angle and keeps firing [toggle]AI_STANDIN = makes entity act as player standing for message quotes during sequences [toggle]AI_TEMP_ON_ACTIVE = initiates the missile temporary life span on activation [toggle]AI_TRIGGER_DISABLE = disable AI_TRIGGER_ON_DEATH if entity runs out of one-upsAI_TRIGGER_ON_DEATH = defines a trigger field to be fired on death – use with extreme care!AI_UNLOCKABLE = makes weapon available only after it has been unlocked [toggle]AI_WEAPON_NOFLIP = designed for player only, prevents weapons from being flipped [toggle]CHARGE = weapon charging time (in milliseconds)DAMAGE = amount of direct damage inflicted when attackingDAMAGE_ORGANIC = attack damage is inflicted only to bleeding objects [toggle]DAMAGE_OWNER = makes player missiles damage player also [toggle]DAMAGE_SHIELD = percent of damage entity takes when attacked (default is 100)DAMAGE_SHOCK = shows damage as electric shock [toggle]DAMAGE_SPLASH = explosion damage blast radius (can be used without inflicting damage)FRAG = destroying this entity will count in killing combos [toggle]FX_360 = emits halo-ripples from the entity [toggle]FX_ACTIVATION_SPARK = create a spark from weapon on entity activation [toggle]

[ 23 / 37 ]

Page 24: TAGAP: The Developer's Handbook

STAT <string> <int>

FX_BAZOOKA = bazooka back smoke [toggle]FX_BREATHE = makes entity breathing, creating effects when necessaryFX_BULLET = makes trace attack to be drawn as bullet (not fully supported by impaling attacks) [toggle]FX_CASING = shell casing typeFX_CLOAK = makes entity cloaked except when damaged (value is time uncloaked in milliseconds)FX_DIM = makes the entity light dim (0 is default dim, while negative and positive values alter the cyclic speed)FX_DIM_COLOR = renders entity with “dim” background color instead of foreground color [toggle]FX_DISABLE = disables particle and flash effects [toggle]FX_DROPDEBRIS = drops the death debris instead of throwing [toggle]FX_ELECTRIC = electricity effect [toggle]FX_ELECTRIC_LIT = electricity effect bound to light size and color [toggle]FX_EXPAND = expands entity towards removal (i.e. flame) [toggle]FX_FADE = fades entity to nothing instead of standard effects [toggle]FX_FLASH_ATTACK = screen flash glare applied on attack (in percents)FX_FLICKER = flickering light effect [toggle]FX_FLOAT = adds y-wise floating [toggle]FX_FORCEWALL = temporary force field effect based on entity's physical size [toggle]FX_GLOBAL_AUDIO = makes all entity sounds audible everywhere [toggle]FX_GLITTER = glitter glitter [toggle]FX_IDLEDISTANCE = audibility distance of idle sounds in percents (default is 40)FX_KEEP_EFFECTS = render effects even when entity is inactive [toggle]FX_LIGHT_ON_OFF = forces entity light to use engine on/off values instead (green/red) [toggle]FX_LIGHTBEAM = entity light beam length (in pixels)FX_MULTITORCH = multiplies the flashlight effectFX_MUZZLE = size of the muzzle flash (in percents)FX_NOENV_FX = disables environmental effects light glare and rain [toggle]FX_NOFACE = ignores facing changes [toggle]FX_NOSOUND = disables automatic (non-user-defined) sounds [toggle]FX_OFFSXFACE = particle effect x-offset (uses face)FX_PANSPEED = sprite panning speed for entity (in percents from default)FX_PLASMA = spawns sparks referring to entity light color [toggle]FX_POWERUP_SIZE = defines the size of power-up effects (default is collision sphere size)FX_PUSHUP = recoil pushes weapon upwards when firing [toggle]FX_RENDERFIRST = render additional models before entity [toggle]FX_SCALE_ITEM = size of entity sprite when appearing in status bar (in percents)FX_SCISSOR = enables scissoring [toggle]FX_SMOKE = adds particle smoke trail [toggle]FX_SMOKE_ANGLE = override angle for smoke FX_SMOKE_SHOOTFX_SMOKE_FLOOR = particle smoke from ground when moving [toggle]FX_SMOKE_SHOOT = shoots out smoke to aiming direction (value is smoke size in percents)FX_SOUND_ON_FIRST = plays attack sound only on the first round of a burst [toggle]FX_SPARKS = adds particle sparks [toggle]FX_SPIN_ATTACK = spin weapon on attack instead of firing [toggle]FX_SPIN_CHARGE = spin weapon on charge instead of glow [toggle]FX_SPIN_MOUNT = mounts gun, preventing spin “kick” and using alternate method for fullmodel angles [toggle]FX_TELEATTACK = applies teleport attack effect for missilesFX_TRANSITION = makes S_SONG_DIE (see: SOUND) to use transition (1 = power down ; 2 = fade out)FX_WADDLE = rapid waddle bias on death [toggle]FX_WADDLE_AIM = constant aim waddling rangeFX_WADDLE_CONSTANT = constant bias waddling rangeFX_WALK_SHAKE = room shaking applied upon movement (shake multiplier in percents)FX_WEAPON_FRAME = overrides weapon slot based weapon frame with defined frameHIGHROF = super rate-of-fire (multiple shots per real-time frame)IMPALE = number of entities trace attack will blow throughINVISIBLE = hidden while inactive [toggle]MISSILE_OFFSETRADIUS = projectile launching radial offsetMISSILE_OFFSETWADDLE = makes projectile offset waddle by defined pixelsMISSILE_RANDOMIZER = projectile entity randomizer valueMODELHACK = weapon model hack, defines entire character a weapon [toggle]MULTISHOT = makes weapon shoot multiple rounds at a timeNOLIST = doesn’t show entity in editor (useful for groups, scripts, etc.) [toggle]REVIVE = for items, restores player to full healthS_AKIMBO = guns akimboS_EXTRALIFE = extra life quantityS_HEALTH = entity life pointsS_IDDQD = gives invulnerability time (in integer seconds)S_KEY = keycard quantityS_OVERDOSE = gives overdose time (in integer seconds)S_QUAD = quad damage time (in integer seconds)S_SCORE = points gained from scoring (killing of picking up)S_SPEEDUP = gives speed-up and flying time (in integer seconds)S_WEAPON = weapon slot indexSCORE = points gained from scoring (killing or picking up)TAKEDAMAGE_BLEED = bleeds and takes damage [toggle]TAKEDAMAGE_ELECTRIC = non-organic, but sparkles and takes extra damage from electricity [toggle]TAKEDAMAGE_ENV = takes damage like environmental texture objects [toggle]TAKEDAMAGE_NONE = doesn’t take damage (same as default, toggle)TAKEDAMAGE_PLASMA = energy object that takes damage [toggle]TAKEDAMAGE_SURFACE = non-organic but takes damage [toggle]TAKEDAMAGE_UNBREAKABLE = unbreakable, solid, can’t be damaged [toggle]TEMPMISSILE = life span when fired as a missile (in integer milliseconds)

[ 24 / 37 ]

Page 25: TAGAP: The Developer's Handbook

TEXPOLY <string>

description: Adds a texture block centered on the entity start origin.

syntax: <string> texture image filename

notes: Being mainly designed for making background mount for static actors like turrets, this command is not that practical with moving entities. If the texture name begins with '(' the texture remains exclusive and doesn't show up in the editor's texture list. If you wish, you can clone it (see: TEXCLONE) to list it. Also texpolys can have assigned entities (see: TEXLITE), but it's not very practical since these are already entity-bound. Remember, though, that textures are always loaded to memory, so if this entity of yours appears rarely and/or is huge, you'd better use either “layer” or “hologram” triggers instead with dynamically loaded graphics (see: TRIGGER, LAYER).

THINK <string #1> <float #1> <string #2> <float #2>

description: Defines the AI routine used for the entity.

syntax: <string #1> main AI routine reference ; <float #1> speed modifier ; <string #2> attack AI function reference ; <float #2> delay between attacks (in seconds)

notes: If no main AI reference is defined the entity will be handled as a static decoration. AI reference AI_MISSILE applies the attack method AI_BLOW by default. Possible main AI references:

AI_AIM = constantly aims at the player, aim affects flying directionAI_CONSTANT = for use with collectives, keeps constant distance to the leaderAI_FOLLOW = follows the player until reaches attack rangeAI_ITEM = an itemAI_MISSILE = weapon projectileAI_USER = player-controlledAI_WANDER = flying entity which wanders around it’s ownerAI_ZOMBIE = walks straight until hits wall or diesNONE = static entity

Possible attack references:AI_FIRE = fires a missileAI_BLOW = acts like missile on impactAI_MELEE = attacks when player is within touchNONE = no attack

VOICE <string>

description: Adds a sample into player voice over group (see: VOICEOVER, VOICEOVER_END).

syntax: <string> sample name

notes: Samples are loaded from data/sound/voiceover folder.

VOICEOVER <string> <bool>

description: Starts defining player voice over group.

syntax: <string> group name ; <bool> “play once” flag

notes: Keeps parsing voice over samples until group is closed (see: VOICE, VOICEOVER_END). Group name is used to determine which group to play. You can name them how you please, except for the first group, which has to be “NULL” for compatibility. If “play once” flag is true (1), group won't play multiple times in a row – that group won't be played again until some other group is played in between. You can define death comments for entities (see: SOUND) or use trigger “infocomp” to create even more specific voice over events (see: Using Triggers: infocomp, TRIGGER). Obviously group must've been defined before it can be used.

VOICEOVER_ENDdescription: Closes player voice over group.

syntax: –

notes: –

WEAPON_RESPONSE <int #1> <int #2>

description: Responds to player's weapon by switching own weapon according to the scripting.

syntax: <int #1> weapon slot to respond to (0-9) ; <int #2> weapon to use against player's gun

notes: Entity's weapon response can be any of the available weapon slots (see: WEAPON). If there's no scripted response for player's weapon, the entity's default weapon (S_WEAPON, see: STAT) will be used. If you want the entity to always use same weapon as the player, use AI_COPY_PLAYER_GUN (see: STAT); That way you need to add weapon response details only for slots you don't want the entity to access.

[ 25 / 37 ]

Page 26: TAGAP: The Developer's Handbook

Definition commandsBACKGROUND_TO_DIMdescription: Makes on-background (dimmed) portions of the screen to use background color shifting instead of the default front

shifting. Used in map themes (see: THEME_START, THEME_END).

syntax: –

notes: Always active in case of overdose effect themes.

CANNONFODDER <int> <string>

description: Defines an cannon fodder list entry.

syntax: <int> index of the fodder list ; <string> name of the entity to add

notes: To-be-spawned entity is picked random from the chosen list. List indexes start from 1 (0=off).

COLOR <bool #1> <bool #2> <byte #1> <byte #2> <byte #3>

description: Defines the lighting colors for a theme. Used in map themes (see: THEME_START, THEME_END).

syntax: <bool #1> part to affect (0=world ; 1=backgrounds) ; <bool #2> shift state to define (0=base ; 1=target value of color shift) ; <bytes> color in RGB format

notes: Theme colors can be static or made to shift in various ways (see: SHIFT).

CVAR <string #1> <int / string #2>

description: Stands for configuration variable and is used for storing engine configurations.

syntax: <string #1> variable name ; <int> numerical value ; <string #2> string value

notes: Use either numerical or string value, not both. There are two types of CVars – those that are automatically stored into user configuration and those that are used for game scripting. See Configuration Variables for Game Editing for editing variables and “Troubleshooting Handbook” for system configuration variables as well as command line usage. CVars are registered engine-side, so you cannot create new CVars through scripting.

DARKNESS <int #1> <int #2>

description: Defines the intensity of the darkness effect. Used in map themes (see: THEME_START, THEME_END).

syntax: <int #1> base darkness ; <int #2> shifted darkness

notes: Darkness intensity ranges from 0 (over bright) to 3 (pitch black). Normal darkness is 1. Shifted darkness is only used by DELAY shifting (see: SHIFT). Not supported by overdose effects, they always refer to values defined of currently active theme.

ENVIRONMENT<string>

description: Defines the environment style for theme. Used in map themes (see: THEME_START, THEME_END).

syntax: <string> environment style

notes: Not supported by overdose effects. Possible environment styles:RAIN = heavy exterior rainRAININT = interior with heavy rain falling outsideSNOW = breezing cold with snowingUNDERWATER = completely flooded underwater setting

FONTW <int #1> <int #2 – #17>

description: Defines width of font characters per line in font textures. Used in game definition script.

syntax: <int #1> line in texture (0-5) ; <int #2 – #17> character widths in pixels

notes: Character width is one of a character in texture. It is strongly recommended, though not required, that all the numerals are of equal width, as different width results slight but visible fluctuation in status display counters, which doesn't look good. Width of numeral characters in default font is 21 pixels.

GRAVITY <int>

description: Defines gravity for theme. Used in map themes (see: THEME_START, THEME_END).

syntax: <int> gravity in percents of normal

[ 26 / 37 ]

Page 27: TAGAP: The Developer's Handbook

GRAVITY <int>

notes: You don't need to define gravity if it's the default 100%. Not supported by overdose effects.

GUISTR <string #1> <string #2> <string #3> <string #4>

description: Defines string to be used in GUI. Used in GUI scripts.

syntax: <string #1> string reference id ; <string #2> item name ; <string #3> help line ; <string #4> help line

notes: Menu ids must start with character '_', editor strings with '*' and sequence strings with '+'. This way you can have same id with different content (i.e. “_save” and “*save”). String id must not be longer than 16 characters. Though used ids of menu and editor strings are fixed in-engine, you can make your own strings for sequences (see: SEQUENCE).

INCLUDE <string>

description: Includes a new script file to be loaded on start-up. Used in game definition script.

syntax: <string> name of the script file to include

notes: Scripts will be loaded in the order specified.

SHIFT <bool> <string> <int #1> <int #2>

description: Defines color shifting for the level theme. Used in map themes (see: THEME_START, THEME_END).

syntax: <bool> part to affect (0=world ; 1=backgrounds) ; <string> style ; <ints> speed modifiers for the shifting cycle

notes: DELAY shifting intervals can be randomized (see: SHIFTRAND) and/or it can make a sound (see: SHIFTSOUND). Styles:

NONE = staticPULSATE = pulsatingDELAY = delayed sharp-cutting shifting (modifiers equal time delay in milliseconds)

SHIFTRAND <bool> <int #1> <int #2>

description: Randomizes theme color shifting modifiers. Used in map themes (see: THEME_START, THEME_END).

syntax: <bool> part to affect (0=world ; 1=backgrounds) ; <ints> max random value added to speed modifiers

notes: Supported only by DELAY color shifting (see: SHIFT).

SHIFTSOUND <string> <bool>

description: Sound played during theme color shifting. Used in map themes (see: THEME_START, THEME_END).

syntax: <string> sample name ; <bool> toggles ambient exterior effect

notes: Shifting sound is only played by DELAY shifting (see: SHIFT). Not supported by overdose effects.

SOUNDLOOP <string #1> <string #2>

description: Defines a sound loop for sound trigger field to choose from.

syntax: <string #1> sound loop reference name ; <string #2> loop sample name

notes: It's not recommended to use sounds that are defined as non-looping as looping and vice versa. Usage of OGG Vorbis format is strongly recommended in case of long loops because of smaller files. Once loop is defined it can be used with trigger “sound” (see: TRIGGER, sound).

STREAM <string>

description: Defines background audio stream to be played. Used in map themes (see: THEME_START, THEME_END).

syntax: <string> stream name

notes: All stream loops are streamed from “sound/world” folder. Streamed audio should be full stereo. Not supported by overdose effects. Doesn't affect sequences to avoid conflicts with sequence streams.

TEXBRIGHT <string>

description: Makes texture completely fullbright without need of adding separate fullbright texture.

syntax: <string> name of the texture

[ 27 / 37 ]

Page 28: TAGAP: The Developer's Handbook

TEXBRIGHT <string>

notes: Comes very handy in creating light sings etc. without wasting memory for nothing.

TEXCLONE <string #1> <string #2> <bool>

description: Clones a texture.

syntax: <string #1> name of the clone ; <string #2> name of the texture to clone ; <bool> toggles full bright of original texture for the clone

notes: Mainly used in creating effect-free versions of already lit or entity-assigned textures. Always create a clone instead of duplicating the image file, thus avoiding needless memory wasting. You can also clone engine-defined textures and entity texpolys (see: TEXPOLY) to be used in editor; In this case the texture has to be defined before creating a clone.

TEXDAMAGE <string #1> <string #2>

description: Defines a damaged equivalent for a texture.

syntax: <string #1> name of the texture ; <string #2> name of the damage texture

notes: Designed for use with trigger “envdamage” (see: TRIGGER, envdamage).

TEXLITE <string #1> <string #2> <int #1> <int #2>

description: Adds an entity for texture polygon.

syntax: <string #1> texture name ; <string #2> entity name ; <int #1> entity x-offset (in percents of texture image size) ; <int #2> entity y-offset (in percents of texture image size)

notes: Both the texture and entity have to be defined before using this command. This was originally designed to add texture lights, but it works with all entities. Use texture clones (see: TEXCLONE) to add different effect variations – to do this, create a clone before assigning any entity to the original texture. You can also add entities to texture clones and entity texpolys (see: TEXPOLY).

TEXMODULATE <string> <float> <int>

description: Makes fullbright of a texture to be parametrically animated or modulated.

syntax: <string> name of the texture ; <float> amount of modulation ; <int> direction

notes: The texture must naturally have a fullbright overlay in order to get the modulation to work. Directions are: 0 = x-wise ; 1 = y-wise ; 2 = round. Modulation works for all sorts of texture objects.

THEME_ENDdescription: Stops parsing values for a level theme.

syntax: –

notes: –

THEME_START <string>

description: Starts defining a level theme.

syntax: <string> name of the theme

notes: Keeps parsing values until THEME_END. If the name starts with '_' it will be handled as overdose effect instead of level theme.

WEAPON <int> <string #1> <string #2> <string #3>

description: Defines a weapon slot.

syntax: <int> weapon slot (0-31) ; <string #1> primary weapon entity name ; <string #2> secondary weapon entity name ; <string #3> weapon display name

notes: Weapon entity must be defined before the weapon itself. Use status variable S_WEAPON to define active weapon slot for an actor entity (see: STAT) or use weapon response scripting (see: WEAPON_RESPONSE). Player can use weapons 0-9 if ammunition is available (see: AMMO), so use slots 10 and above for non-player weapons. To add multiple weapons combine weapon slots with projectile definition (see: MISSILE).

[ 28 / 37 ]

Page 29: TAGAP: The Developer's Handbook

Scripting commandsENTITY_SET <string> <int #1> <int #2> <int #3> <bool>

description: Adds a new entity into a desired location.

syntax: <string> entity name ; <int #1> entity x coordinates ; < int #2> entity y coordinates ; <int #3> entity facing or angle ; <bool> activity state (0 = active ; 1 = inactive)

notes: In case of AI_AIM entity facing is actually the default aiming angle in integer degrees, otherwise it's boolean representing left/right). In case of player character, setting entity inactive makes it “teleport in” in the beginning of the level and/or sequence.

LAYER <int #1> <int #2> <int #3> <int #4> <string> <int #5>

description: Adds a image layer that can be used as parallax background, static image or even sprite. Used in level and sequence scripts.

syntax: <int #1> scrolling speed multiplier ; <int #2> layer y-axis offset from the top of the screen ; <int #3> x-wise movement speed ; <int #4> y-wise movement speed ; <string> texture filename <int #5> in-game rendering flag

notes: Use status variable FX_LAYER_SPRITE to use specific image layer as a sprite (see: STAT). Use movement speed 0 for still images. In case of sequence script the scrolling speed multiplier works as a x-axis offset. Sequence images are manipulated with SEQFLAGs (see: SEQFLAG). Use 32 bit parallaxes only when absolutely necessary – large ones are major slowdown on older video cards with poor fill rate.

LINEDEF <int #1> <int #2> <int #3> <int #4> <int #5>

description: Stands for “line definition” and adds a new geometry line into the map.

syntax: <int #1> starting point x coordinate ; <int #2> starting point y coordinate ; <int #3> ending point x coordinate ; <int #4> ending point y coordinate ; <int #5> style flag

notes: Linedefs are used as floors, ceilings and walls for physics calculations. Style flag defines the linedef facing and style (0 = floor or facing left ; 1 = ceiling or facing right ; 2 = plate floor ; 3 = plate ceiling). Incorrect face may result incorrect entity movement and awkward collision events.

LINK <int> <string>

description: Adds a multitap link. Used in level multitaps (see: MULTITAP, MULTITAP_END).

syntax: <int> target index ; <string> link class

notes: Link class LNK_NONE is disabled from multitaps as a complete waste-of-space. Possible link classes are LNK_ENTITY (entity link) and LNK_TRIGGER (trigger link). For safety reasons multitaps cannot be linked to other multitaps by class LNK_MTAP, like triggers.

MESSAGEdescription: Starts parsing info message.

syntax: –

notes: Keeps parsing message lines until message is closed (see: MESSAGE_END). Messages are referred to by trigger “infocomp” (see: TRIGGER, infocomp).

MESSAGE_ENDdescription: Closes current message.

syntax: –

notes: Always close messages with MESSAGE_END.

MESSAGE_LINE <string>

description: Adds a line into current message. Used in message scripts (see: MESSAGE, MESSAGE_END).

syntax: <string> message line

notes: –

MULTITAPdescription: Starts parsing multitap controller.

[ 29 / 37 ]

Page 30: TAGAP: The Developer's Handbook

MULTITAPsyntax: –

notes: Keeps parsing multitap links (see: LINK) until the device is closed (see: MULTITAP_END).

MULTITAP_ENDdescription: Closes the current multitap.

syntax: –

notes: Always close multitaps with MULTITAP_END.

POLYGON <string> <int> <bool>

description: Starts parsing a polygonal texture shape.

syntax: <string> texture name ; <int> polygon point used as the texture offset ; <bool> texture shading (on/off)

notes: Keeps parsing polygonal shape until the shape is closed (see: POLYGON_END, POLYPOINT). The order of polygons in the script equals to the order they are drawn to the world.

POLYGON_ENDdescription: Closes the current polygonal texture shape.

syntax: –

notes: Always close polygons with POLYGON_END, not by re-entering the first polypoint.

POLYPOINT <float #1> <float #2>

description: Adds a new point to the current texture polygon. Used in polygons (see: POLYGON, POLYGON_END).

syntax: <float #1> point x coordinate ; <float #2> point y coordinate

notes: Polygon must have at least three points to be valid.

SEQFLAG <string> <int> <float #1> <float #2>

description: Adds sequence image layer rendering flag. Used in sequence scripts.

syntax: <string> flag id ; <int> index of affected image ; <float #1> speed / offset ; <float #2> distance / amount value

notes: Used to animate sequence images (see: LAYER). The speed / offset value defines the direction (positive or negative) and amount value works as a target multiplier. Creating picture box BUTTON requires two images (normal and mouse hover version). Sequence flags are private for each sequence script, so when keeping images in memory during multiple sequences (see: “noreload” in Editing Variables, CVAR), they can be manipulated independently on each frame. All flags except BLIT, BLITCONSTANT, BLITRANDOM, BUTTON, DISABLE, FADE, FRONT, RELOCATE and REPEAT can be set to affect the entire scene; Just set image index to ‘-1’. Possible flag ids:

BLANK = image is used for blank items and isn’t shownBLIT = draws image for a “amount” period of time (speed defines invisibility time)BLITCONSTANT = defines a delay during which layer manipulation, like movement, is disabledBLITRANDOMIZE = image blit value randomizerBUTTON = transforms GUI item into button (offset is image state 1 or 2, amount is GUI item index)DIM = dim shading, amount equals time spent fully lit, ‘0’ or below makes pulsing imageDISABLE = prevents layer from being rendered (in case of images loaded in previous sequence).FADE = fades invisible, works like dimFRONT = defines the image rendering layer (from 0 to 3; use -1 to make image appear only as parallax)MAGNIFY = same as zoom, but from original image to “full * amount” sizeMOVEX / MOVEY = moves image to its position from offset in “time / amount”RELOCATE = relocates layer image that has been loaded in previous sequenceREPEAT = makes non-ARB image repeated texture (values represent added width and height)ROTATE = rotates image until angle is “amount” (amount ‘0’ is unlimited rotation)SCISSOR = scissor area (value = start x ; amount = start y ; scene only)SCISSORSIZE = scissor area size (value = width ; amount = height ; scene only)ZOOM = zooms to or out from “full * amount” sized image

SEQSOUND <int #1> <int #2>

description: Defines a sound to be played for sequence button item.

syntax: <int #1> button item index ; <int #2> sound index

notes: Sound will be played when active button item is used. Basic user interface sounds are indexed from 0 to 6. Only sounds defined in-engine can be used (user-defined in-game samples aren't available).

[ 30 / 37 ]

Page 31: TAGAP: The Developer's Handbook

SEQUENCE <string #1> <int #1 / float> <int #2 / string #2> <string #3> <int #3> <string #4>

description: General sequence scripting command with two different possible syntaxes. Used in sequence scripts.

syntax: <string #1> command id ; <int #1> x-wise offset ; <float> timer time (in milliseconds) ; <int #2> y-wise offset ; <string #2> timer command id ; <string #3> output text string / timer command string value <int #3> item layer (non-timer) ; <string #4> hyperlink (non-timer)

notes: Possible timer commands are MAP (go to the next map) and SEQ (activate another sequence). Use “TIMER” command id to activate timer parsing. See LAYER for sequence image handling. Item layer 0 means it will be drawn into sequence itself and it is affected by all fade and glare effects. Layer 1 is for active items, which are never faded or glared. Remember to define a hyperlink even for non-hyperlinks to avoid parser errors (use “_”). For text items use negative layer value for alternate alignment (-1 = left, -2 = center, -3 = front center). To use GUI strings with hover help, use output text (see: GUISTR). Possible command ids:

FREEZEAI = freezes all AI activity (timer only)MAP = go to the next mapNEWGAME = start a new gameRESTART = restart from beginning of the previous levelSAVE = brings up the save game list for savingSCORE = prints the current contents of a Cvar (use hyperlink value)SEQ = activate another sequenceSTOPSOUND = stops all sound effects (timer only)STOPSTREAM = stops audio stream nut music and effects will continue (timer only)TEXT = bright text stringTEXT_DIM = darkened text stringTEXT_LARGE = large, bright text stringTEXT_LARGE_DIM = large, darkened text stringTEXT_WHITE = white, null text stringTEXT_WHITE_DIM = darkened white text stringTIMER = sets a timer

SEQTIMER <int> <float>

description: Sequence trigger timer. Used in sequence scripts.

syntax: <int> index pointer of the trigger to be fired ; <float> time to firing the trigger (in seconds)

notes: Each timer will fire only once.

TRIGGER <int #1> <int #2> <int #3> <int #4> <int #5> <string #1> <string #2> <string #3> <int #6>

description: Adds a trigger field.

syntax: <int #1> top-left x coordinate ; <int #2> top-left y coordinate ; <int #3> bottom-right x coordinate ; <int #4> bottom-right y coordinate ; <int #5> target index reference or modifier value ; <string #1> trigger name ; <string #2> trigger string ; <string #3> link class ; <int #6> additional variable value

notes: Triggers with other field names will be ignored. Field must have both height and width to become valid. Triggers can be linked to entities, usable trigger fields and multitaps. To learn more about triggers and to view all possible trigger names, see: Creating Levels: Triggers and Using Triggers. Possible link classes:

LNK_ENTITY = entity linkLNK_MTAP = multitap linkLNK_TRIGGER = trigger linkNONE = no link

[ 31 / 37 ]

Page 32: TAGAP: The Developer's Handbook

Appendix C: Configuration variablesConfiguration variables (commonly referred to as “Cvars”, see: CVAR) are what the name suggests; global variables registered to the engine and used to setup and adjust both system and the game. You can go and tweak these from within the script-, level-, and configuration files manually.

Setup variablesinput_autoswitch Toggles automatic switching into new weapons (1=on, default ; 0=off). Stored in configuration file.

input_gamepad Toggles gamepad controls (1=on ; 0=off, default). Stored in configuration file.

input_guispeed Mouse speed modifier as byte. Stored in configuration file.

input_keyleft, input_keyright, input_keydown, input_keyload, input_keyjump, input_keynext, input_keyprev, input_keypeak

In-game keyboard configurations. Values refer to DirectInput keyboard constants. Stored in configuration file.

input_peak Switches peaking mode between toggle and hold (1=toggle ; 0=hold). Stored in configuration file.

nosound Disable all sounds (1=disable sounds). Ignores completely the sound calls so the game can be run even without sound card, like on workstation computer. Command line only.

safemode Use value 1 to revert all game settings to defaults. Command line only.

snd_dsound Toggles DirectSound driver for sound (1=on, default ; 0=off). When DirectSound is turned off Windows Multimedia driver will be used instead. Though DirectSound is generally faster and has better compatibility, some older soundcards may have incompatible drivers, resulting stuttering playback. If so, use Windows Multimedia drivers instead. Stored in configuration file.

snd_musicvol, snd_soundvol

Sound effects and music volumes in bytes (0–255).

snd_voiceover Toggles player voice over (1=on, default ; 0=off).

vid_bpp Video color depth in bits-per-pixel. Most cards don’t support other than either 16 or 32 bits-per-pixel. Only affects full screen mode as windowed mode uses the desktop color depth. Note that though using lower color depth results less-sharp graphics, it gives significant speed boost, especially when using low-end graphic cards.

vid_fullscreen Full screen mode (1=full screen ; 0=windowed mode). Windowed mode always uses the desktop color depth for the best compatibility.

vid_width, vid_height Video resolution dimensions in pixels (default is 800x600). Note that TAGAP was designed for 800x600 and 800x600 only, so using higher resolutions doesn't affect graphical quality, but allows the usage of full screen with displays that don't support the game's resolution. Normally the game runs in a virtual window, but you can use “vid_stretch” to to stretch the screen to fit the resolution

vid_stretch Toggles screen stretch (1=on ; 0=off). This stretches the game screen to fit the resolution instead of showing up in a virtual window. Recommended only for very fast video cards.

vid_warp Toggles framebuffer warping effects of water (1=on ; 0=off). Turning this option off improves performance significantly on slower systems.

user_cheats Toggles ”Cheats” menu access on/off (1=on ; 0=off). Command line only. Game can't be saved and achievements can't be unlocked while cheat mode is on.

user_hijack Permanently hijacks another user name to be associated with the current Windows log-in name. All configurations, achievements and saved games are stored according to user name, so after changing user name you'll need to use this variable. Note that all progress made under current Windows log-in name will be lost during an account hijack. To use another account on per-session basis without removing current progress, use “user_name” override. Command line only.

user_name Overrides user name. User name is by default the same as user's Windows log-in name (with caps replaced with “_”). The override user name is used for that session only; To permanently hijack an account use variable "user_hijack”. Command line only.

Editing variablesmap_cannonfodder Defines cannon fodder summoning (0=off).

[ 32 / 37 ]

Page 33: TAGAP: The Developer's Handbook

map_fodderrain Toggles fodders falling from the sky (1=on ; 2=sides and sky ; 0=off).

map_fodderspeed Defines cannon fodder speed ranging from 1 to 20.

map_interior Toggles use of level interior skybox backgrounds instead of full parallaxes (1=on ; 0=off).

map_nextmap Filename of the next map loaded when the level is completed. When used from command line the “next map” is loaded on start-up – use this to load custom levels.

map_nosave Toggles possibility to save on/off (1=on ; 0=off). Designed for use in sequence scripts only, but works in-game, too.

map_scheme Defines the default environmental theme of the level.

map_sequence Filename of the sequence loaded when the level is completed or proper sequence event is initiated. Use name “none” if you want to load the next level straight on exit. When used from command line the sequence is loaded on start-up.

map_title Title of the level. Mainly used in level scripts. Title “Untitled” won’t be printed on loading a level.

noreload Prevents dynamically loaded graphics data from being flushed between sequences (1=on ; 0=off, default). If you want your sequence to be timed perfectly and synced with streams without falling behind on slower machines, use this. When turned on, it affects the next sequence swap and is reverted off again; You must define it for each sequence script independently.

snd_noloop When toggled (1=on ; 0=off, default) the in-song loop points are ignored and the song is looped from the beginning to the end. Used only in sequence scripts, this value is reset back to “off” on every level and sequence load.

snd_pausesong When toggled (1=on ; 0=off, default) pausing the game or using the menu won't pause the music; Comes handy in sequences featuring cinematic score. This variable is reset back to “off” on every level and sequence load.

snd_song Filename of the default song to be streamed. Use name ”off” for no default music. When the music resumes, like after a boss fight, this is the song that'll be played.

snd_stream Filename of the sequence audio to be streamed. This variable is turned to ”off” before loading a sequence, so to continue streaming current audio, you'll have to define the same stream for the follow sequence, too. Usable only in sequence scripts.

user_bbox Toggles entity bounding box display on/off (1=on ; 0=off). Ideal for testing collisions and offsets. Only in developer mode.

user_color_gui_r/g/b, user_color_text_r/g/b

Text color definitions in RGB bytes. Used in game definition script.

user_developer Toggles developer mode on with value 1. Command line only. When toggled on you can access the level editor through the main menu and in-game editor shortcuts are enabled. Game can't be saved and achievements can't be unlocked while developer mode is on.

user_game Defines the game mod to be loaded. Command line only. Mods are loaded from ”mods” directory.

user_fps Toggles frames-per-second display (1=on). Amount of rendered frames-per-second will be shown at the top-right corner of the screen. Only in developer mode.

user_fx_spark Defines the entities called from within the engine. Used in game definition script.

user_info Game info and copyright string for start-up loading screen. Used in game definition script.

user_lobotomy Disables all AI making testing level geometry and trigger functions easier (1=on ; 0=off). Only in developer mode.

user_log Toggles detailed developer log output on/off (1=detailed ; 0=basic, default). While basic mode reports only the main engine events (initialization calls, errors occurred, etc.) the detailed mode also reports most file events. Detailed mode is mainly intended for bug-hunting and development.

user_mapdir Defines the level directory for mod (default is ”data/script/maps”). This way you can make mods that can be used in TAGAP's original maps. Used in game definition script.

user_promo Enables promo screen capture mode on/off (1=disable GUIs ; 2=disable player and AI ; 0=off). When toggled on, no status display, messages or player effects will be drawn, making it easier to take environmental screenshots or capture demo reel video. Command line only.

user_seq_start, user_seq_gameover, user_seq_newgame

Filename definitions for sequences automatically loaded by the engine on specific events. Used in game definition script.

user_sfx_master Master volume for sound effects in percents (default is 75). Use this to tune the default balance of music and sound effects according to what kind of custom music you are using. Used in game definition script.

user_soundcpu Toggles sound engine's CPU usage display (1=on). This variable was meant for system testing and debugging during the engine development, but it also works fine to determine possible glitches created by sound overflows. Only in developer mode.

user_startsave Toggles whether or not the current level will be saved automatically when you launch it from the

[ 33 / 37 ]

Page 34: TAGAP: The Developer's Handbook

editor. Saved in configuration file.

user_tex_base, user_tex_crack

Filename of the texture definitions for base textures used by editor and rendering engine. Used in game definition script.

user_vo_ex, user_vo_neg, user_vo_pos

Voiceovers (see: VOICEOVER) for played in certain game events, like when discovering a secret area, trying to use lock without a key, etc. They are as follows; “user_vo_ex” is excited, “user_vo_neg” is negative feedback and “user_vo_pos” is positive feedback. Used in game definition script.

[ 34 / 37 ]

Page 35: TAGAP: The Developer's Handbook

Appendix D: Essential Software

Retail softwareLet's face it; You'll need to buy some software if you want to get your game done. It's simply an undeniable fact that some software suites, like Adobe Photoshop or Cakewalk Sonar, have been tuned to tiniest detail in terms of user interface, compatibility and efficiency, and though they cost some money, they'll eventually pay themselves in development speed and reliability.

www.adobe.com/photoshop

Adobe Photoshop CS3The one and only graphics software and the best 800€ I've ever spent. Unequaled on every level, Adobe Photoshop has been created to answer all the needs of 2D artist of both pro and amateurs alike. You might need Photoshop 7.0 legacy file plug-ins for best Targa TGA handling, though. Note that Photoshop CS series is not to be confused with Adobe Photoshop Elements line-up, which is budget solution for photo processing and can't be used to create CGI from scratch.

www.adobe.com/premiereel

Adobe Premiere ElementsVery likely the best non-linear video editing software around. Unlike with Adobe's Photoshop, in case of Premiere I found Elements version better than the full product; Elements is slicker, faster and a lot easier to use. Besides costing around 80€ it won't bankrupt you either.

www.fraps.com

FrapsWhen it came time to capture the footage for TAGAP trailer, I had two choices; Buy an expensive video capture card or go and buy beepa's Fraps for 27€. Though it's best known for it's video- and screen capturing capabilities as well as it's support for Machinima community, it's also a benchmarking gadget that can come handy in game development.

www.cakewalk.com

Cakewalk Sonar Home Studio XLIn the beginning TAGAP's music was written as MIDI, recorded into audio tracks, hammered with wave editor, put together and encoded to Ogg Vorbis. Not-so-surprisingly we soon started looking for an alternative and Cakewalk Sonar had it all in one; Composition, arrangement, recording, encoding... heck, even web publishing!

Freeware softwareThese days it's common belief that game development is too expensive for hobbyists unless you do warez. Wrong! It's relatively cheap, as there are many freeware and/or open source tools out there. Here are the of most useful freeware programs Penguin DT used to craft TAGAP.

www.towofu.net

@Icon SushiSimple and effective utility for creating Windows icons. It supports anything from old 8 bit icons to 32 bit XP and hi-res Vista ones, supporting images sized from 1x1 to 256x256. @Icon also flawlessly supports wide range of modern formats.

[ 35 / 37 ]

Page 36: TAGAP: The Developer's Handbook

audacity.sourceforge.net

AudacityFree, cross-platform sound editor that simply beats the crap out of it's commercial competitors, featuring much-needed options like multi-track editing and project workspace feature. You can do a lot with it out-of-the-zip, but the ability to customize it with all the available plug-ins ensures only your imagination is the limit. Or your hard disk space.

www.fmod.org

FMOD Ex: Music & Sound Effects SystemFMOD definitely deserves to get mentioned. The brilliance of FMOD lays in it's flexibility; With it you can do anything from just playing mono sample to complex hardware-supporting 3D soundscapes. On commercial front it's been used in titles like World of WarCraft and Crysis, so it's heavy league. It's free for use in freeware titles and there's also affordable hobbyist license option.

www.gimp.org

GIMP: GNU Image Manipulation ProgramThough Adobe Photoshop is the definite king of 2D graphics software, GIMP has proven itself handy in smaller graphics tasks, like in creating texture patterns. It's very flexible, though requires time to get into, thanks to it's... er... funky interface. It's also available on every possible platform.

www.jedit.org

jEdit: Programmer's Text EditorLife-saver tool and like the name says, designed for programming. It recognizes most programming language syntaxes and it's quit fast, but the best part is it's find-and-replace capability; Just type in the changes and it does it all for you, even in thousands of files. Though I like standard Notepad-alike software better, all large-scale script updating was done with jEdit. Requires Java 2 virtual machine to install and run.

msdn.microsoft.com

Microsoft Visual C++ 2005 Express EditionMicrosoft in freeware list? Yes, as Microsoft fanboy I love surprising you skeptics! Simply put; The “One-And-Only Programming Tool” as free lite version. Sure, there are some features missing compared to retail editions, but nothing hobbyist can't live without. One of those very few developer tools I've ever encountered from which I have nothing bad to say. It's just perfect. Get your's NOW!

nsis.sourceforge.net

NSIS: Nullsoft Scriptable Install SystemOpen source install system that was used to create TAGAP installer. It's from Nullsoft, developers of famous WinAmp and it's widely used. Distributing your software in installer package makes things way more user-friendly. It speaks of something that NSIS has been adapted by likes of Ubisoft, NCsoft and Google.

www.vorbis.com

OggDropAnother small utility redefining the phrase “less is more”. Just drag your audio files and drop 'em to OggDrop – and you have the entire game soundtrack and/or sound effects archive encoded to OGG Vorbis format in a matter of seconds. Why make it harder?

[ 36 / 37 ]

Page 37: TAGAP: The Developer's Handbook

www.openoffice.org

OpenOffice.orgOpen source alternative and replacement for Office suite. Though OpenOffice.org Writer requires more orientation than Word, it's more powerful, supports greater array of formats and can produce fluent .pdf and .html files. Writer was used to create all TAGAP's documentations, including this handbook you are just reading.

www.gena01.com/win32pad

Win32PadThere are dozens of Notepad replacements out there, but I think this is the best one. It features Infinite undo, unlimited file size, yet it's light-weight and doesn't waste any extra memory. This gadget was used for both TAGAP_Script creation and website composition (yes, I'm one those dozen people who still do their websites with text editor).

[ 37 / 37 ]