Copyright (C)2001,2002 by Eric Sunshine <sunshine@sunshineco.com>
Copyright (C)1997 by Paul McCarthy <zarnuk@high-speed-software.com>

FILE_SYNTAX.txt

Syntax for the files used by SokoSave.

File Types
    Sokoban puzzle files: *.sokomaze  *.xsb
    Hexoban puzzle files: *.sokohex   *.hsb
    Triboan puzzle files: *.sokotri   *.tsb
    Save Files: *.sokosave
    Score File: SCORES


===============================================================================
PUZZLE FILE SYNTAX
-------------------------------------------------------------------------------
Puzzles are text files containing a simple 2-dimensional map of ASCII
characters.

'#'  0x23  Wall.
' '  0x20  Plain empty square.
'.'  0x2e  Empty goal square.
'$'  0x24  Crate on an empty square.
'*'  0x2a  Crate on a goal square.
'@'  0x40  Player on an empty square.
'+'  0x2b  Player on a goal square.

There must be exactly one player on the map.  The map must be "closed" -- it
must have walls enclosing the playing area.  It should be solvable, but the
program does not know how to verify that.

In classic square-tiled Sokoban puzzles, each cell should contain a valid
puzzle token.

Example: 01.sokomaze
    #####
    #   #
    #$  #
  ###  $##
  #  $ $ #
### # ## #   ######
#   # ## #####  ..#
# $  $          ..#
##### ### #@##  ..#
    #     #########
    #######

In hexagonal-tiled puzzles, tokens should appear in even numbered columns on
even rows, and in odd columns on odd rows.  Row and column numbers begin at
one, in the upper-left corner.  The even-on-even / odd-on-odd convention allows
the textual representation of the puzzle to take on the same staggered
appearance as the rendered puzzle.  SokoSave is also able to deal gracefully
with puzzles which employ the inverse even-on-odd / odd-on-even layout, but
other Sokoban implementations may not, so it is best to stick with the
conventional even-on-even / odd-on-odd layout.

Example: dws001.hsb (by David W. Skinner <sasquatch@bentonrea.com>)
    # # #
   #     #
    #     #
   #   . #
  #   .   #
 #   $ $   #
  # # # *   #
     # @   #
      # # #

In triangular-tiled puzzles, the first column of the first row represents a
south-pointing triangle; the second column a north-pointing triangle; etc.  The
first column of the second row represents a north-pointing triangle; the second
column, a south-pointing triangle, etc.

Example: tryoban003.tsb (by Francois Marques <sokoban@free.fr>)
       #######
      ##     ##
     ##  *@*  ##
     ##  ***  ##  
   ######   ######
  ##   #     #   ##
 ##  *.*$   $*.*  ##
 ## $**. ### .**$ ##
  ##     ###     ##
   ####### #######

Any line which begins with a non-puzzle characters, optionally preceded by
whitespace, is considered meta-data.  Meta-data is typically composed of
comments or informational text inserted by the puzzle's author.

Puzzle files may contain any meta-data, though SokoSave takes special note of
the following "pragmas".

    Pragma: no-high-score
    Pragma: no-auto-save
    Pragma: no-auto-advance

These pragmas, which may be of special interest to puzzle authors, inhibit
behaviors which are typically inappropriate or annoying during the iterative
puzzle design-test cycle.  no-high-score prevents the "New Score" panel from
launching.  no-auto-save prevents the game from being saved automatically when
solved.  no-auto-advance inhibits advancement of the user's "highest level"
setting.

Puzzle authors may wish to insert these pragmas into the puzzle file at design
time, and remove them once the design has been finalized.  For example:

Author: David W. Skinner <sasquatch@bentonrea.com>
Level: Microban 44
Name: Duh!
Pragma: no-high-score
Pragma: no-auto-save
Pragma: no-auto-advance
#####
#@$.#
#####


===============================================================================
SAVE FILE SYNTAX
-------------------------------------------------------------------------------
Save files are printable ASCII text files.  The current save file version
number is 2.

Save files contain a simple encoding of the player's movement history.  The
history is encoded as follows:

Direction  Move  Push
Up         u     U
Left       l     L
Right      r     R
Down       d     D
North      n     N
South      s     S

North and South only have meaning for hexagonal-tiled puzzles.  For such
puzzles, Up means up-and-left, North means up-and-right, Down mean
down-and-right, and South means down-and-left.

The puzzle itself is stored in its current state at save time.  The puzzle is
encoded using the following characters:

'#'  0x23  Wall.
' '  0x20  Plain empty square.
'.'  0x2e  Empty goal square.
'$'  0x24  Crate on an empty square.
'*'  0x2a  Crate on a goal square.
'@'  0x40  Player on an empty square.
'+'  0x2b  Player on a goal square.

The puzzle's style is recorded as either "square", "hexagon", or "triangle".
The meta-data from the original puzzle file is reproduced in the save file
following the puzzle data.

The recorded "best" scores are the best individual scores yet achieved for this
game.  These scores only make sense individually -- never as a group -- and are
used in an administrative capacity by SokoSave to determine if a new entry
should be recorded in the score file.  They are not intended for human
consumption.

The complete version 2 file layout is as follows.

<version:int>
<puzzle-filename:string>
<style:string>
<history-len:int> <history-pos:int>
<history:string>
<best-#-moves:int> <best-#-pushes:int> <best-#-runs:int> <best-#-focus:int>
<puzzle-row-1:string>
<puzzle-row-2:string>
<puzzle-row-3:string>
...
<meta-data:string>
<meta-data:string>
...

Example:
2
$(SokoSave)/puzzle/01.sokomaze
square
33 33
ullluuuLUllDlldddrRRRRRRRRRRRRurD
0 0 0 0
    #####          
    #   #          
    #$ $#          
  ###   ##         
  #   $  #         
### #$## #   ######
#   # ## #####  ..#
# $             .+#
##### ### # ##  .*#
    #     #########
    #######        
Author: Hiroyuki Imabayashi

Version 1 save files are similar to version 2 save files, with the following
exceptions:

- They represent only classic square-tiled puzzles.
- The puzzle style is not stored since all version 1 puzzles are square.
- The amount of memory allocated for the history is stored.  This is an
  implementation detail which is of no consequence to the actual saved game,
  thus it was dropped for version 2.
- A simple run-length-encoding (RLE) scheme is used to compress the history and
  the stored puzzle representation.  Two or more successive instances of the
  same character are replaced by an integer count (in printable ASCII decimal
  characters) followed by a single instance of the character.
- Only "best" moves and pushes are recorded.  Version 2 and later store
  additional "best" scores.
- The scores at the current history position are stored.  In version 2 and
  later, the scores are instead computed directly from the history.
- The puzzle dimensions are stored.  In version 2 and later, the puzzle
  dimensions are computed from the saved puzzle data.
- Unreachable empty squares surrounding the puzzle (and those enclosed by the
  puzzle) are represented as walls rather than empty space.
- Meta-data is not stored.
- The saved puzzle is encoded using the following characters rather than the
  normal puzzle characters used by version 2 and later.

'H'  0x48  Wall.
'@'  0x40  Plain empty square.
'A'  0x41  Empty goal square.
'D'  0x44  Crate on an empty square.
'E'  0x45  Crate on a goal square.
'B'  0x42  Player on an empty square.
'C'  0x43  Player on a goal square.

The complete version 1 file layout is as follows.

<version:int>
<puzzle-filename:string>
<history-max:int> <history-len:int> <history-pos:int>
<rle-history:string>
<best-#-moves:int> <best-#-pushes:int>
<#-moves:int> <#-pushes:int>
<puzzle-height:int> <puzzle-width:int>
<rle-puzzle-row-1:string>
<rle-puzzle-row-2:string>
<rle-puzzle-row-3:string>
...

Example:
1
$(SokoSave)/puzzle/01.sokomaze
1024 33 33
u3l3uLU2lD2l3dr12RurD
0 0
33 16
11 19
19H
5H3@11H
5HD@D11H
5H3@11H
3H3@D2@10H
3H@HD2H@10H
H3@H@2H@5H2@2AH
H@D13@ACH
5H@3H@H@2H2@AEH
5H5@9H
19H


===============================================================================
SCORE FILE SYNTAX
-------------------------------------------------------------------------------
The SCORES file is a text file containing one score per line.  The fields are
separated by a tab character.  There must not be any tabs nor newlines in any
of the fields.  Each line must be less than 2048 characters long.

Field  Name    Description
1      Puzzle  Base part of the puzzle filename; the directory and the file
               extension are excluded.
2      Moves   Unsigned positive integer number of moves.
3      Pushes  Unsigned positive integer number of pushes.
4      Date    Unsigned positive integer seconds since Unix Epoch.
5      Player  Player's name.
6      Notes   Player's notes.
7      Runs    Unsigned positive integer number of runs.
8      Focus   Unsigned positive integer number of focus changes.

Example:
01    246    97     1011561138    sunshine    Notes       23    13
02    521    139    1011561285    sunshine    Comments    58    17
...
