The Jetpack 2 Level Editor is a very powerful tool, allowing you to easily create anything from a simple puzzle, to a detailed story with journal entries, to an imaginative maze with moving Tile Groups and custom scripting. The Level Editor is lots of fun, and takes only a short time to master.
Getting to Know the Editor
Drawing Your Level
Playtesting!
Advanced Editing Tools
Tile Groups
Level Settings
Ini Config File
Ini Config: Text Blocks
Ini Config: Scripting
Tile Triggers
Tips for Designing the Best Levels
Getting to Know the Editor
Press
TAB
to activate the Level Browser. Check out the shared folders, where you can see what other people are building. Load a level to explore the inner details of different level designs.When you're ready to build your own level, press
SHIFT+N
to create a new level. The Level Settings dialog will appear, with many settings for configuring your level. Right now, the only ones that need your attention are Title and Background. After you name your level, pressESCAPE
to exit and begin designing your level.You can save your level at any time by pressing
SHIFT+S
Keyboard Shortcuts
TAB
: Level Browser - Browse your levels, and other user-created levelsSHIFT+N
: New levelSHIFT+S
: Save levelSHIFT+L
: Level settingsSHIFT+A
: Advanced Scripting / Ini ConfigDrawing Your Level
Select a Tile
Select a tile with the Tile Picker (SPACE
), or grab a tile withZ
or by holdingSPACE
.0-8
: Switch layers. Each layer remembers its last used tile.< , >
: Rotate/cycle tile alternatesJDGIFBLTS
: Quick-select certain tilesPAGE UP/DOWN
: Change tile themeBACKSPACE
: Put away the tile (stop drawing)Drawing
While holding a tile,drag the mouse
to draw with the current tileHold SHIFT + click
: Place the tile on the free-range layer instead of the tile's normal layerHold CTRL + drag
: Delete tilesPlaytesting!
TIP: Temporarily move Jetman's starting location to test different parts of your level
Keyboard Shortcuts
ENTER
: Playtest your levelSHIFT+ESCAPE
: Quit back to editorF2
: Live edit mode+ / -
: Change game speedCheat Keys
Cheating can be essential when testing difficult parts of your level.(you may substitute
SEMICOLON
forHOME
)HOME+INSERT
: Open/close doorHOME+DELETE
: SuicideHOME+F
: Fill fuel tanksHOME+I
: Invincible JetmanAdvanced Editing Tools
Select a Rectangular Area
While not holding a tile,drag the mouse
.SHIFT+X
: Cut,SHIFT+C
: Copy,SHIFT+V
: PasteDELETE
: Delete the selectionSHIFT+F
: Fill with the current tileSHIFT + 0-8
: Hide/filter layers\ (backslash) + A-Z
: Toggle Tile GroupNote: In paste mode, Fill & Delete apply to the clipboard.
Hiding Layers
It's easier to see background layers if you hide foreground layers - especially if you are using the opaque layer to conceal parts of your level.Hold 0-8
: View only a layer or combination of layers.Hold SHIFT
while releasing the numbers to lockSpecial Tools
SHIFT+T
: Convert level to the current themeSHIFT+ARROWS
: Shift tiles (with wrap)Note: In paste mode, these apply to the clipboard. Some commands don't work in live edit mode.
SHIFT+I
: Import a .JET fileSHIFT+E
: Export to .JET fileTile Groups
Assigning Tile Groups
Every tile in your level can by a member of any number of groups. When Tile Groups are visible, each tile is overlayed with its group letters.\ (backslash) or Eszett
: View Tile GroupsWhile viewing:
\ (backslash) + A-Z
: Toggle Tile GroupTile Group Effect Editor
SHIFT+G
: Edit Tile Group effectsWhile you edit the group's effect, a preview of the effect is shown.
You may also assign tile groups to tiles from this dialog.
Tile Group Settings
name
: For your own reference. Spaces are not allowed.triggerRange=#
: In tiles. Only applies to trigger "proximity". The maximum range is 5 tiles.globalSound=$id
: The sound played when the group activates. The sound has no position. See list at Scripting/playSound.Triggers
atStart
: Run when the level startsproximity
: Run when the player enters a certain range of any tile in the groupproximityStop
: (requires "proximity") Stops when the player leaves the proximity of the grouptriggerRestarts
: Re-triggering the group restarts it from the beginningonceOnly
: The group can only be run onceautoReverse
: When the group is triggered OFF, it first reverses to the beginning, then stops. Does not apply to scripts.Effects
To run a script as a group's effect, use[when $groupName]
. Scripts are not reversible.create
: Create the tiles in the group, if they don't already exist at their starting locations.destroy
: Destroy the tiles in the group. If "duration" is set, uses a fade out effect first.fadeIn
: Changes the opacity of the tiles to make them visible.fadeOut
: Changes the opacity of the tiles to make them disappear. Use with the opaque layer to reveal hidden rooms.moveLine
: Move the group in a lineangle=#
: The direction to move, in degrees. 0=right, 90=down.distance=#
: The distance to move, in tilesmoveEllipse
: Move the group in a circle or ovalcenter=x,y
: The center point, in tilestrack=x,y
: Rotate a single tracking point instead of each tile. Maintain's the group's shape.axisRatio=#
: Adjust the shape. 1=circle.makeDynamic
: Make static tiles like bricks, become movable and affected by gravityrandomPush=#
: Increase the spread of the objects by giving them a pushphase
: Phase out the phaseable tiles in the groupGeneral Effect Settings
duration=$seconds
: How long the effect lasts before stopping or reversingoptions=$options
: reversed, pingPongeasing=$type
: none, slow-fast, fast-slow, slow-fast-slow, fast-slow-fast, endBounceiterations=#
: How many times the effect repeats. To reset the counter, use triggerRestartsEffect Options
reversed
: Forward & reverse are swapped. Ignored by scripts.pingPong
: When the effect ends, it will reverse to the beginning. This counts as 2 iterations.Level Settings
Achievements
Achievements enhance gameplay by giving players extra goals. In Jetpack 2 this is especially useful: achievements are used to give expert players a run for their money, while beginners are still able to beat the level. Try to make your achievements clever, and tricky.Par & Master Times
The Par & Master Times are another kind of achievement, to make the game more challenging for experts.To beat these times, a player must collect all the treasure AND the idol before making it out the exit door. Make sure to include these when measuring your level's times.
Par Time
: An average player should be able to beat this time after a few tries.Master Time
: An expert player must navigate the level almost perfectly to beat this time.TIP: You MUST include getting all the treasure AND the idol when measuring Par & Master Times!
Other Settings
Reset on Death
: Normally, when the player dies, the world continues to run. This setting forces the world to reset on death. Certain designs may need this to prevent the player from entering an unwinnable scenario. Avoid using this setting unless absolutely necessary.Disable Stains
: Smoke and blood stains may look good on the walls, but if your level has any "open air" spaces where there is no back wall, they look odd. Use this setting to disable them.Ini Config File
TIP: Case matters - camelCase is recommended
Settings Sections
[group $letter:$name]
: Tile Group settings[groupEffect $letter:$type]
: Tile Group effect settingsTile Groups
Advanced users may find it more convenient to edit Tile Groups in the Ini Config file rather than the dialog. This makes editing faster, and allows for copying group settings to other levels. Note: the dialog edits only the first groupEffect for each group.See Tile Groups for details.
Example
[group A:movingPlatform]
triggers=atStart
[groupEffect A:moveEllipse]
duration=12
options=reversed
track=0,-3.5
axisRatio=1.5
triggers=atStart
[groupEffect A:moveEllipse]
duration=12
options=reversed
track=0,-3.5
axisRatio=1.5
Ini Config: Text Blocks
Text Sections
[editorNotes]
: Design goals & notes that should be respected during future editing[editorTodo]
: Remaining "to do" list for completing the level[msg $trigger]
: Plain text[help $trigger]
: Markup for a help popup[journal $trigger]
: Markup for a journal entry. Journal entries are only added once, no matter how many times they are triggered.Triggers
See "Scripting/Triggers" for information on triggers.Markup
In markup, newlines and extra space are ignored. To add a newline, use \nFlexibility is limited - it's advised to stick to the format of the examples
Available Markup Tokens
<%set $varNames=$values%>
: Set variables & dialog overrides<%panel%>
text<%endPanel%>
: A rectangular area<%image $imageId id=$id%>
: An image. The id affects the style.Expert use only:
<%define $varName%>
text<%endDefine%>
: Capture text in a variable<%textRules id=$id spanclass=$class%>
: Set the id of the text element / wrap the text in a <span><%endText%>
: End a textRules block, also serves as a forced newlineAvailable CSS Classes
jrnSmall, help-header, help-center, help-secondary, help-centerSec, help-bold, help-small, help-more, help-footer
Available Images
$keyLayoutImage, IMG_exitDoor, IMG_idol
Available showGraphic
uiBigArrow_help, uiBigArrow_statusBox, uiBigArrow_fuelTank, uiBigArrow_achv, uiBigArrow_timer
Available Journal Images
IMG_journal_jetpack, IMG_journal_teleporter, IMG_journal_checkpoint, IMG_journal_gem, IMG_journal_idol, IMG_journal_spring, IMG_journal_trackbot, IMG_journal_talisman, IMG_journal_phaser, IMG_journal_switch, IMG_journal_computer
Examples
Storing sign text in the Ini Config
Give the sign tile a trigger ID:@mulberryBush@
Ini Config:
[msg mulberryBush]
Here we go round
the mulberry bush
Here we go round
the mulberry bush
Journal entry embedded in a level
[journal autoInit]
Welcome to my level
<%panel id=iconArea%><%image IMG_journal_gem id=journalIcon%><%textRules spanClass=jrnSmall%>
These gems may hold the key to escape.
<%endPanel%>
Welcome to my level
<%panel id=iconArea%><%image IMG_journal_gem id=journalIcon%><%textRules spanClass=jrnSmall%>
These gems may hold the key to escape.
<%endPanel%>
Simple popup
[help simpleHelp]
<span class='help-center'>Here's some help text.\nAnd some more.</span>
<span class='help-center'>Here's some help text.\nAnd some more.</span>
Advanced popup
[help advancedHelp]
<%set title="Advanced Help Box" showGraphic=uiBigArrow_fuelTank moreLink="More Info ..."%>
<span class='help-center'>There's an arrow pointing at the player's fuel.</span>
<span class='help-centerSec'>Here's a picture of a door.</span>\n
<%image IMG_exitDoor%>
<%define moreContent%>
<span class='help-header'>More Info</span>\n
Press <span class='key'>MINUS</span> to slow down
<%endDefine%>
<%set title="Advanced Help Box" showGraphic=uiBigArrow_fuelTank moreLink="More Info ..."%>
<span class='help-center'>There's an arrow pointing at the player's fuel.</span>
<span class='help-centerSec'>Here's a picture of a door.</span>\n
<%image IMG_exitDoor%>
<%define moreContent%>
<span class='help-header'>More Info</span>\n
Press <span class='key'>MINUS</span> to slow down
<%endDefine%>
Ini Config: Scripting
TIP: Case matters - camelCase is recommended
Script Sections
Each section is it's own self-contained script.[when $trigger $settings]
: Runs when trigger is set ON[whenOff $trigger $settings]
: Runs when trigger is set OFFTriggers
A trigger can be a simple true/false condition that you name and trigger manually, like "heHitTheSwitch". There are also several automatic triggers.TIP: To avoid confusion, it's recommended to avoid using the same names for triggers & tile groups.
Automatic Triggers
[when autoInit]
: The level is starting for the first time, or restarting[when autoReady]
: The level is ready to play, any intro transition is complete. Also runs after respawn.[when autoAction]
: The action has started. Also runs after respawn.[when autoEachTreasure]
: The player got a treasure.[when autoEachGem]
: The player got a gem.[when autoAllGems]
: The player got all the gems. This can reverse on death (perfectionist).[when autoVictory]
: The player completed the level[when autoDeath]
: The player died[when switch:$color]
: A switch was toggled (blue, red, cyan, or silver)[when $groupName]
: A Tile Group was toggledAchievement Triggers
Be aware that these are reversible, and some start already on.achvTreasure
,achvIdol
,achvTalisman
,achvEarthDay
,achvFuelMiser
,achvOutOfPhase
,achvRestYourLegs
,achvTheMcCoy
,achvSuperstitious
,achvSwitchophobe
,achvNinja
,achvUntouchable
,achvTheTrapper
,achvFoolsGold
Trigger Settings
pauseOnToggle
: When the trigger toggles, pause the script.stopOnToggle
: When the trigger toggles, terminate the script.triggerBind
: The script is bound to the thing that triggered it. Allows multiple copies to run at once.Targets
Syntax:target $type
Target Types
target player
: Target the playertarget trigger
: Target the object that triggered the scripttarget group=$ids
: Target all the tiles in group(s)target type=$ids
: Target all tiles of certain type(s)Jetman, Trackbot, Knight, SteelBall, EyeBall, Peppermint, Bat, BatBot, Flitzer, Missile, Seeker, SpikeWheel, Spring, exitDoor, gem, gem:gone, treasure:coin, treasure:pile, treasure:vase, idol, talisman
target world
: Target the world environmenttarget camera
: Target the viewport cameraTargetless Commands
wait
: Wait for any "slide" commands to completewait $seconds
: Pause script execution. (This could result in multiple copies of the script running at once.)tick
: Defer execution until the text game tickrepeat @_marker_
: Loop back on the next tick. If @_marker_ is not set, loops back to start.(total=$total OR time=$seconds)
: Repeat $total times or for $seconds seconds.@_marker_
: A position marker used for loopinguse $var=$value
: Set the default values to use with future commands: speed, time, easingtrigger $trigger
: Trigger other Ini Config sections matching $triggermsg $text
: Display message $text in the notice window. Raw text must be "quoted".runGroup $ids
: Activate Tile GroupstopGroup $ids
: Deactivate Tile GroupresetGroup $ids
: Reset Tile GrouptoggleGroup $ids
: Toggle Tile Groupswitch $color=$action
: Activate a switch (blue, red, cyan, or silver). Actions: toggle (default), on, off.globalSound $id
: Play a sound that has no position.stopSound
: Stop the current sound.Targeted Commands
Note "+=2" means add 2 to the current value. Also available: -=, *=, /=set $prop=$value $prop+=$value
: Set the targets' propertiesrandom=$rand
: Multiply each value by a random number from 0-$rand before applyingreset $prop $prop
: Reset changes to the targets' properties. Does not apply to: x, y, angle, fuel.slide time=$seconds $prop=$value
: Gradually change the targets' propertieseasing=$type
: none, slow-fast, fast-slow, slow-fast-slow, fast-slow-fast, endBounceslide (time=$seconds OR speed=$speed) x=$value y=$value
: Using slide to apply motion.curve=$value
: Curve: 0=none, 1=circle, -1=reverse circledestroy
: Destroy the targetplaySound $id
: Play a sound at the target's position: boom, crate, glass, electro, powerup, treasure, idol, achv, notice, warning, retroBuzz, retroLaugh, futureDoor, switchOn, switchOff, switchOnOff, grind, elevatorTarget Properties
These values are ratios unless otherwise noted: "1" represents the full default value. (To reset a value, use the "reset" command, not a number)all entities
: x (tiles), y (tiles), angle (radians), velX, velY, velAngle, gravity, immobile / visuals: opacity, rotation (radians), scale, blendMode (string)Jetman
: runAccel, runSpeed, climbAccel, climbSpeedX, climbSpeedY, driftAccel, driftSpeed, jumpUpSlam, jumpSideSlam, jetpackThrust, fuel=0-1, hasPhaseShifter=0/1, forceJump=1, forceJetpack=1, invincible=1Trackbot / Knight
: runAccel, runSpeed, climbAccel, climbSpeedX, climbSpeedY, driftAccel, driftSpeed, targetTrackRadiusBat
: accel, speedBatBot
: accel, speedFlitzer
: accel, aiTurnChance, aiReverseChance, aiSkipCycles=#Missile
: accel, speed, sideAccelSeeker
: speed, orbitGravity, orbitAccelSpikeWheel
: accel, speedSpring
: accel, upSpeed, downSpeedSteelBall / EyeBall / Peppermint
: speedWorld
: gravityCamera
: shake=#tilesExit Door
: state=opening/closingSpear
: state=fireAlarm
: state=on/off/silentExamples
Start the game with the red switch off, then toggle it every 3.5 seconds
[when autoInit]
switch red=off
wait 3.5
switch red
repeat line=2
switch red=off
wait 3.5
switch red
repeat line=2
Give the player super jump ability, only while holding the talisman
[when achvTalisman]
target player
set invincible=1
msg "You are now invincible!"
[whenOff achvTalisman]
target player
reset invincible
msg "You are now mortal."
target player
set invincible=1
msg "You are now invincible!"
[whenOff achvTalisman]
target player
reset invincible
msg "You are now mortal."
Tile Triggers
Activation
Tiles activated by player touch: textSign, invisibleTrigger, journalIcon, helpIconTiles activated by any touch: triggerTouchSwitch
Tiles activated by player use: triggerSwitch
Note: Contacts existing at level start do not activate triggers.
Syntax
optional text to display @_triggerId_/_setting_/_setting_@
@_triggerId_/_setting_/_setting_@
: Triggers Ini Config sections matching _triggerId_. _setting_ is optional.TIP: If the triggerId matches a tile group name, that group will also be activated.
Settings
Trigger Type
(none/default): Each activation triggers ONoff
: Each activation triggers OFFtoggle
: First activation triggers ON / Next activation triggers OFF / repeatheld
: Activation triggers ON / Deactivation triggers OFFTrigger Source
This only applies to touch switches and invisible triggers.(none/default): invisible triggers=
player
/ touch switches=all
player
: The player triggers thisentity
: Entities trigger this (enemies)solid
: Moving blocks trigger thisall
: All of the aboveOther
limit=#
: Limit number of times tile can be triggereddestroy
: Destroy when limit reached (if no limit, destroy on activation)Examples
An invisible trigger that activates a Tile Group only while it is touched
The platform is moving... @movePlatform/held@
Ini Config:
[when movePlatform]
runGroup movingPlatform
runGroup movingPlatform
A switch that toggles super jump ability
Press to toggle super jump! @setSuperJump/toggle@
Ini Config:
[when setSuperJump]
target player
set jumpUpSlam=2.0
msg "SuperJump on"
[whenOff setSuperJump]
target player
reset jumpUpSlam
msg "SuperJump off"
target player
set jumpUpSlam=2.0
msg "SuperJump on"
[whenOff setSuperJump]
target player
reset jumpUpSlam
msg "SuperJump off"
Tips for Designing the Best Levels
General Tips
- A great way to learn is by finding an existing level that you like, and modifying it.
- Make your level beatable by all skill levels, saving the most difficult parts for achievements.
Uniqueness
What makes your level stand out from the rest? Here are some ideas.- Find a fun way to implement one or many of these gameplay elements: Action, Puzzle, Adventure, & Strategy
- Use Tile Groups in unexpected ways to surprise the player
- Explore the many unique ways to use custom scripting to violate typical game rules
Appearance
Decide on the look of your level before starting. Will you use heavy symmetry, a curvy flow, or random sections? An open feel, tight corridors, or partitioned rooms? Let the underlying design guide your visual choices.- Add scenery as a last step, after you complete the underlying design
- Be careful when mixing tile themes, to avoid a sloppy look
Achievements
For the best player experience, try to make sure your level has all the available achievements.- Each level needs 1 idol & some treasure, all gettable (this is an achievement)
- Set par & master times - both MUST include getting all treasure + the idol (no other achievements)
- Set 3 custom achievements for your level
I hope you enjoy using the Jetpack 2 Level Editor. I can't wait to see what you come up with!
- Adam Pedersen