Some more sokoban changes from Sean Morrisey's FS #6702. (includes moving the default level file back to the previous filename)

git-svn-id: svn://svn.rockbox.org/rockbox/trunk@13738 a1c6a512-1295-4272-9138-f99709370657
This commit is contained in:
Antoine Cellerier 2007-06-29 19:52:13 +00:00
parent 4e7b760740
commit ec7252c96f
4 changed files with 195 additions and 92 deletions

View file

@ -33,8 +33,9 @@ extern const fb_data sokoban_tiles[];
#define SOKOBAN_TITLE "Sokoban" #define SOKOBAN_TITLE "Sokoban"
#define SOKOBAN_LEVELS_FILE PLUGIN_DIR "/sokobanlevels.sok" #define SOKOBAN_LEVELS_FILE PLUGIN_DIR "/sokoban.levels"
#define SOKOBAN_SAVE_FILE PLUGIN_DIR "/sokobansave.sok" #define SOKOBAN_SAVE_FILE PLUGIN_DIR "/sokoban.save"
#define SOKOBAN_SAVE_FOLDER "/games"
/* Magnify is the number of pixels for each block. /* Magnify is the number of pixels for each block.
* Set dynamically so all targets can support levels * Set dynamically so all targets can support levels
@ -112,6 +113,7 @@ extern const fb_data sokoban_tiles[];
#define SOKOBAN_LEVEL_DOWN BUTTON_F1 #define SOKOBAN_LEVEL_DOWN BUTTON_F1
#define SOKOBAN_LEVEL_REPEAT BUTTON_F2 #define SOKOBAN_LEVEL_REPEAT BUTTON_F2
#define SOKOBAN_LEVEL_UP BUTTON_F3 #define SOKOBAN_LEVEL_UP BUTTON_F3
#define SOKOBAN_PAUSE BUTTON_PLAY
#define BUTTON_SAVE BUTTON_ON #define BUTTON_SAVE BUTTON_ON
#define BUTTON_SAVE_NAME "ON" #define BUTTON_SAVE_NAME "ON"
@ -125,6 +127,7 @@ extern const fb_data sokoban_tiles[];
#define SOKOBAN_LEVEL_DOWN (BUTTON_MENU | BUTTON_LEFT) #define SOKOBAN_LEVEL_DOWN (BUTTON_MENU | BUTTON_LEFT)
#define SOKOBAN_LEVEL_REPEAT (BUTTON_MENU | BUTTON_UP) #define SOKOBAN_LEVEL_REPEAT (BUTTON_MENU | BUTTON_UP)
#define SOKOBAN_LEVEL_UP (BUTTON_MENU | BUTTON_RIGHT) #define SOKOBAN_LEVEL_UP (BUTTON_MENU | BUTTON_RIGHT)
#define SOKOBAN_PAUSE BUTTON_MENU
#define BUTTON_SAVE BUTTON_MENU #define BUTTON_SAVE BUTTON_MENU
#define BUTTON_SAVE_NAME "MENU" #define BUTTON_SAVE_NAME "MENU"
@ -138,10 +141,11 @@ extern const fb_data sokoban_tiles[];
#define SOKOBAN_LEVEL_DOWN (BUTTON_ON | BUTTON_DOWN) #define SOKOBAN_LEVEL_DOWN (BUTTON_ON | BUTTON_DOWN)
#define SOKOBAN_LEVEL_REPEAT BUTTON_ON #define SOKOBAN_LEVEL_REPEAT BUTTON_ON
#define SOKOBAN_LEVEL_UP (BUTTON_ON | BUTTON_UP) #define SOKOBAN_LEVEL_UP (BUTTON_ON | BUTTON_UP)
#define SOKOBAN_PAUSE BUTTON_ON
#define BUTTON_SAVE BUTTON_MODE #define BUTTON_SAVE BUTTON_MODE
#define BUTTON_SAVE_NAME "MODE" #define BUTTON_SAVE_NAME "MODE"
#define SOKOBAN_RC_QUIT BUTTON_RC_STOP #define SOKOBAN_RC_MENU BUTTON_RC_STOP
#elif (CONFIG_KEYPAD == IPOD_4G_PAD) || \ #elif (CONFIG_KEYPAD == IPOD_4G_PAD) || \
(CONFIG_KEYPAD == IPOD_3G_PAD) (CONFIG_KEYPAD == IPOD_3G_PAD)
@ -153,19 +157,21 @@ extern const fb_data sokoban_tiles[];
#define SOKOBAN_REDO (BUTTON_SELECT | BUTTON_PLAY) #define SOKOBAN_REDO (BUTTON_SELECT | BUTTON_PLAY)
#define SOKOBAN_LEVEL_DOWN (BUTTON_SELECT | BUTTON_LEFT) #define SOKOBAN_LEVEL_DOWN (BUTTON_SELECT | BUTTON_LEFT)
#define SOKOBAN_LEVEL_UP (BUTTON_SELECT | BUTTON_RIGHT) #define SOKOBAN_LEVEL_UP (BUTTON_SELECT | BUTTON_RIGHT)
#define SOKOBAN_PAUSE BUTTON_SELECT
#define BUTTON_SAVE BUTTON_SELECT #define BUTTON_SAVE BUTTON_SELECT
#define BUTTON_SAVE_NAME "SELECT" #define BUTTON_SAVE_NAME "SELECT"
/* FIXME: if/when simultaneous button presses work for X5, /* FIXME: if/when simultaneous button presses work for X5/M5,
* add redo & level repeat */ * add level up/down */
#elif CONFIG_KEYPAD == IAUDIO_X5M5_PAD #elif CONFIG_KEYPAD == IAUDIO_X5M5_PAD
#define SOKOBAN_UP BUTTON_UP #define SOKOBAN_UP BUTTON_UP
#define SOKOBAN_DOWN BUTTON_DOWN #define SOKOBAN_DOWN BUTTON_DOWN
#define SOKOBAN_MENU BUTTON_POWER #define SOKOBAN_MENU BUTTON_POWER
#define SOKOBAN_UNDO_PRE BUTTON_SELECT #define SOKOBAN_UNDO_PRE BUTTON_SELECT
#define SOKOBAN_UNDO (BUTTON_SELECT | BUTTON_REL) #define SOKOBAN_UNDO (BUTTON_SELECT | BUTTON_REL)
#define SOKOBAN_LEVEL_DOWN BUTTON_REC #define SOKOBAN_LEVEL_REPEAT BUTTON_REC
#define SOKOBAN_LEVEL_UP BUTTON_PLAY #define SOKOBAN_REDO BUTTON_PLAY
#define SOKOBAN_PAUSE BUTTON_PLAY
#define BUTTON_SAVE BUTTON_SELECT #define BUTTON_SAVE BUTTON_SELECT
#define BUTTON_SAVE_NAME "SELECT" #define BUTTON_SAVE_NAME "SELECT"
@ -179,6 +185,7 @@ extern const fb_data sokoban_tiles[];
#define SOKOBAN_LEVEL_DOWN (BUTTON_PLAY | BUTTON_SCROLL_DOWN) #define SOKOBAN_LEVEL_DOWN (BUTTON_PLAY | BUTTON_SCROLL_DOWN)
#define SOKOBAN_LEVEL_REPEAT (BUTTON_PLAY | BUTTON_RIGHT) #define SOKOBAN_LEVEL_REPEAT (BUTTON_PLAY | BUTTON_RIGHT)
#define SOKOBAN_LEVEL_UP (BUTTON_PLAY | BUTTON_SCROLL_UP) #define SOKOBAN_LEVEL_UP (BUTTON_PLAY | BUTTON_SCROLL_UP)
#define SOKOBAN_PAUSE BUTTON_PLAY
#define BUTTON_SAVE BUTTON_PLAY #define BUTTON_SAVE BUTTON_PLAY
#define BUTTON_SAVE_NAME "PLAY" #define BUTTON_SAVE_NAME "PLAY"
@ -191,6 +198,7 @@ extern const fb_data sokoban_tiles[];
#define SOKOBAN_LEVEL_DOWN BUTTON_VOL_DOWN #define SOKOBAN_LEVEL_DOWN BUTTON_VOL_DOWN
#define SOKOBAN_LEVEL_REPEAT BUTTON_MENU #define SOKOBAN_LEVEL_REPEAT BUTTON_MENU
#define SOKOBAN_LEVEL_UP BUTTON_VOL_UP #define SOKOBAN_LEVEL_UP BUTTON_VOL_UP
#define SOKOBAN_PAUSE BUTTON_SELECT
#define BUTTON_SAVE BUTTON_SELECT #define BUTTON_SAVE BUTTON_SELECT
#define BUTTON_SAVE_NAME "SELECT" #define BUTTON_SAVE_NAME "SELECT"
@ -204,6 +212,7 @@ extern const fb_data sokoban_tiles[];
#define SOKOBAN_LEVEL_DOWN (BUTTON_SELECT | BUTTON_DOWN) #define SOKOBAN_LEVEL_DOWN (BUTTON_SELECT | BUTTON_DOWN)
#define SOKOBAN_LEVEL_REPEAT (BUTTON_SELECT | BUTTON_RIGHT) #define SOKOBAN_LEVEL_REPEAT (BUTTON_SELECT | BUTTON_RIGHT)
#define SOKOBAN_LEVEL_UP (BUTTON_SELECT | BUTTON_UP) #define SOKOBAN_LEVEL_UP (BUTTON_SELECT | BUTTON_UP)
#define SOKOBAN_PAUSE BUTTON_SELECT
#define BUTTON_SAVE BUTTON_SELECT #define BUTTON_SAVE BUTTON_SELECT
#define BUTTON_SAVE_NAME "SELECT" #define BUTTON_SAVE_NAME "SELECT"
@ -218,7 +227,7 @@ extern const fb_data sokoban_tiles[];
/* Level data & stats */ /* Level data & stats */
struct LevelInfo { struct LevelInfo {
short index; /* Level index (level number - 1) */ int index; /* Level index (level number - 1) */
int moves; /* Moves & pushes for the stats */ int moves; /* Moves & pushes for the stats */
int pushes; int pushes;
short boxes_to_go; /* Number of unplaced boxes remaining in level */ short boxes_to_go; /* Number of unplaced boxes remaining in level */
@ -294,7 +303,7 @@ static void get_delta(char direction, short *d_r, short *d_c)
} }
} }
static void undo(void) static bool undo(void)
{ {
char undo; char undo;
short r, c; short r, c;
@ -304,7 +313,7 @@ static void undo(void)
/* If no more undos or we've wrapped all the way around, quit */ /* If no more undos or we've wrapped all the way around, quit */
if (undo_info.count == 0 || undo_info.current - 1 == undo_info.max) if (undo_info.count == 0 || undo_info.current - 1 == undo_info.max)
return; return false;
/* Move to previous undo in the list */ /* Move to previous undo in the list */
if (undo_info.current == 0 && undo_info.count > 1) if (undo_info.current == 0 && undo_info.count > 1)
@ -356,7 +365,7 @@ static void undo(void)
current_info.level.moves--; current_info.level.moves--;
return; return true;
} }
static void add_undo(char undo) static void add_undo(char undo)
@ -844,9 +853,22 @@ static void draw_level(void)
static bool save(char *filename, bool solution) static bool save(char *filename, bool solution)
{ {
int fd; int fd;
char *loc;
DIR *dir;
char dirname[MAX_PATH];
rb->splash(0, "Saving..."); rb->splash(0, "Saving...");
/* Create dir if it doesn't exist */
if ((loc = rb->strrchr(filename, '/')) != NULL) {
rb->strncpy(dirname, filename, loc - filename);
dirname[loc - filename] = '\0';
if(!(dir = rb->opendir(dirname)))
rb->mkdir(dirname);
else
rb->closedir(dir);
}
if (filename[0] == '\0' || if (filename[0] == '\0' ||
(fd = rb->open(filename, O_WRONLY|O_CREAT|O_TRUNC)) < 0) { (fd = rb->open(filename, O_WRONLY|O_CREAT|O_TRUNC)) < 0) {
rb->splash(HZ*2, "Unable to open %s", filename); rb->splash(HZ*2, "Unable to open %s", filename);
@ -874,11 +896,13 @@ static bool save(char *filename, bool solution)
static bool load(char *filename, bool silent) static bool load(char *filename, bool silent)
{ {
int fd; int fd;
int i = 0, n; int i, n;
int len; int len;
bool play_solution;
int button; int button;
int step_delay = HZ/4; bool play_solution;
bool paused = false;
unsigned short speed = 2;
int delay[] = {HZ/2, HZ/3, HZ/4, HZ/6, HZ/8, HZ/12, HZ/16, HZ/25};
if (filename[0] == '\0' || (fd = rb->open(filename, O_RDONLY)) < 0) { if (filename[0] == '\0' || (fd = rb->open(filename, O_RDONLY)) < 0) {
if (!silent) if (!silent)
@ -934,11 +958,12 @@ static bool load(char *filename, bool silent)
n = n*10 + buf[i] - '0'; n = n*10 + buf[i] - '0';
current_info.level.index = n - 1; current_info.level.index = n - 1;
/* Get current undo index */ /* Get undo index */
for (n = 0, i++; buf[i] >= '0' && buf[i] <= '9' && i < 21; i++) for (n = 0, i++; buf[i] >= '0' && buf[i] <= '9' && i < 21; i++)
n = n*10 + buf[i] - '0'; n = n*10 + buf[i] - '0';
if (n > len) if (n > len)
n = len; n = len;
undo_info.max = len;
if (current_info.level.index < 0) { if (current_info.level.index < 0) {
if (!silent) if (!silent)
@ -958,40 +983,78 @@ static bool load(char *filename, bool silent)
if (play_solution) { if (play_solution) {
rb->lcd_clear_display(); rb->lcd_clear_display();
update_screen(); update_screen();
rb->sleep(2*step_delay); rb->sleep(2*delay[speed]);
/* Replay solution until the end or quit button is pressed */ /* Replay solution until menu button is pressed */
for (i = 0; i < len; i++) { i = 0;
if (!move(undo_info.history[i], true)) { while (true) {
n = i; if (i < len) {
break; if (!move(undo_info.history[i], true)) {
} n = i;
break;
}
rb->lcd_clear_display();
update_screen();
i++;
} else
paused = true;
rb->lcd_clear_display(); rb->sleep(delay[speed]);
update_screen();
rb->sleep(step_delay);
/* Ignore keypresses except for quit & changing speed */ while ((button = rb->button_get(false)) || paused) {
while ((button = rb->button_get(false)) != BUTTON_NONE) {
switch (button) { switch (button) {
case SOKOBAN_MENU: case SOKOBAN_MENU:
/* Pretend the level is complete so we'll quit */ /* Pretend the level is complete so we'll quit */
current_info.level.boxes_to_go = 0; current_info.level.boxes_to_go = 0;
return true; return true;
case SOKOBAN_PAUSE:
/* Toggle pause state */
paused = !paused;
break;
case BUTTON_LEFT:
case BUTTON_LEFT | BUTTON_REPEAT:
/* Go back one move */
if (paused) {
if (undo())
i--;
rb->lcd_clear_display();
update_screen();
}
break;
case BUTTON_RIGHT:
case BUTTON_RIGHT | BUTTON_REPEAT:
/* Go forward one move */
if (paused) {
if (redo())
i++;
rb->lcd_clear_display();
update_screen();
}
break;
case SOKOBAN_UP: case SOKOBAN_UP:
if (step_delay > HZ/12) case SOKOBAN_UP | BUTTON_REPEAT:
step_delay = 5*step_delay/6; /* Speed up */
if (speed < sizeof(delay)/sizeof(int) - 1)
speed++;
break; break;
case SOKOBAN_DOWN: case SOKOBAN_DOWN:
if (step_delay < 3*HZ/4) case SOKOBAN_DOWN | BUTTON_REPEAT:
step_delay = 6*step_delay/5; /* Slow down */
if (speed > 0)
speed--;
} }
if (paused)
rb->sleep(HZ/33);
} }
} }
/* If level complete, wait for keypress before quitting */ /* If level is complete, wait for keypress before quitting */
if (current_info.level.boxes_to_go == 0) if (current_info.level.boxes_to_go == 0)
rb->button_get(true); rb->button_get(true);
@ -1008,7 +1071,6 @@ static bool load(char *filename, bool silent)
rb->lcd_clear_display(); rb->lcd_clear_display();
} }
undo_info.max = len;
undo_info.current = n; undo_info.current = n;
} }
@ -1022,9 +1084,10 @@ static int sokoban_menu(void)
int i; int i;
bool menu_quit; bool menu_quit;
int start_selected = 0; int start_selected = 0;
int prev_level = current_info.level.index;
MENUITEM_STRINGLIST(menu, "Sokoban Menu", NULL, MENUITEM_STRINGLIST(menu, "Sokoban Menu", NULL,
"Resume", "Audio Playback", "Keys", "Resume", "Select Level", "Audio Playback", "Keys",
"Load Default Level Set", "Quit Without Saving", "Load Default Level Set", "Quit Without Saving",
"Save Progress & Quit"); "Save Progress & Quit");
@ -1036,12 +1099,25 @@ static int sokoban_menu(void)
case 0: /* Resume */ case 0: /* Resume */
break; break;
case 1: /* Audio playback control */ case 1: /* Select level */
current_info.level.index++;
rb->set_int("Select Level", "", UNIT_INT,
&current_info.level.index, NULL, 1, 1,
current_info.max_level, NULL);
current_info.level.index--;
if (prev_level != current_info.level.index) {
init_undo();
draw_level();
} else
menu_quit = false;
break;
case 2: /* Audio playback control */
playback_control(rb); playback_control(rb);
menu_quit = false; menu_quit = false;
break; break;
case 2: /* Keys */ case 3: /* Keys */
FOR_NB_SCREENS(i) FOR_NB_SCREENS(i)
rb->screens[i]->clear_display(); rb->screens[i]->clear_display();
rb->lcd_setfont(SOKOBAN_FONT); rb->lcd_setfont(SOKOBAN_FONT);
@ -1079,8 +1155,8 @@ static int sokoban_menu(void)
#elif CONFIG_KEYPAD == IAUDIO_X5M5_PAD #elif CONFIG_KEYPAD == IAUDIO_X5M5_PAD
rb->lcd_putsxy(3, 6, "[POWER] Menu"); rb->lcd_putsxy(3, 6, "[POWER] Menu");
rb->lcd_putsxy(3, 16, "[SELECT] Undo"); rb->lcd_putsxy(3, 16, "[SELECT] Undo");
rb->lcd_putsxy(3, 26, "[REC] Previous Level"); rb->lcd_putsxy(3, 26, "[PLAY] Redo");
rb->lcd_putsxy(3, 36, "[PLAY] Next Level"); rb->lcd_putsxy(3, 36, "[REC] Restart Level");
#elif CONFIG_KEYPAD == IRIVER_H10_PAD #elif CONFIG_KEYPAD == IRIVER_H10_PAD
rb->lcd_putsxy(3, 6, "[POWER] Menu"); rb->lcd_putsxy(3, 6, "[POWER] Menu");
rb->lcd_putsxy(3, 16, "[REW] Undo"); rb->lcd_putsxy(3, 16, "[REW] Undo");
@ -1117,17 +1193,17 @@ static int sokoban_menu(void)
menu_quit = false; menu_quit = false;
break; break;
case 3: /* Load default levelset */ case 4: /* Load default levelset */
init_boards(); init_boards();
if (!read_levels(true)) if (!read_levels(true))
return 4; return 5; /* Quit */
load_level(); load_level();
break; break;
case 4: /* Quit */ case 5: /* Quit */
break; break;
case 5: /* Save & quit */ case 6: /* Save & quit */
save(SOKOBAN_SAVE_FILE, false); save(SOKOBAN_SAVE_FILE, false);
rb->reload_directory(); rb->reload_directory();
} }
@ -1163,13 +1239,13 @@ static bool sokoban_loop(void)
switch(button) switch(button)
{ {
#ifdef SOKOBAN_RC_QUIT #ifdef SOKOBAN_RC_MENU
case SOKOBAN_RC_QUIT: case SOKOBAN_RC_MENU:
#endif #endif
case SOKOBAN_MENU: case SOKOBAN_MENU:
switch (sokoban_menu()) { switch (sokoban_menu()) {
case 4: /* Quit */ case 5: /* Quit */
case 5: /* Save & quit */ case 6: /* Save & quit */
return PLUGIN_OK; return PLUGIN_OK;
} }
update_screen(); update_screen();
@ -1292,7 +1368,7 @@ static bool sokoban_loop(void)
rb->button_clear_queue(); rb->button_clear_queue();
/* Display for 4 seconds or until new keypress */ /* Display for 4 seconds or until new keypress */
for (i = 0; i < 75; i++) { for (i = 0; i < 80; i++) {
rb->sleep(HZ/20); rb->sleep(HZ/20);
button = rb->button_get(false); button = rb->button_get(false);
if (button && !(button & BUTTON_REL) && if (button && !(button & BUTTON_REL) &&
@ -1302,16 +1378,25 @@ static bool sokoban_loop(void)
if (button == BUTTON_SAVE) { if (button == BUTTON_SAVE) {
if (undo_info.count < MAX_UNDOS) { if (undo_info.count < MAX_UNDOS) {
/* Default filename to current levelset plus /* Set filename to current levelset plus level number
* level number and .sok extension */ * and .sok extension. Use SAVE_FOLDER if using the
loc = rb->strrchr(buffered_boards.filename, '.'); * default levelset, since it's in a hidden folder. */
if (loc != NULL) if (rb->strcmp(buffered_boards.filename,
*loc = '\0'; SOKOBAN_LEVELS_FILE) == 0) {
rb->snprintf(buf, sizeof(buf), "%s.%d.sok", rb->snprintf(buf, sizeof(buf),
buffered_boards.filename, "%s/sokoban.%d.sok",
current_info.level.index + 1); SOKOBAN_SAVE_FOLDER,
if (loc != NULL) current_info.level.index + 1);
*loc = '.'; } else {
if ((loc = rb->strrchr(buffered_boards.filename,
'.')) != NULL)
*loc = '\0';
rb->snprintf(buf, sizeof(buf), "%s.%d.sok",
buffered_boards.filename,
current_info.level.index + 1);
if (loc != NULL)
*loc = '.';
}
if (!rb->kbd_input(buf, MAX_PATH)) if (!rb->kbd_input(buf, MAX_PATH))
save(buf, true); save(buf, true);
@ -1355,8 +1440,8 @@ static bool sokoban_loop(void)
current_info.level.index = 0; current_info.level.index = 0;
switch (sokoban_menu()) { switch (sokoban_menu()) {
case 4: /* Quit */ case 5: /* Quit */
case 5: /* Save & quit */ case 6: /* Save & quit */
return PLUGIN_OK; return PLUGIN_OK;
} }
} }

View file

@ -637,8 +637,8 @@
#### ####
#### # # #### # #
### @###$ # ### ###$ #
## $ # ## @ $ #
## $ $$## ## ## $ $$## ##
# #$## # # #$## #
# # $ $$ # ### # # $ $$ # ###
@ -656,7 +656,7 @@
# # ###### # # # ###### #
# # $ $ $ $# # # # $ $ $ $# #
# # $@$ ## ## # # $@$ ## ##
# # $ $ $###...# # # #$ $ $###...#
# # $ $ ##...# # # $ $ ##...#
# ###$$$ $ ##...# # ###$$$ $ ##...#
# # ## ##...# # # ## ##...#
@ -780,14 +780,14 @@
# # $ #@ # # # $ #@ #
# #######$#### ### # #######$#### ###
# # ## # #$ ..# # # ## # #$ ..#
# # $ # # #.# # # $ $ # # #.#
# # $ # #$ ..# # # $ # #$ ..#
# # ### ## #.# # # ### ## #.#
# ### # # #$ ..# # ### # # #$ ..#
# # # #### #.# # # # $#### #.#
# #$ $ $ #$ ..# # #$ $ $ #* ..#
# $ # $ $ # #.# # $ # $ $ # #.#
#### $### #$ ..# #### $### #* ..#
# $$ ###....# # $$ ###....#
# ## ###### # ## ######
######## ########
@ -847,10 +847,10 @@
# $ $ $ # # $ $ $ #
## #### # $ # # ## #### # $ # #
# # ## # ## # # ## # ##
# $# # ## ### ## # $# # ## ### #
# $ #$### ### ## # $ #$### # # #
### $ # # ### ## ### $ # # ### #
### $ ## # # ## ## $ ## # # ##
# $ # $ $ $ # # $ # $ $ $ #
# $ $#$$$ # # # $ $#$$$ # #
# # $ ##### # # $ #####
@ -869,7 +869,7 @@
# # #$#$### # # #$#$###
# #### #$$$$$ # # #### #$$$$$ #
# # $ # # # # $ # #
# # ## ### # # ## ## ###
# ######$###### $ # # ######$###### $ #
# # # # # # # #
########## ##### ########## #####
@ -1049,7 +1049,7 @@
#...... ######### #...... #########
#...... # ## # #...... # ## #
#..### $ $ # #..### $ $ #
#... $ $ # ## # #... $ $ # ### #
#...#$##### # # #...#$##### # #
### # #$ #$ # ### # #$ #$ #
# $$ $ $ $## # # $$ $ $ $## #
@ -1130,8 +1130,8 @@
### ......# $$ ## ### ......# $$ ##
# ......# # # # ......# # #
# # ......#$ $ # # # ......#$ $ #
# #$...... $$# $ # # # ...... $$# $ #
# ### ###$ $ ## # $ ### ###$ $ ##
### $ $ $ $ # ### $ $ $ $ #
# $ $ $ $ # # $ $ $ $ #
###### ###### ###### ######
@ -1202,7 +1202,7 @@
## $ $ ##### ## $ $ #####
# ## ## ##...# # ## ## ##...#
# #$$ $ $$#$##...# # #$$ $ $$#$##...#
# # @ # ...# # # @ # ...#
# $# ###$$ ...# # $# ###$$ ...#
# $ $$ $ ##....# # $ $$ $ ##....#
###$ ####### ###$ #######
@ -1245,16 +1245,16 @@
############ ############
##.. # # ##.. # #
##..* $ $ # ##..* $ $ #
##..*.# # # $## ##..*.# # #$ ##
#..*.# # # $ # #..*.# # # $ #
####...# # # # ####...# # # #
# ## # # # ## # #
# @$ $ ### # ## # @$ $ ### # # ##
# $ $ # # # # $ $ # # #
###$$ # # # # # ###$$ # # # # #
# $ # # ##### # $ # # #####
# $# ##### # # $# ##### #
#$ # # # # #$ # # # #
# ### ## # # ### ## #
# # # ## # # # ##
#### ###### #### ######

View file

@ -13,12 +13,14 @@ information about the level format, see
\begin{table} \begin{table}
\begin{btnmap}{}{} \begin{btnmap}{}{}
\multicolumn{2}{c}{\textbf{In game}} \\
\hline
\opt{RECORDER_PAD,ARCHOS_AV300_PAD,ONDIO_PAD,IRIVER_H100_PAD,IRIVER_H300_PAD,IAUDIO_X5_PAD,GIGABEAT_PAD,SANSA_E200_PAD} \opt{RECORDER_PAD,ARCHOS_AV300_PAD,ONDIO_PAD,IRIVER_H100_PAD,IRIVER_H300_PAD,IAUDIO_X5_PAD,GIGABEAT_PAD,SANSA_E200_PAD}
{\ButtonUp, \ButtonDown,} {\ButtonUp, \ButtonDown, }%
\opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonMenu, \ButtonPlay,} \opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonMenu, \ButtonPlay, }%
\opt{IRIVER_H10_PAD}{\ButtonScrollUp, \ButtonScrollDown,} \opt{IRIVER_H10_PAD}{\ButtonScrollUp, \ButtonScrollDown, }%
\ButtonLeft, \ButtonRight \ButtonLeft, \ButtonRight
& Move the ``sokoban'' up, down, left or right\\ & Move the ``sokoban'' up, down, left, or right\\
\opt{RECORDER_PAD,ARCHOS_AV300_PAD,ONDIO_PAD,IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonOff} \opt{RECORDER_PAD,ARCHOS_AV300_PAD,ONDIO_PAD,IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonOff}
\opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonSelect+\ButtonMenu} \opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonSelect+\ButtonMenu}
\opt{IAUDIO_X5_PAD,IRIVER_H10_PAD,GIGABEAT_PAD,SANSA_E200_PAD}{\ButtonPower} \opt{IAUDIO_X5_PAD,IRIVER_H10_PAD,GIGABEAT_PAD,SANSA_E200_PAD}{\ButtonPower}
@ -29,11 +31,10 @@ information about the level format, see
\opt{IPOD_4G_PAD,IPOD_3G_PAD,IAUDIO_X5_PAD,GIGABEAT_PAD,SANSA_E200_PAD}{\ButtonSelect} \opt{IPOD_4G_PAD,IPOD_3G_PAD,IAUDIO_X5_PAD,GIGABEAT_PAD,SANSA_E200_PAD}{\ButtonSelect}
\opt{IRIVER_H10_PAD}{\ButtonRew} \opt{IRIVER_H10_PAD}{\ButtonRew}
& Undo last movement \\ & Undo last movement \\
\opt{RECORDER_PAD,ARCHOS_AV300_PAD}{\ButtonPlay} \opt{RECORDER_PAD,ARCHOS_AV300_PAD,IAUDIO_X5_PAD}{\ButtonPlay}
\opt{ONDIO_PAD}{\ButtonMenu+\ButtonDown} \opt{ONDIO_PAD}{\ButtonMenu+\ButtonDown}
\opt{IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonMode} \opt{IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonMode}
\opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonSelect+\ButtonPlay} \opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonSelect+\ButtonPlay}
\opt{IAUDIO_X5_PAD}{n/a}
\opt{IRIVER_H10_PAD}{\ButtonFF} \opt{IRIVER_H10_PAD}{\ButtonFF}
\opt{GIGABEAT_PAD}{\ButtonA} \opt{GIGABEAT_PAD}{\ButtonA}
\opt{SANSA_E200_PAD}{\ButtonRec} \opt{SANSA_E200_PAD}{\ButtonRec}
@ -42,7 +43,7 @@ information about the level format, see
\opt{ONDIO_PAD}{\ButtonMenu+\ButtonLeft} \opt{ONDIO_PAD}{\ButtonMenu+\ButtonLeft}
\opt{IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonOn+\ButtonDown} \opt{IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonOn+\ButtonDown}
\opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonSelect+\ButtonLeft} \opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonSelect+\ButtonLeft}
\opt{IAUDIO_X5_PAD}{\ButtonRec} \opt{IAUDIO_X5_PAD}{n/a}
\opt{IRIVER_H10_PAD}{\ButtonPlay+\ButtonScrollDown} \opt{IRIVER_H10_PAD}{\ButtonPlay+\ButtonScrollDown}
\opt{GIGABEAT_PAD}{\ButtonVolDown} \opt{GIGABEAT_PAD}{\ButtonVolDown}
\opt{SANSA_E200_PAD}{\ButtonSelect+\ButtonDown} \opt{SANSA_E200_PAD}{\ButtonSelect+\ButtonDown}
@ -50,7 +51,8 @@ information about the level format, see
\opt{RECORDER_PAD,ARCHOS_AV300_PAD}{\ButtonFTwo} \opt{RECORDER_PAD,ARCHOS_AV300_PAD}{\ButtonFTwo}
\opt{ONDIO_PAD}{\ButtonMenu+\ButtonUp} \opt{ONDIO_PAD}{\ButtonMenu+\ButtonUp}
\opt{IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonOn} \opt{IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonOn}
\opt{IPOD_4G_PAD,IPOD_3G_PAD,IAUDIO_X5_PAD}{n/a} \opt{IPOD_4G_PAD,IPOD_3G_PAD}{n/a}
\opt{IAUDIO_X5_PAD}{\ButtonRec}
\opt{IRIVER_H10_PAD}{\ButtonPlay+\ButtonRight} \opt{IRIVER_H10_PAD}{\ButtonPlay+\ButtonRight}
\opt{GIGABEAT_PAD}{\ButtonMenu} \opt{GIGABEAT_PAD}{\ButtonMenu}
\opt{SANSA_E200_PAD}{\ButtonSelect+\ButtonRight} \opt{SANSA_E200_PAD}{\ButtonSelect+\ButtonRight}
@ -59,16 +61,30 @@ information about the level format, see
\opt{ONDIO_PAD}{\ButtonMenu+\ButtonRight} \opt{ONDIO_PAD}{\ButtonMenu+\ButtonRight}
\opt{IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonOn+\ButtonUp} \opt{IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonOn+\ButtonUp}
\opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonSelect+\ButtonRight} \opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonSelect+\ButtonRight}
\opt{IAUDIO_X5_PAD}{\ButtonPlay} \opt{IAUDIO_X5_PAD}{n/a}
\opt{IRIVER_H10_PAD}{\ButtonPlay+\ButtonScrollUp} \opt{IRIVER_H10_PAD}{\ButtonPlay+\ButtonScrollUp}
\opt{GIGABEAT_PAD}{\ButtonVolUp} \opt{GIGABEAT_PAD}{\ButtonVolUp}
\opt{SANSA_E200_PAD}{\ButtonSelect+\ButtonUp} \opt{SANSA_E200_PAD}{\ButtonSelect+\ButtonUp}
& Go to next level \\ & Go to next level \\
\hline
\multicolumn{2}{c}{\textbf{Solution playback}} \\
\hline
\opt{RECORDER_PAD,ARCHOS_AV300_PAD,IAUDIO_X5_PAD,IRIVER_H10_PAD}{\ButtonPlay}
\opt{ONDIO_PAD}{\ButtonMenu}
\opt{IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonOn}
\opt{IPOD_4G_PAD,IPOD_3G_PAD,GIGABEAT_PAD,SANSA_E200_PAD}{\ButtonSelect}
& Pause/resume \\
\opt{RECORDER_PAD,ARCHOS_AV300_PAD,ONDIO_PAD,IRIVER_H100_PAD,IRIVER_H300_PAD,IAUDIO_X5_PAD,GIGABEAT_PAD,SANSA_E200_PAD} \opt{RECORDER_PAD,ARCHOS_AV300_PAD,ONDIO_PAD,IRIVER_H100_PAD,IRIVER_H300_PAD,IAUDIO_X5_PAD,GIGABEAT_PAD,SANSA_E200_PAD}
{\ButtonUp/\ButtonDown,} {\ButtonUp/\ButtonDown}
\opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonMenu/\ButtonPlay,} \opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonMenu/\ButtonPlay}
\opt{IRIVER_H10_PAD}{\ButtonScrollUp/\ButtonScrollDown,} \opt{IRIVER_H10_PAD}{\ButtonScrollUp/\ButtonScrollDown}
& Increase/decrease solution playback speed & Increase/decrease playback speed \\
\ButtonLeft/\ButtonRight
& Go backward/forward (while paused) \\
\opt{RECORDER_PAD,ARCHOS_AV300_PAD,ONDIO_PAD,IRIVER_H100_PAD,IRIVER_H300_PAD}{\ButtonOff}
\opt{IPOD_4G_PAD,IPOD_3G_PAD}{\ButtonSelect+\ButtonMenu}
\opt{IAUDIO_X5_PAD,IRIVER_H10_PAD,GIGABEAT_PAD,SANSA_E200_PAD}{\ButtonPower}
& Quit \\
\end{btnmap} \end{btnmap}
\end{table} \end{table}
@ -77,3 +93,5 @@ Some places where can you can find level sets:
\item \url{http://www.sourcecode.se/sokoban/levels.php} \item \url{http://www.sourcecode.se/sokoban/levels.php}
\item \url{http://sokobano.de/en/levels.php} \item \url{http://sokobano.de/en/levels.php}
\end{itemize} \end{itemize}
Note that some level sets may contain levels that are too large for this
version of Sokoban and are unplayable as a result.

View file

@ -329,7 +329,7 @@ STOP
`cp $ROOT/apps/tagnavi.config .rockbox/`; `cp $ROOT/apps/tagnavi.config .rockbox/`;
if($bitmap) { if($bitmap) {
`cp $ROOT/apps/plugins/sokobanlevels.sok .rockbox/rocks/`; # sokoban levels `cp $ROOT/apps/plugins/sokoban.levels .rockbox/rocks/`; # sokoban levels
`cp $ROOT/apps/plugins/snake2.levels .rockbox/rocks/`; # snake2 levels `cp $ROOT/apps/plugins/snake2.levels .rockbox/rocks/`; # snake2 levels
} }