From 8951fdff1aada126257e07699ea6f132cb8d2e65 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Tue, 18 Dec 2012 00:02:49 -0500 Subject: Remove various explicit delays and reduce screen tearing when drawing emulated screens. --- source/nds/entry.cpp | 17 ++++++----------- source/nds/gui.c | 16 ++++++++-------- 2 files changed, 14 insertions(+), 19 deletions(-) (limited to 'source/nds') diff --git a/source/nds/entry.cpp b/source/nds/entry.cpp index d3dbae3..c14902c 100644 --- a/source/nds/entry.cpp +++ b/source/nds/entry.cpp @@ -172,12 +172,7 @@ bool8 S9xDeinitUpdate (int Width, int Height, bool8 /*sixteen_bit*/) break; } - -// memcpy(up_screen_addr, GFX.Screen, 256*192*2); -// memcpy(down_screen_addr, GFX.Screen+256*192*2, 256*(224-192)*2); - - ds2_flipScreen(UP_SCREEN, 0); -// ds2_flipScreen(DOWN_SCREEN, 0); + ds2_flipScreen(UP_SCREEN, 1); // synchronise to vblank to avoid tearing return (TRUE); } @@ -454,12 +449,12 @@ int load_gamepak(char* file) CPU.Flags = 0; S9xReset (); - mdelay(50); + // mdelay(50); // Delete this delay if (!Memory.LoadROM (file)) return -1; Memory.LoadSRAM (S9xGetFilename (".srm")); - mdelay(50); + // mdelay(50); // Delete this delay //S9xLoadCheatFile (S9xGetFilename (".cht")); S9xCheat_Disable(); @@ -507,7 +502,7 @@ int load_gamepak(char* file) } */ - mdelay(50); + // mdelay(50); // Delete this delay if (!Settings.APUEnabled) S9xSetSoundMute (FALSE); @@ -602,7 +597,7 @@ int sfc_main (int argc, char **argv) if (Settings.Paused) { S9xSetSoundMute (TRUE); - mdelay(50); + // mdelay(50); // Delete this delay unsigned short screen[256*192]; copy_screen((void*)screen, up_screen_addr, 0, 0, 256, 192); @@ -996,7 +991,7 @@ const unsigned int keymap[12] = { unsigned int S9xReadJoypad (int which1) { - struct key_buf inputdata; + struct key_buf inputdata; ds2_getrawInput(&inputdata); if(inputdata.key & KEY_TOUCH) //Active menu diff --git a/source/nds/gui.c b/source/nds/gui.c index f8cd03b..99ea7b0 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -1650,7 +1650,7 @@ unsigned int frame_interval; --------------------------------------------------------*/ u32 menu(u16 *screen) { - mdelay(50); + mdelay(50); // to prevent the touch key from being applied too soon? gui_action_type gui_action; u32 i; u32 repeat; @@ -2059,7 +2059,7 @@ u32 menu(u16 *screen) reorder_latest_file(); save_game_config_file(); - mdelay(500); + // mdelay(500); // Delete this delay } } } @@ -2842,7 +2842,7 @@ u32 menu(u16 *screen) draw_string_vcenter(up_screen_addr, 0, 80, 256, COLOR_WHITE, msg[MSG_NON_LOAD_GAME]); ds2_flipScreen(UP_SCREEN, 1); - mdelay(500); + // mdelay(500); // Delete this delay } } @@ -2894,7 +2894,7 @@ u32 menu(u16 *screen) } save_emu_config_file(); - mdelay(500); + // mdelay(500); // Delete this delay } } @@ -3617,7 +3617,7 @@ u32 menu(u16 *screen) //----------------------------------------------------------------------------// // Menu Start ds2_setCPUclocklevel(0); - mdelay(200); + // mdelay(200); // Delete this delay ds2_setBacklight(3); @@ -3647,7 +3647,7 @@ u32 menu(u16 *screen) choose_menu(&main_menu); // Menu loop - mdelay(200); + // mdelay(50); // Delete this delay, shortened from 200 while(repeat) { @@ -4133,9 +4133,9 @@ u32 menu(u16 *screen) save_game_config_file(); } save_emu_config_file(); - mdelay(100); + // mdelay(100); // Delete this delay set_cpu_clock(clock_speed_number); - mdelay(200); + // mdelay(200); // Delete this delay ds2_clearScreen(DOWN_SCREEN, 0); ds2_flipScreen(DOWN_SCREEN, 1); -- cgit v1.2.3 From 286bfd58050a13e2e0e30bb35a7a1d189ec7edd1 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Tue, 18 Dec 2012 00:40:18 -0500 Subject: Sync sound. In addition to having less sound skipping going on, certain platformer games (I'm looking at you, Super Mario World) are helped by having more synchronised controls. In other words, synchronising the audio also synchronises the controls a bit more. --- source/nds/entry.cpp | 1 + 1 file changed, 1 insertion(+) (limited to 'source/nds') diff --git a/source/nds/entry.cpp b/source/nds/entry.cpp index c14902c..24c0e03 100644 --- a/source/nds/entry.cpp +++ b/source/nds/entry.cpp @@ -385,6 +385,7 @@ void init_sfc_setting(void) Settings.NetPlay = FALSE; Settings.ServerName [0] = 0; Settings.ThreadSound = FALSE; + Settings.SoundSync = TRUE; Settings.AutoSaveDelay = 0; #ifdef _NETPLAY_SUPPORT Settings.Port = NP_DEFAULT_PORT; -- cgit v1.2.3 From 65b56543ab4bab2307fe3b29a15f43caaa88dfa1 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Wed, 19 Dec 2012 01:30:30 -0500 Subject: Raise the CPU's clock speed to 396 MHz while loading ROMs. Also raise the CPU's clock speed to 396 MHz by default, instead of 360 MHz, when emulating a ROM. --- source/nds/gui.c | 30 +++++++++++++++++++++--------- 1 file changed, 21 insertions(+), 9 deletions(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index 99ea7b0..07f59d0 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -1721,7 +1721,7 @@ u32 menu(u16 *screen) game_config.clock_speed_number = clock_speed_number; reorder_latest_file(); - //S9xAutoSaveSRAM (); + S9xAutoSaveSRAM (); save_game_config_file(); } save_emu_config_file(); @@ -1734,7 +1734,7 @@ u32 menu(u16 *screen) if(gamepak_name[0] != 0) { - //S9xAutoSaveSRAM (); + S9xAutoSaveSRAM (); save_game_config_file(); } @@ -1748,7 +1748,10 @@ u32 menu(u16 *screen) draw_string_vcenter(down_screen_addr, 36, 100, 190, COLOR_MSSG, msg[MSG_LOADING_GAME]); ds2_flipScreen(DOWN_SCREEN, 2); - if(load_gamepak(line_buffer) == -1) + ds2_setCPUclocklevel(13); + int load_result = load_gamepak(&line_buffer); + ds2_setCPUclocklevel(0); + if(load_result == -1) { first_load = 1; gamepak_name[0] = '\0'; @@ -1812,8 +1815,12 @@ u32 menu(u16 *screen) draw_message(down_screen_addr, bg_screenp, 28, 31, 227, 165, bg_screenp_color); draw_string_vcenter(down_screen_addr, 36, 100, 190, COLOR_MSSG, msg[MSG_LOADING_GAME]); ds2_flipScreen(DOWN_SCREEN, 2); - - if(load_gamepak(args[1]) == -1) + + ds2_setCPUclocklevel(13); + int load_result = load_gamepak(args[1]); + ds2_setCPUclocklevel(0); + + if(load_result == -1) { first_load = 1; gamepak_name[0] = '\0'; @@ -3495,7 +3502,7 @@ u32 menu(u16 *screen) if(gamepak_name[0] != 0) { - //S9xAutoSaveSRAM (); + S9xAutoSaveSRAM (); save_game_config_file(); } @@ -3511,7 +3518,12 @@ u32 menu(u16 *screen) *ext_pos= '/'; ext_pos = emu_config.latest_file[current_option_num -1]; - if(load_gamepak(ext_pos) == -1) { + + ds2_setCPUclocklevel(13); + int load_result = load_gamepak(ext_pos); + ds2_setCPUclocklevel(0); + + if(load_result == -1) { first_load = 1; return; } @@ -4129,7 +4141,7 @@ u32 menu(u16 *screen) game_config.clock_speed_number = clock_speed_number; reorder_latest_file(); - //S9xAutoSaveSRAM (); + S9xAutoSaveSRAM (); save_game_config_file(); } save_emu_config_file(); @@ -4308,7 +4320,7 @@ void init_game_config(void) { u32 i; - game_config.clock_speed_number = 2; //360MHz + game_config.clock_speed_number = 5; // 396 MHz by default clock_speed_number = 2; game_config.graphic = 0; -- cgit v1.2.3 From dd06ba36fff3fad1eea457026c21f49a01c78604 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Wed, 19 Dec 2012 01:37:10 -0500 Subject: Default to Graphics Mode 3, which displays the correct SNES aspect ratio at the cost of some lines at the top and bottom. --- source/nds/gui.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index 07f59d0..4c0a9d7 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -4321,8 +4321,8 @@ void init_game_config(void) u32 i; game_config.clock_speed_number = 5; // 396 MHz by default - clock_speed_number = 2; - game_config.graphic = 0; + clock_speed_number = 5; + game_config.graphic = 3; // By default, have a good-looking aspect ratio game_config.gamepad_config_menu = BUTTON_ID_TOUCH; memcpy(game_config.gamepad_config_map, gamepad_config_map_init, sizeof(gamepad_config_map_init)); -- cgit v1.2.3 From eee0a7ecdaa08f15ebeb7821d6e805234dc78c33 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Wed, 19 Dec 2012 03:10:55 -0500 Subject: Change the English labels so they're more descriptive. Really set the default CPU frequency to the highest. --- source/nds/gui.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index 4c0a9d7..af04c74 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -266,7 +266,7 @@ u32 game_enable_audio = 1; /****************************************************************************** ******************************************************************************/ static u32 menu_cheat_page = 0; -static u32 clock_speed_number = 2; +static u32 clock_speed_number = 5; u32 gamepad_config_menu; /****************************************************************************** -- cgit v1.2.3 From 973cd8d5e37dba2e15de3d3fd1965d2fbfc2cdab Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Wed, 19 Dec 2012 18:38:04 -0500 Subject: EN: Link the French translation to the interface. FR: Ajout de la traduction française à l'interface. EN: * bdf_font.c: Add support for having a main font, [0], of more than 128 characters. Refactor character width checks into a new function, BDF_width16_ucs. * bdf_font.h, draw.h, gui.c: Use UTF-8 for all strings to allow more translations. Use BDF_width16_ucs where possible. FR: * bdf_font.c: Prendre en charge une police principale, [0], de plus de 128 caractères. Diriger les vérifications de la largeur d'un caractère vers une nouvelle routine, BDF_width16_ucs. * bdf_font.h, draw.h, gui.c: Utiliser le codage UTF-8 pour toutes les chaînes pour permettre d'autres traductions. Utiliser BDF_width16_ucs là où c'est possible. --- source/nds/bdf_font.c | 300 ++++++++++++++++++++++++++------------------------ source/nds/draw.h | 118 ++++++++++---------- source/nds/gui.c | 38 ++++--- source/nds/message.h | 2 +- 4 files changed, 240 insertions(+), 218 deletions(-) (limited to 'source/nds') diff --git a/source/nds/bdf_font.c b/source/nds/bdf_font.c index 5da57e3..b1e7ccd 100644 --- a/source/nds/bdf_font.c +++ b/source/nds/bdf_font.c @@ -27,13 +27,13 @@ #include "gui.h" -#define BDF_VERDANA "SYSTEM/verdana.bdf" +#define BDF_PICTOCHAT "SYSTEM/Pictochat-16.bdf" #define BDF_SONG "SYSTEM/song.bdf" -#define ODF_VERDANA "SYSTEM/verdana.odf" +#define ODF_PICTOCHAT "SYSTEM/Pictochat-16.odf" #define ODF_SONG "SYSTEM/song.odf" -#define HAVE_ODF -//#define DUMP_ODF +#define HAVE_ODF // Define this if you have generated Pictochat-16.odf [Neb] +// #define DUMP_ODF // Define this if you want to regenerate Pictochat-16.odf [Neb] #define BDF_LIB_NUM 2 #define ODF_VERSION "1.0" @@ -49,21 +49,24 @@ static u32 fonts_max_height; static u32 bitmap_code(unsigned char *code, unsigned char *bitmap) { unsigned char *map; - u32 a, b, len; + u8 a, b; + u32 len; len= 0; map= (unsigned char*)bitmap; while(*map) { - //character to number, we assume the character can convert to number! + // One hex character represents the state of 4 successive pixels if(*map != 0x0A) { - if(*map <= 0x39) a= *map - 0x30; - else a= *map - 0x37; + if (*map <= '9') a= *map - '0'; + else if (*map <= 'F') a= *map - 'A' + 10; + else if (*map <= 'f') a= *map - 'a' + 10; map++; - if(*map <= 0x39) b= *map - 0x30; - else b= *map - 0x37; + if (*map <= '9') b= *map - '0'; + else if (*map <= 'F') b= *map - 'A' + 10; + else if (*map <= 'f') b= *map - 'a' + 10; *code++ = (a << 4) | b; len++; @@ -108,7 +111,7 @@ static u32 hatoi(char *string) /* * example * -* STARTCHAR 2264 +* STARTCHAR * ENCODING 8804 * SWIDTH 840 0 * DWIDTH 14 0 @@ -202,8 +205,17 @@ static int parse_bdf(char *filename, u32 start, u32 span, struct bdflibinfo *bdf pt += 6; ret= atoi(pt); - bdflibinfop -> start= start; - bdflibinfop -> span= span; + if (method == 1) + bdflibinfop -> start= start; + switch (method) { + case 0: + default: + bdflibinfop -> span= span + start; + break; + case 1: + bdflibinfop -> span= span; + break; + } //construct bdf font information bdffontp= (struct bdffont*)malloc(span * sizeof(struct bdffont)); @@ -241,14 +253,7 @@ static int parse_bdf(char *filename, u32 start, u32 span, struct bdflibinfo *bdf } if(!(strncasecmp(string, "STARTCHAR ", 10))) { - i= hatoi(pt +10); - if(i < start) continue; - else if(i < end) break; - else //Not found the start - { - ret= -7; - goto parse_bdf_error; - } + break; } } @@ -266,7 +271,7 @@ static int parse_bdf(char *filename, u32 start, u32 span, struct bdflibinfo *bdf pt= string + 9; index= atoi(pt); - if(index >= end) break; + if(index < start || index >= end) break; if(method == 0) i= index; else if(method == 1) i= index-start; @@ -534,15 +539,15 @@ int BDF_font_init(void) fonts_max_height= 0; #ifndef HAVE_ODF - sprintf(tmp_path, "%s/%s", main_path, BDF_VERDANA); - err= parse_bdf(tmp_path, 0, 128, &bdflib_info[0], 0); + sprintf(tmp_path, "%s/%s", main_path, BDF_PICTOCHAT); + err= parse_bdf(tmp_path, 32 /* from SPACE */, 8564 /* to one past the last character, "DOWNWARDS ARROW" */, &bdflib_info[0], 1); if(err < 0) { printf("BDF 0 initial error: %d\n", err); return -1; } #else - sprintf(tmp_path, "%s/%s", main_path, ODF_VERDANA); + sprintf(tmp_path, "%s/%s", main_path, ODF_PICTOCHAT); err= init_from_odf(tmp_path, &bdflib_info[0]); if(err < 0) { @@ -556,7 +561,7 @@ int BDF_font_init(void) fonts_max_height = bdflib_info[0].height; #ifdef DUMP_ODF - sprintf(tmp_path, "%s/%s", main_path, BDF_VERDANA); + sprintf(tmp_path, "%s/%s", main_path, BDF_PICTOCHAT); err= dump2odf(tmp_path, &bdflib_info[0]); if(err < 0) { @@ -613,7 +618,7 @@ void BDF_font_release(void) } } -/*----------------------------------------------------------------------------- +/*---------------------------------------------------------------------------- //16-bit color // Unicode Character // back is background, 0x8000 is transparence, other are visable colors @@ -626,26 +631,25 @@ u32 BDF_render16_ucs(void* screen_address, u32 screen_w, u32 v_align, u32 back, unsigned char cc; struct bdffont *bdffontp; - if(ch < 128) - { - bdffontp= bdflib_info[0].fonts; - fonts_height= bdflib_info[0].height; - } - else if(bdflib_info[1].fonts != NULL) - { - k= bdflib_info[1].start; - m= k + bdflib_info[1].span; - if(ch >= k && ch < m) - { + int font_num; + bool found = 0; + for (font_num = 0; font_num < BDF_LIB_NUM && !found; font_num++) { + if(bdflib_info[font_num].fonts != NULL) + { + k = bdflib_info[font_num].start; + if (ch < k) + continue; + m = k + bdflib_info[font_num].span; + if (ch >= m) + continue; ch -= k; - bdffontp= bdflib_info[1].fonts; - fonts_height= bdflib_info[0].height; - } - else - return 8; - } - else - return 8; + bdffontp= bdflib_info[font_num].fonts; + fonts_height= bdflib_info[font_num].height; + found = 1; + } + } + if (!found) + return 8; // the width of an undefined character, not an error code width= bdffontp[ch].dwidth >> 16; ret= width; @@ -715,6 +719,27 @@ u32 BDF_render16_ucs(void* screen_address, u32 screen_w, u32 v_align, u32 back, return ret; } +/* Returns the width, in pixels, of a character given its UCS-16 codepoint. */ +u32 BDF_width16_ucs(u16 ch) +{ + u32 k, ret; + + int font_num; + for (font_num = 0; font_num < BDF_LIB_NUM; font_num++) { + if(bdflib_info[font_num].fonts != NULL) + { + k = bdflib_info[font_num].start; + if (ch < k) + continue; + if (ch > k + bdflib_info[font_num].span) + continue; + ch -= k; + return bdflib_info[font_num].fonts[ch].dwidth >> 16; + } + } + return 8; // the width of an undefined character, not an error code +} + /*----------------------------------------------------------------------------- //16-bit color // ASCII Character @@ -837,101 +862,101 @@ void BDF_render_string(void* screen_address, u32 x, u32 y, u32 back, u32 front, /*----------------------------------------------------------------------------- ------------------------------------------------------------------------------*/ -char* utf8decode(char *utf8, u16 *ucs) -{ - unsigned char c = *utf8++; - unsigned long code; - int tail = 0; - - if ((c <= 0x7f) || (c >= 0xc2)) { - /* Start of new character. */ - if (c < 0x80) { /* U-00000000 - U-0000007F, 1 byte */ - code = c; - } else if (c < 0xe0) { /* U-00000080 - U-000007FF, 2 bytes */ - tail = 1; - code = c & 0x1f; - } else if (c < 0xf0) { /* U-00000800 - U-0000FFFF, 3 bytes */ - tail = 2; - code = c & 0x0f; - } else if (c < 0xf5) { /* U-00010000 - U-001FFFFF, 4 bytes */ - tail = 3; - code = c & 0x07; - } else { - /* Invalid size. */ - code = 0; - } - - while (tail-- && ((c = *utf8++) != 0)) { - if ((c & 0xc0) == 0x80) { - /* Valid continuation character. */ - code = (code << 6) | (c & 0x3f); - - } else { - /* Invalid continuation char */ - code = 0xfffd; - utf8--; - break; - } - } - } else { - /* Invalid UTF-8 char */ - code = 0; - } - /* currently we don't support chars above U-FFFF */ - *ucs = (code < 0x10000) ? code : 0; - return utf8; -} - -static u8 utf8_ucs2(const char *utf8, u16 *ucs) +char* utf8decode(char *utf8, u16 *ucs) +{ + unsigned char c = *utf8++; + unsigned long code; + int tail = 0; + + if ((c <= 0x7f) || (c >= 0xc2)) { + /* Start of new character. */ + if (c < 0x80) { /* U-00000000 - U-0000007F, 1 byte */ + code = c; + } else if (c < 0xe0) { /* U-00000080 - U-000007FF, 2 bytes */ + tail = 1; + code = c & 0x1f; + } else if (c < 0xf0) { /* U-00000800 - U-0000FFFF, 3 bytes */ + tail = 2; + code = c & 0x0f; + } else if (c < 0xf5) { /* U-00010000 - U-001FFFFF, 4 bytes */ + tail = 3; + code = c & 0x07; + } else { + /* Invalid size. */ + code = 0; + } + + while (tail-- && ((c = *utf8++) != 0)) { + if ((c & 0xc0) == 0x80) { + /* Valid continuation character. */ + code = (code << 6) | (c & 0x3f); + + } else { + /* Invalid continuation char */ + code = 0xfffd; + utf8--; + break; + } + } + } else { + /* Invalid UTF-8 char */ + code = 0; + } + /* currently we don't support chars above U-FFFF */ + *ucs = (code < 0x10000) ? code : 0; + return utf8; +} + +static u8 utf8_ucs2(const char *utf8, u16 *ucs) { char *pt = (char*)utf8; - - while(*pt !='\0') - { - pt = utf8decode(pt, ucs++); - } - *ucs = '\0'; - return 0; -} - -static u32 ucslen(const u16 *ucs) -{ + + while(*pt !='\0') + { + pt = utf8decode(pt, ucs++); + } + *ucs = '\0'; + return 0; +} + +static u32 ucslen(const u16 *ucs) +{ u32 len = 0; - - while(ucs[len] != '\0') - len++; - return len; + + while(ucs[len] != '\0') + len++; + return len; } unsigned char* skip_utf8_unit(unsigned char* utf8, unsigned int num) { while(num--) { - unsigned char c = *utf8++; - int tail = 0; - if ((c <= 0x7f) || (c >= 0xc2)) { - /* Start of new character. */ - if (c < 0x80) { /* U-00000000 - U-0000007F, 1 byte */ - } else if (c < 0xe0) { /* U-00000080 - U-000007FF, 2 bytes */ - tail = 1; - } else if (c < 0xf0) { /* U-00000800 - U-0000FFFF, 3 bytes */ - tail = 2; - } else if (c < 0xf5) { /* U-00010000 - U-001FFFFF, 4 bytes */ - tail = 3; - } else { /* Invalid size. */ - } - - while (tail-- && ((c = *utf8++) != 0)) { - if ((c & 0xc0) != 0x80) { - /* Invalid continuation char */ - utf8--; - break; - } - } + unsigned char c = *utf8++; + int tail = 0; + if ((c <= 0x7f) || (c >= 0xc2)) { + /* Start of new character. */ + if (c < 0x80) { /* U-00000000 - U-0000007F, 1 byte */ + } else if (c < 0xe0) { /* U-00000080 - U-000007FF, 2 bytes */ + tail = 1; + } else if (c < 0xf0) { /* U-00000800 - U-0000FFFF, 3 bytes */ + tail = 2; + } else if (c < 0xf5) { /* U-00010000 - U-001FFFFF, 4 bytes */ + tail = 3; + } else { /* Invalid size. */ + } + + while (tail-- && ((c = *utf8++) != 0)) { + if ((c & 0xc0) != 0x80) { + /* Invalid continuation char */ + utf8--; + break; + } + } } } - /* currently we don't support chars above U-FFFF */ + /* currently we don't support chars above U-FFFF */ return utf8; } @@ -971,10 +996,9 @@ void BDF_render_mix(void* screen_address, u32 screen_w, u32 x, u32 y, u32 v_alig continue; } - if(unicode < 128) - cmp = bdf_fontp[0][unicode].dwidth>>16; - else if(unicode >= start && unicode < end) - cmp = bdf_fontp[1][unicode -start].dwidth>>16; + /* If the text would go beyond the end of the line, go back to the + * start instead. */ + cmp = BDF_width16_ucs(unicode); if((screenp+cmp) >= line_start) { @@ -1074,10 +1098,7 @@ u32 BDF_cut_unicode(u16 *unicodes, u32 len, u32 width, u32 direction) while(len > 0) { unicode= unicodes[i]; - if(unicode < 128) - xw += bdf_fontp[0][unicode].dwidth>>16; - else if(unicode >= start && unicode < end) - xw += bdf_fontp[1][unicode -start].dwidth>>16; + xw += BDF_width16_ucs(unicode); if(xw >= width) break; i += direction; @@ -1096,10 +1117,7 @@ u32 BDF_cut_unicode(u16 *unicodes, u32 len, u32 width, u32 direction) while(len-- > 0) { unicode= unicodes[i]; - if(unicode < 128) - xw += bdf_fontp[0][unicode].dwidth>>16; - else if(unicode >= start && unicode < end) - xw += bdf_fontp[1][unicode -start].dwidth>>16; + xw += BDF_width16_ucs(unicode); i += direction; } diff --git a/source/nds/draw.h b/source/nds/draw.h index 3bdf5be..f40aa23 100644 --- a/source/nds/draw.h +++ b/source/nds/draw.h @@ -17,8 +17,8 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ -#ifndef __DRAW_H__ -#define __DRAW_H__ +#ifndef __DRAW_H__ +#define __DRAW_H__ #include "ds2_types.h" #include "ds2io.h" @@ -27,12 +27,12 @@ #define NDS_SCREEN_WIDTH 256 #define NDS_SCREEN_HEIGHT 192 #define NDS_SCREEN_SIZE (NDS_SCREEN_WIDTH*NDS_SCREEN_HEIGHT) - -#define COLOR16(red, green, blue) ((blue << 10) | (green << 5) | red) -#define GET_R16(color) (color & 0x1f) -#define GET_G16(color) ((color >> 5) & 0x1f) -#define GET_B16(color) ((color >> 10)& 0x1f) -#define COLOR32(red, green, blue) (0xff000000 | ((blue & 0xff) << 16) | ((green & 0xff) << 8) | (red & 0xff)) + +#define COLOR16(red, green, blue) ((blue << 10) | (green << 5) | red) +#define GET_R16(color) (color & 0x1f) +#define GET_G16(color) ((color >> 5) & 0x1f) +#define GET_B16(color) ((color >> 10)& 0x1f) +#define COLOR32(red, green, blue) (0xff000000 | ((blue & 0xff) << 16) | ((green & 0xff) << 8) | (red & 0xff)) #define RGB24_15(pixel) ((((*pixel) & 0xF8) << 7) |\ (((*(pixel+1)) & 0xF8) << 2) |\ @@ -44,36 +44,36 @@ #define PRINT_STRING(screen, str, fg_color, x, y) \ - BDF_render_string(screen, x, y, COLOR_TRANS, fg_color, str) \ + BDF_render_mix(screen, SCREEN_WIDTH, x, y, 0, COLOR_TRANS, fg_color, str) \ #define PRINT_STRING_SHADOW(screen, str, fg_color, x, y) \ - BDF_render_string(screen, x+1, y+1, 0, 0, str); \ - BDF_render_string(screen, x, y, 0, 0, str) \ + BDF_render_mix(screen, SCREEN_WIDTH, x+1, y+1, 0, 0, 0, str); \ + BDF_render_mix(screen, SCREEN_WIDTH, x, y, 0, 0, 0, str) \ #define PRINT_STRING_BG(screen, str, fg_color, bg_color, x, y) \ - BDF_render_string(screen, x, y, bg_color, fg_color, str) \ + BDF_render_mix(screen, SCREEN_WIDTH, x, y, 0, bg_color, fg_color, str) \ + +// #define PRINT_STRING_BG_UTF8(screen, utf8, fg_color, bg_color, x, y) \ +// BDF_render_mix(screen, SCREEN_WIDTH, x, y, 0, bg_color, fg_color, utf8) \ -#define PRINT_STRING_BG_UTF8(screen, utf8, fg_color, bg_color, x, y) \ - BDF_render_mix(screen, SCREEN_WIDTH, x, y, 0, bg_color, fg_color, utf8) \ - //colors -#define COLOR_TRANS COLOR16(31, 31, 63) -#define COLOR_WHITE COLOR16(31, 31, 31) -#define COLOR_BLACK COLOR16( 0, 0, 0) -#define COLOR_TEXT COLOR16(31, 31, 31) -#define COLOR_PROGRESS_TEXT COLOR16( 0, 0, 0) -#define COLOR_PROGRESS_BAR COLOR16(15, 15, 15) -#define COLOR_ERROR COLOR16(31, 0, 0) -#define COLOR_BG COLOR16(2, 4, 10) -#define COLOR_BG32 COLOR32(2*8, 4*8, 10*8) -#define COLOR_ROM_INFO COLOR16(22, 18, 26) -#define COLOR_ACTIVE_ITEM COLOR16(31, 31, 31) -#define COLOR_INACTIVE_ITEM COLOR16(13, 20, 18) -#define COLOR_HELP_TEXT COLOR16(16, 20, 24) -#define COLOR_DIALOG COLOR16(31, 31, 31) -#define COLOR_DIALOG_SHADOW COLOR16( 0, 2, 8) -#define COLOR_FRAME COLOR16( 0, 0, 0) +#define COLOR_TRANS COLOR16(31, 31, 63) +#define COLOR_WHITE COLOR16(31, 31, 31) +#define COLOR_BLACK COLOR16( 0, 0, 0) +#define COLOR_TEXT COLOR16(31, 31, 31) +#define COLOR_PROGRESS_TEXT COLOR16( 0, 0, 0) +#define COLOR_PROGRESS_BAR COLOR16(15, 15, 15) +#define COLOR_ERROR COLOR16(31, 0, 0) +#define COLOR_BG COLOR16(2, 4, 10) +#define COLOR_BG32 COLOR32(2*8, 4*8, 10*8) +#define COLOR_ROM_INFO COLOR16(22, 18, 26) +#define COLOR_ACTIVE_ITEM COLOR16(31, 31, 31) +#define COLOR_INACTIVE_ITEM COLOR16(13, 20, 18) +#define COLOR_HELP_TEXT COLOR16(16, 20, 24) +#define COLOR_DIALOG COLOR16(31, 31, 31) +#define COLOR_DIALOG_SHADOW COLOR16( 0, 2, 8) +#define COLOR_FRAME COLOR16( 0, 0, 0) #define COLOR_YESNO_TEXT COLOR16( 0, 0, 0) #define COLOR_GREEN COLOR16( 0, 31, 0 ) #define COLOR_GREEN1 COLOR16( 0, 24, 0 ) @@ -81,14 +81,14 @@ #define COLOR_GREEN3 COLOR16( 0, 12, 0 ) #define COLOR_GREEN4 COLOR16( 0, 6, 0 ) #define COLOR_RED COLOR16( 31, 0, 0 ) -#define COLOR_MSSG COLOR16( 16, 8, 29) -/****************************************************************************** - * +#define COLOR_MSSG COLOR16( 16, 8, 29) +/****************************************************************************** + * ******************************************************************************/ #ifdef __cplusplus extern "C" { #endif - + struct background{ char bgname[128]; char bgbuffer[256*192*2]; @@ -151,17 +151,17 @@ extern struct gui_iconlist gui_icon_list[]; #define ICON_CHTFILE gui_icon_list[38] #define ICON_MSG gui_icon_list[39] #define ICON_BUTTON gui_icon_list[40] - -/****************************************************************************** - * - ******************************************************************************/ + +/****************************************************************************** + * + ******************************************************************************/ extern void print_string_center(void* screen_addr, u32 sy, u32 color, u32 bg_color, char *str); -extern void print_string_shadow_center(void* screen_addr, u32 sy, u32 color, char *str); -extern void hline(u32 sx, u32 ex, u32 y, u32 color); -extern void hline_alpha(u32 sx, u32 ex, u32 y, u32 color, u32 alpha); -extern void vline(u32 x, u32 sy, u32 ey, u32 color); -extern void vline_alpha(u32 x, u32 sy, u32 ey, u32 color, u32 alpha); -extern void drawbox(void* screen_address, u32 sx, u32 sy, u32 ex, u32 ey, u32 color); +extern void print_string_shadow_center(void* screen_addr, u32 sy, u32 color, char *str); +extern void hline(u32 sx, u32 ex, u32 y, u32 color); +extern void hline_alpha(u32 sx, u32 ex, u32 y, u32 color, u32 alpha); +extern void vline(u32 x, u32 sy, u32 ey, u32 color); +extern void vline_alpha(u32 x, u32 sy, u32 ey, u32 color, u32 alpha); +extern void drawbox(void* screen_address, u32 sx, u32 sy, u32 ex, u32 ey, u32 color); extern void drawboxfill(void* screen_address, u32 sx, u32 sy, u32 ex, u32 ey, u32 color); extern void draw_selitem(void* screen_address, u32 x, u32 y, u32 color, u32 active); extern void draw_message(void* screen_address, u16 *screen_bg, u32 sx, u32 sy, u32 ex, u32 ey, @@ -173,19 +173,19 @@ extern void draw_string_vcenter(void* screen_address, u32 sx, u32 sy, u32 width, extern u32 draw_hscroll_init(void* screen_address, u32 sx, u32 sy, u32 width, u32 color_bg, u32 color_fg, char *string); extern u32 draw_hscroll(u32 index, s32 scroll_val); -extern void draw_hscroll_over(u32 index); -extern void boxfill_alpha(u32 sx, u32 sy, u32 ex, u32 ey, u32 color, u32 alpha); -extern void init_progress(enum SCREEN_ID screen, u32 total, char *text); -extern void update_progress(void); -extern void show_progress(char *text); -extern void scrollbar(void* screen_addr, u32 sx, u32 sy, u32 ex, u32 ey, u32 all, u32 view, u32 now); +extern void draw_hscroll_over(u32 index); +extern void boxfill_alpha(u32 sx, u32 sy, u32 ex, u32 ey, u32 color, u32 alpha); +extern void init_progress(enum SCREEN_ID screen, u32 total, char *text); +extern void update_progress(void); +extern void show_progress(char *text); +extern void scrollbar(void* screen_addr, u32 sx, u32 sy, u32 ex, u32 ey, u32 all, u32 view, u32 now); extern u32 yesno_dialog(char *text); -extern u32 draw_yesno_dialog(enum SCREEN_ID screen, u32 sy, char *yes, char *no); -extern void msg_screen_init(const char *title); -extern void msg_screen_draw(); -extern void msg_printf(const char *text, ...); -extern void msg_screen_clear(void); -extern void msg_set_text_color(u32 color); +extern u32 draw_yesno_dialog(enum SCREEN_ID screen, u32 sy, char *yes, char *no); +extern void msg_screen_init(const char *title); +extern void msg_screen_draw(); +extern void msg_printf(const char *text, ...); +extern void msg_screen_clear(void); +extern void msg_set_text_color(u32 color); extern int icon_init(u32 language_id); extern int gui_change_icon(u32 language_id); @@ -203,5 +203,5 @@ extern void blit_to_screen(void* screen_addr, u16 *src, u32 w, u32 h, u32 dest_x } #endif -#endif //__DRAW_H__ - +#endif //__DRAW_H__ + diff --git a/source/nds/gui.c b/source/nds/gui.c index af04c74..b1b9ce5 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -40,10 +40,11 @@ char rom_path[MAX_PATH]; char gamepak_name[MAX_PATH]; char gcheat_filename[MAX_PATH]; -char *lang[2] = +char *lang[3] = { "English", // 0 "简体中文", // 1 + "Français", // 2 }; /****************************************************************************** @@ -1937,7 +1938,7 @@ u32 menu(u16 *screen) else color= COLOR_INACTIVE_ITEM; - PRINT_STRING_BG_UTF8(down_screen_addr, line_buffer, color, COLOR_TRANS, 23, 40 + line[i]*27); + PRINT_STRING_BG(down_screen_addr, line_buffer, color, COLOR_TRANS, 23, 40 + line[i]*27); } int slot_index; @@ -1948,7 +1949,7 @@ u32 menu(u16 *screen) slot_index= get_savestate_slot(); sprintf(line_buffer, "%d", (slot_index+2) > SAVE_STATE_SLOT_NUM ? SAVE_STATE_SLOT_NUM : (slot_index+2)); - PRINT_STRING_BG_UTF8(down_screen_addr, line_buffer, COLOR_INACTIVE_ITEM, COLOR_TRANS, 146, 40 + 0*27); + PRINT_STRING_BG(down_screen_addr, line_buffer, COLOR_INACTIVE_ITEM, COLOR_TRANS, 146, 40 + 0*27); if(current_option_num == 1) selected = slot_index+1; @@ -2006,7 +2007,7 @@ u32 menu(u16 *screen) else color= COLOR_INACTIVE_ITEM; - PRINT_STRING_BG_UTF8(down_screen_addr, line_buffer, color, COLOR_TRANS, 23, 40 + line[i]*27); + PRINT_STRING_BG(down_screen_addr, line_buffer, color, COLOR_TRANS, 23, 40 + line[i]*27); } if(current_option_num == 2) @@ -2578,7 +2579,7 @@ u32 menu(u16 *screen) pt = strrchr(tmp_buf, ')'); strcat(line_buffer, pt); - PRINT_STRING_BG_UTF8(down_screen_addr, line_buffer, color, COLOR_TRANS, 26, 40 + display_option-> line_number*27); + PRINT_STRING_BG(down_screen_addr, line_buffer, color, COLOR_TRANS, 26, 40 + display_option-> line_number*27); } void dynamic_cheat_menu_end() @@ -2801,7 +2802,7 @@ u32 menu(u16 *screen) mm = *(display_option->current_option); sprintf(line_buffer, *(display_option->display_string), str[mm]); - PRINT_STRING_BG_UTF8(down_screen_addr, line_buffer, color, COLOR_TRANS, 27, + PRINT_STRING_BG(down_screen_addr, line_buffer, color, COLOR_TRANS, 27, 38 + (display_option-> line_number)*32); } @@ -2913,7 +2914,7 @@ u32 menu(u16 *screen) strcpy(line_buffer, *(display_option->display_string)); line_num= display_option-> line_number; - PRINT_STRING_BG_UTF8(down_screen_addr, line_buffer, COLOR_INACTIVE_ITEM, COLOR_TRANS, 27, + PRINT_STRING_BG(down_screen_addr, line_buffer, COLOR_INACTIVE_ITEM, COLOR_TRANS, 27, 40 + (display_option->line_number)*27); num_byte = freespace; @@ -2945,7 +2946,7 @@ u32 menu(u16 *screen) strcat(line_buffer, ".0 GB"); } - PRINT_STRING_BG_UTF8(down_screen_addr, line_buffer, COLOR_INACTIVE_ITEM, COLOR_TRANS, 147, + PRINT_STRING_BG(down_screen_addr, line_buffer, COLOR_INACTIVE_ITEM, COLOR_TRANS, 147, 40 + (display_option->line_number)*27); } @@ -2965,7 +2966,7 @@ u32 menu(u16 *screen) char *enable_disable_options[] = { (char*)&msg[MSG_EN_DIS_ABLE_0], (char*)&msg[MSG_EN_DIS_ABLE_1] }; - char *language_options[] = { (char*)&lang[0], (char*)&lang[1] }; + char *language_options[] = { (char*) &lang[0], (char*) &lang[1], (char*) &lang[2] }; char *keyremap_options[] = {(char*)&msg[MSG_KEY_MAP_NONE], (char*)&msg[MSG_KEY_MAP_A], (char*)&msg[MSG_KEY_MAP_B], (char*)&msg[MSG_KEY_MAP_SL], (char*)&msg[MSG_KEY_MAP_ST], (char*)&msg[MSG_KEY_MAP_RT], @@ -3124,7 +3125,7 @@ u32 menu(u16 *screen) /* 01 */ NUMERIC_SELECTION_OPTION(NULL, &msg[MSG_SUB_MENU_42], &clock_speed_number, 6, NULL, 1), /* 02 */ STRING_SELECTION_OPTION(language_set, NULL, &msg[MSG_SUB_MENU_41], language_options, - &emu_config.language, 2, NULL, ACTION_TYPE, 2), + &emu_config.language, 3 /* number of possibilities */, NULL, ACTION_TYPE, 2), /* 03 */ STRING_SELECTION_OPTION(NULL, show_card_space, &msg[MSG_SUB_MENU_43], NULL, &desert, 2, NULL, PASSIVE_TYPE | HIDEN_TYPE, 3), @@ -3582,7 +3583,7 @@ u32 menu(u16 *screen) else color= COLOR_INACTIVE_ITEM; - PRINT_STRING_BG_UTF8(down_screen_addr, line_buffer, color, COLOR_TRANS, 26, 37 + line_num*32); + PRINT_STRING_BG(down_screen_addr, line_buffer, color, COLOR_TRANS, 26, 37 + line_num*32); } void game_fastforward() @@ -3758,7 +3759,7 @@ u32 menu(u16 *screen) else color= COLOR_INACTIVE_ITEM; - PRINT_STRING_BG_UTF8(down_screen_addr, line_buffer, color, COLOR_TRANS, 23, 40 + i*27); + PRINT_STRING_BG(down_screen_addr, line_buffer, color, COLOR_TRANS, 23, 40 + i*27); } } } @@ -4204,6 +4205,7 @@ int load_language_msg(char *filename, u32 language) switch(language) { case ENGLISH: + default: strcpy(start, "STARTENGLISH"); strcpy(end, "ENDENGLISH"); cmplen= 12; @@ -4213,10 +4215,10 @@ int load_language_msg(char *filename, u32 language) strcpy(end, "ENDCHINESESIM"); cmplen= 15; break; - default: - strcpy(start, "STARTENGLISH"); - strcpy(end, "ENDENGLISH"); - cmplen= 12; + case FRENCH: + strcpy(start, "STARTFRENCH"); + strcpy(end, "ENDFRENCH"); + cmplen= 11; break; } //find the start flag @@ -4898,7 +4900,9 @@ void gui_init(u32 lang_id) flag = load_font(); if(0 != flag) { - err_msg(DOWN_SCREEN, "initial font library error, press any key to exit\n"); + char message[128]; + sprintf(message, "Font library initialisation error %d, press any key to exit\n", flag); + err_msg(DOWN_SCREEN, message); goto gui_init_err; } diff --git a/source/nds/message.h b/source/nds/message.h index fc6bd33..9292d3f 100644 --- a/source/nds/message.h +++ b/source/nds/message.h @@ -165,7 +165,7 @@ enum MSG enum LANGUAGE{ ENGLISH, CHINESE_SIMPLIFIED, - CHINESE_TRADITIONAL + FRENCH }; char *msg[MSG_END+1]; -- cgit v1.2.3 From 100c3bd9e9f9e7fc809434706ddcc2fde96143af Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Wed, 19 Dec 2012 18:49:13 -0500 Subject: Make it easier to add new translations to the menu. * source/nds/gui.c: Calculate the number of options based on the array size of language_otions. --- source/nds/gui.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index b1b9ce5..3201665 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -3125,7 +3125,7 @@ u32 menu(u16 *screen) /* 01 */ NUMERIC_SELECTION_OPTION(NULL, &msg[MSG_SUB_MENU_42], &clock_speed_number, 6, NULL, 1), /* 02 */ STRING_SELECTION_OPTION(language_set, NULL, &msg[MSG_SUB_MENU_41], language_options, - &emu_config.language, 3 /* number of possibilities */, NULL, ACTION_TYPE, 2), + &emu_config.language, sizeof(language_options) / sizeof(language_options[0]) /* number of possible languages */, NULL, ACTION_TYPE, 2), /* 03 */ STRING_SELECTION_OPTION(NULL, show_card_space, &msg[MSG_SUB_MENU_43], NULL, &desert, 2, NULL, PASSIVE_TYPE | HIDEN_TYPE, 3), -- cgit v1.2.3 From 80858801300a2f48ad250721a79ebc7b1b0aba92 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Thu, 20 Dec 2012 18:10:38 -0500 Subject: Remove the SNES Open Bus behaviour by default. Also simplify translation again. SNES Open Bus is a quirk of the memory subsystem that allow reads of invalid addresses to return the last byte read from memory. However, it is seldom needed by a game, and it costs 1 to 3 MIPS instructions per SNES instruction to emulate. If you need SNES Open Bus, you can remove -DNO_OPEN_BUS from the Makefile. --- source/nds/gui.c | 8 ++++---- source/nds/message.h | 2 ++ 2 files changed, 6 insertions(+), 4 deletions(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index 3201665..61a3b58 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -40,6 +40,8 @@ char rom_path[MAX_PATH]; char gamepak_name[MAX_PATH]; char gcheat_filename[MAX_PATH]; +// If adding a language, make sure you update the size of the array in +// message.h too. char *lang[3] = { "English", // 0 @@ -2966,8 +2968,6 @@ u32 menu(u16 *screen) char *enable_disable_options[] = { (char*)&msg[MSG_EN_DIS_ABLE_0], (char*)&msg[MSG_EN_DIS_ABLE_1] }; - char *language_options[] = { (char*) &lang[0], (char*) &lang[1], (char*) &lang[2] }; - char *keyremap_options[] = {(char*)&msg[MSG_KEY_MAP_NONE], (char*)&msg[MSG_KEY_MAP_A], (char*)&msg[MSG_KEY_MAP_B], (char*)&msg[MSG_KEY_MAP_SL], (char*)&msg[MSG_KEY_MAP_ST], (char*)&msg[MSG_KEY_MAP_RT], (char*)&msg[MSG_KEY_MAP_LF], (char*)&msg[MSG_KEY_MAP_UP], (char*)&msg[MSG_KEY_MAP_DW], @@ -3124,8 +3124,8 @@ u32 menu(u16 *screen) //CPU speed /* 01 */ NUMERIC_SELECTION_OPTION(NULL, &msg[MSG_SUB_MENU_42], &clock_speed_number, 6, NULL, 1), - /* 02 */ STRING_SELECTION_OPTION(language_set, NULL, &msg[MSG_SUB_MENU_41], language_options, - &emu_config.language, sizeof(language_options) / sizeof(language_options[0]) /* number of possible languages */, NULL, ACTION_TYPE, 2), + /* 02 */ STRING_SELECTION_OPTION(language_set, NULL, &msg[MSG_SUB_MENU_41], lang, + &emu_config.language, sizeof(lang) / sizeof(lang[0]) /* number of possible languages */, NULL, ACTION_TYPE, 2), /* 03 */ STRING_SELECTION_OPTION(NULL, show_card_space, &msg[MSG_SUB_MENU_43], NULL, &desert, 2, NULL, PASSIVE_TYPE | HIDEN_TYPE, 3), diff --git a/source/nds/message.h b/source/nds/message.h index 9292d3f..4a0acd2 100644 --- a/source/nds/message.h +++ b/source/nds/message.h @@ -168,6 +168,8 @@ enum LANGUAGE{ FRENCH }; +extern char* lang[3]; // Allocated in gui.c, needs to match the languages ^ + char *msg[MSG_END+1]; char msg_data[16 * 1024]; -- cgit v1.2.3 From 8a4343ff8e4114f19f034130a4b841a6b9a98217 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Thu, 20 Dec 2012 19:34:51 -0500 Subject: Bump the version number for NDSSFC. * gui.c: #define NDSSFC_VERSION "1.08". --- source/nds/gui.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index 61a3b58..64953be 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -54,7 +54,7 @@ char *lang[3] = ******************************************************************************/ #define SUBMENU_ROW_NUM 6 -#define NDSSFC_VERSION "1.07" +#define NDSSFC_VERSION "1.08" #define SAVE_STATE_SLOT_NUM 10 -- cgit v1.2.3 From 712c249e8c2b614555a6492b520244fe12cd1910 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Thu, 20 Dec 2012 23:52:09 -0500 Subject: Simplify the GUI code. * gui.c: Simplify row and column checks when handling touch events. * draw.c, err_msg: Use ConsoleInit instead of a custom drawstring function when an initialisation error that is NOT related to DS2 I/O occurs. This allows \r\n to work. * gui.c, initialisation: Remove the Engrish in the "initial error" messages. Make them appear in English and French. Unfortunately, the console doesn't support Chinese characters, and I don't know Chinese. --- source/nds/draw.c | 54 +------------- source/nds/gui.c | 219 ++++++++++++++++++------------------------------------ 2 files changed, 74 insertions(+), 199 deletions(-) (limited to 'source/nds') diff --git a/source/nds/draw.c b/source/nds/draw.c index 6223c6e..b6c3f9b 100644 --- a/source/nds/draw.c +++ b/source/nds/draw.c @@ -1273,57 +1273,11 @@ void show_log(void* screen_addr) } /*************************************************************/ -extern const unsigned char font_map[128][8]; - -//font size 8*8 -static inline void drawfont(unsigned short *addr, unsigned short f_color, unsigned short b_color, unsigned char ch) -{ - unsigned char *dot_map; - unsigned int j, k; - unsigned char dot; - unsigned short *dst; - - dot_map = (unsigned char*)font_map[ch&0x7F]; - - for(j= 0; j < 8; j++) - { - dot = *dot_map++; - dst = addr + j*SCREEN_WIDTH; - for(k = 0; k < 8; k++) - *dst++ = (dot & (0x80>>k)) ? f_color : b_color; - } -} - -static void drawstring(unsigned int x, unsigned int y, enum SCREEN_ID screen, char *string, - unsigned short f_color, unsigned short b_color) -{ - unsigned short *scr_addr, *dst; - - if(screen & UP_MASK) - scr_addr = up_screen_addr; - else - scr_addr = down_screen_addr; - - if(x>= 32 || y>= 24) return; - - while(*string) - { - dst = scr_addr + (y*8)*SCREEN_WIDTH + x*8; - drawfont(dst, f_color, b_color, *string++); - - x += 1; - if(x>= 32) - { - x = 0; - y+= 1; - if(y >= 24) break; - } - } -} - void err_msg(enum SCREEN_ID screen, char *msg) { - drawstring(0, 0, screen, msg, COLOR16(16, 16, 16), COLOR16(0, 0, 0)); + // A wild console appeared! + ConsoleInit(RGB15(31, 31, 31), RGB15(0, 0, 0), UP_SCREEN, 512); + printf(msg); } /* @@ -1372,5 +1326,3 @@ void blit_to_screen(void* screen_addr, u16 *src, u32 w, u32 h, u32 dest_x, u32 d *dst++ = *src++; } } - - diff --git a/source/nds/gui.c b/source/nds/gui.c index 64953be..f2d9af6 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -403,13 +403,14 @@ static int sort_function(const void *dest_str_ptr, const void *src_str_ptr) char *dest_str = *((char **)dest_str_ptr); char *src_str = *((char **)src_str_ptr); + // For files and directories, . and .. sort first. if(src_str[0] == '.') return 1; if(dest_str[0] == '.') return -1; - return strcasecmp(dest_str, src_str); + return strcasecmp(dest_str, src_str); } static int my_array_partion(void *array, int left, int right) @@ -464,9 +465,9 @@ static void strupr(char *str) } } -//****************************************************************************** +// ****************************************************************************** // get file list -//****************************************************************************** +// ****************************************************************************** #define FILE_LIST_MAX 512 #define DIR_LIST_MAX 64 #define NAME_MEM_SIZE (320*64) @@ -628,7 +629,7 @@ static int load_file_list(struct FILE_LIST_INFO *filelist_infop) strcpy(current_dir_name, filelist_infop -> current_path); - //* path formate should be: "fat:/" or "fat:/dir0" or "fat:", not "fat:/dir0/" + // path formate should be: "fat:/" or "fat:/dir0" or "fat:", not "fat:/dir0/" current_dir = opendir(current_dir_name); //Open directory faiure if(current_dir == NULL) { @@ -792,31 +793,23 @@ s32 load_file(char **wildcards, char *result, char *default_dir_name) { case CURSOR_TOUCH: ds2_getrawInput(&inputdata); - if(inputdata.y <= 33) + // ___ 33 This screen has 6 possible rows. Touches + // ___ 60 above or below these are ignored. + // . . . (+27) + // ___ 192 + if(inputdata.y <= 33 || inputdata.y > 192) break; - else if(inputdata.y <= 60) - mod = 0; - else if(inputdata.y <= 87) - mod = 1; - else if(inputdata.y <= 114) - mod = 2; - else if(inputdata.y <= 141) - mod = 3; - else if(inputdata.y <= 168) - mod = 4; - else if(inputdata.y <= 192) - mod = 5; else - break; - + mod = (inputdata.y - 33) / 27; + if(selected_item_on_list - selected_item_on_screen + mod >= total_items_num) break; - + selected_item_on_list = selected_item_on_list - selected_item_on_screen + mod; - + if(selected_item_on_list + 1 <= num_files) { - //The ".." directory + //The ".." directory is the parent if(!strcasecmp(file_list[selected_item_on_list], "..")) { char *ext_pos; @@ -852,7 +845,7 @@ s32 load_file(char **wildcards, char *result, char *default_dir_name) case CURSOR_UP: redraw = 1; if(selected_item_on_screen > 0) - { + { //Not the first item on list selected_item_on_list -= 1; //Selected item on screen center @@ -2868,7 +2861,7 @@ u32 menu(u16 *screen) draw_message(down_screen_addr, bg_screenp, 28, 31, 227, 165, bg_screenp_color); draw_string_vcenter(down_screen_addr, 36, 80, 190, COLOR_MSSG, msg[MSG_EMU_VERSION0]); - sprintf(line_buffer, "%s %s", msg[MSG_EMU_VERSION1], NDSSFC_VERSION); + sprintf(line_buffer, "%s %s", msg[MSG_EMU_VERSION1], NDSSFC_VERSION); draw_string_vcenter(down_screen_addr, 36, 95, 190, COLOR_MSSG, line_buffer); ds2_flipScreen(DOWN_SCREEN, 2); @@ -3461,7 +3454,7 @@ u32 menu(u16 *screen) { draw_hscroll_over(current_option_num-1); ext_pos= strrchr(emu_config.latest_file[current_option_num-1], '/'); - draw_hscroll_init(down_screen_addr, 26, 35 + (current_option_num-1)*27, 200, + draw_hscroll_init(down_screen_addr, 26, 40 + (current_option_num-1)*27, 200, COLOR_TRANS, COLOR_INACTIVE_ITEM, ext_pos+1); } @@ -3780,26 +3773,13 @@ u32 menu(u16 *screen) /* Main menu */ if(current_menu == &main_menu) { - if(inputdata.x <= 86 && inputdata.y <= 80) - current_option_num = 0; - else if(inputdata.x <= 172 && inputdata.y <= 80) - current_option_num = 1; - else if(inputdata.x <= 256 && inputdata.y <= 80) - current_option_num = 2; - else if(inputdata.x <= 86 && inputdata.y <= 160) - current_option_num = 3; - else if(inputdata.x <= 172 && inputdata.y <= 160) - current_option_num = 4; - else if(inputdata.x <= 256 && inputdata.y <= 160) - current_option_num = 5; - else if(inputdata.x <= 86 && inputdata.y <= 192) - current_option_num = 6; - else if(inputdata.x <= 172 && inputdata.y <= 192) - current_option_num = 7; - else if(inputdata.x <= 256 && inputdata.y <= 192) - current_option_num = 8; - else - break; + // 0 86 172 256 + // _____ _____ _____ 0 + // |0VID_|1SAV_|2CHT_| 80 + // |3TLS_|4OPT_|5EXI_| 160 + // |6NEW_|7RET_|8RST_| 192 + + current_option_num = (inputdata.y / 80) * 3 + (inputdata.x / 86); current_option = current_menu->options + current_option_num; if(current_option -> option_type & HIDEN_TYPE) @@ -3818,31 +3798,22 @@ u32 menu(u16 *screen) && current_menu != (main_menu.options +6)->sub_menu && current_menu != ((main_menu.options +6)->sub_menu->options + 2)->sub_menu) { - if(inputdata.y <= 33) + if (inputdata.y <= 33 || inputdata.y > 192) break; - else if(inputdata.y <= 60) - current_option_num = 1; - else if(inputdata.y <= 87) - current_option_num = 2; - else if(inputdata.y <= 114) - current_option_num = 3; - else if(inputdata.y <= 141) - current_option_num = 4; - else if(inputdata.y <= 168) - current_option_num = 5; - else if(inputdata.y <= 192) - current_option_num = 6; - else - break; - + // ___ 33 This screen has 6 possible rows. Touches + // ___ 60 above or below these are ignored. + // . . . (+27) + // ___ 192 + current_option_num = (inputdata.y - 33) / 27; + current_option = current_menu->options + current_option_num; - + if(current_option -> option_type & HIDEN_TYPE) break; - + if(!current_option) break; - + if(current_menu->key_function) { gui_action = CURSOR_RIGHT; @@ -3885,33 +3856,16 @@ u32 menu(u16 *screen) u32 current_option_val = *(current_option->current_option); u32 old_option_val = current_option_val; - if(inputdata.x <= 25) - break; - else if(inputdata.x <= 45) - current_option_val = 0; - else if(inputdata.x <= 65) - current_option_val = 1; - else if(inputdata.x <= 86) - current_option_val = 2; - else if(inputdata.x <= 107) - current_option_val = 3; - else if(inputdata.x <= 128) - current_option_val = 4; - else if(inputdata.x <= 149) - current_option_val = 5; - else if(inputdata.x <= 170) - current_option_val = 6; - else if(inputdata.x <= 191) - current_option_val = 7; - else if(inputdata.x <= 212) - current_option_val = 8; - else if(inputdata.x <= 233) - current_option_val = 9; - else + if(inputdata.x <= 23 || inputdata.x > 233) break; - + // | | | | | | | | | | | + // 23 44 65 86 ... (+21) 233 + // This row has 10 cells for save states, each 21 + // pixels wide. + current_option_val = (inputdata.x - 23) / 21; + *(current_option->current_option) = current_option_val; - + if(current_option_val == old_option_val) { gui_action = CURSOR_SELECT; @@ -3952,33 +3906,16 @@ u32 menu(u16 *screen) u32 current_option_val = *(current_option->current_option); u32 old_option_val = current_option_val; - if(inputdata.x <= 25) - break; - else if(inputdata.x <= 45) - current_option_val = 0; - else if(inputdata.x <= 65) - current_option_val = 1; - else if(inputdata.x <= 86) - current_option_val = 2; - else if(inputdata.x <= 107) - current_option_val = 3; - else if(inputdata.x <= 128) - current_option_val = 4; - else if(inputdata.x <= 149) - current_option_val = 5; - else if(inputdata.x <= 170) - current_option_val = 6; - else if(inputdata.x <= 191) - current_option_val = 7; - else if(inputdata.x <= 212) - current_option_val = 8; - else if(inputdata.x <= 233) - current_option_val = 9; - else + if(inputdata.x <= 23 || inputdata.x > 233) break; - + // | | | | | | | | | | | + // 23 44 65 86 ... (+21) 233 + // This row has 10 cells for save states, each 21 + // pixels wide. + current_option_val = (inputdata.x - 23) / 21; + *(current_option->current_option) = current_option_val; - + if(current_option_val == old_option_val) { gui_action = CURSOR_SELECT; @@ -4004,25 +3941,16 @@ u32 menu(u16 *screen) || current_menu == (main_menu.options + 6)->sub_menu || current_menu == ((main_menu.options +6)->sub_menu->options + 2)->sub_menu) { - if(inputdata.y <= 33) + if (inputdata.y <= 33 || inputdata.y > 192) break; - else if(inputdata.y <= 60) - current_option_num = 1; - else if(inputdata.y <= 87) - current_option_num = 2; - else if(inputdata.y <= 114) - current_option_num = 3; - else if(inputdata.y <= 141) - current_option_num = 4; - else if(inputdata.y <= 168) - current_option_num = 5; - else if(inputdata.y <= 192) - current_option_num = 6; - else - break; - + // ___ 33 This screen has 6 possible rows. Touches + // ___ 60 above or below these are ignored. + // . . . (+27) The row between 33 and 60 is [1], though! + // ___ 192 + current_option_num = (inputdata.y - 33) / 27 + 1; + current_option = current_menu->options + current_option_num; - + if(current_option -> option_type & HIDEN_TYPE) break; else if(current_option->option_type & ACTION_TYPE) @@ -4150,12 +4078,9 @@ u32 menu(u16 *screen) set_cpu_clock(clock_speed_number); // mdelay(200); // Delete this delay - ds2_clearScreen(DOWN_SCREEN, 0); - ds2_flipScreen(DOWN_SCREEN, 1); - ds2_clearScreen(UP_SCREEN, 0); - ds2_flipScreen(UP_SCREEN, 1); - ds2_clearScreen(UP_SCREEN, 0); - ds2_flipScreen(UP_SCREEN, 1); + ds2_clearScreen(DUAL_SCREEN, 0); + ds2_flipScreen(DUAL_SCREEN, 1); + ds2_flipScreen(UP_SCREEN, 1); // Flip again because otherwise it flickers ds2_setBacklight(2); //save game config @@ -4855,7 +4780,7 @@ void gui_init(u32 lang_id) { int flag; - ds2_setCPUclocklevel(11); + ds2_setCPUclocklevel(13); // Crank it up. When the menu starts, -> 0. printf_clock(); //Find the "CATSFC" system directory @@ -4876,11 +4801,11 @@ void gui_init(u32 lang_id) strcpy(main_path, "fat:"); if(search_dir("CATSFC", main_path) == 0) { - printf("Dirctory find: %s\n", main_path); + printf("Found CATSFC directory\r\nDossier CATSFC trouve\r\n\r\n%s\r\n", main_path); } else { - err_msg(DOWN_SCREEN, "Can't fine CATSFC directory, press any key to exit\n"); + err_msg(DOWN_SCREEN, "/CATSFC: Directory missing\r\nPress any key to return to\r\nthe menu\r\n\r\n/CATSFC: Dossier manquant\r\nAppuyer sur une touche pour\r\nretourner au menu"); goto gui_init_err; } } @@ -4892,7 +4817,7 @@ void gui_init(u32 lang_id) flag = icon_init(lang_id); if(0 != flag) { - err_msg(DOWN_SCREEN, "some icon can't open when initial GUI, press any key to exit\n"); + err_msg(DOWN_SCREEN, "Some icons are missing\r\nLoad them onto your card\r\nPress any key to return to\r\nthe menu\r\n\r\nDes icones sont manquantes\r\nChargez-les sur votre carte\r\nAppuyer sur une touche pour\r\nretourner au menu"); goto gui_init_err; } @@ -4900,8 +4825,8 @@ void gui_init(u32 lang_id) flag = load_font(); if(0 != flag) { - char message[128]; - sprintf(message, "Font library initialisation error %d, press any key to exit\n", flag); + char message[512]; + sprintf(message, "Font library initialisation\r\nerror (%d)\r\nPress any key to return to\r\nthe menu\r\n\r\nErreur d'initalisation de la\r\npolice de caracteres (%d)\r\nAppuyer sur une touche pour\r\nretourner au menu", flag, flag); err_msg(DOWN_SCREEN, message); goto gui_init_err; } @@ -4912,13 +4837,14 @@ void gui_init(u32 lang_id) flag = load_language_msg(LANGUAGE_PACK, lang_id); if(0 != flag) { - err_msg(DOWN_SCREEN, "initial language package error, press any key to exit\n"); + char message[512]; + sprintf(message, "Language pack initialisation\r\nerror (%d)\r\nPress any key to return to\r\nthe menu\r\n\r\nErreur d'initalisation du\r\npack de langue (%d)\r\nAppuyer sur une touche pour\r\nretourner au menu", flag, flag); + err_msg(DOWN_SCREEN, message); goto gui_init_err; } initial_path_config(); - return; gui_init_err: @@ -4927,6 +4853,3 @@ gui_init_err: quit(); while(1); } - - - -- cgit v1.2.3 From 5585c035fbec86ee4bec79865357479142e94b9f Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Fri, 21 Dec 2012 00:05:07 -0500 Subject: Fix an off-by-one in the previous commit's touch handling code. --- source/nds/gui.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index f2d9af6..2f9e1d2 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -3802,9 +3802,9 @@ u32 menu(u16 *screen) break; // ___ 33 This screen has 6 possible rows. Touches // ___ 60 above or below these are ignored. - // . . . (+27) + // . . . (+27) The row between 33 and 60 is [1], though! // ___ 192 - current_option_num = (inputdata.y - 33) / 27; + current_option_num = (inputdata.y - 33) / 27 + 1; current_option = current_menu->options + current_option_num; -- cgit v1.2.3 From 3972512b2a5c25236ea3ba586621dba6e5b56361 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Fri, 21 Dec 2012 01:44:57 -0500 Subject: Looks like only having 'lang' crashes the options dialog. Restore the array of pointers. --- source/nds/gui.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index 2f9e1d2..bf85b67 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -49,6 +49,8 @@ char *lang[3] = "Français", // 2 }; +char *language_options[] = { (char *) &lang[0], (char *) &lang[1], (char *) &lang[2] }; + /****************************************************************************** * Macro definition ******************************************************************************/ @@ -3117,8 +3119,8 @@ u32 menu(u16 *screen) //CPU speed /* 01 */ NUMERIC_SELECTION_OPTION(NULL, &msg[MSG_SUB_MENU_42], &clock_speed_number, 6, NULL, 1), - /* 02 */ STRING_SELECTION_OPTION(language_set, NULL, &msg[MSG_SUB_MENU_41], lang, - &emu_config.language, sizeof(lang) / sizeof(lang[0]) /* number of possible languages */, NULL, ACTION_TYPE, 2), + /* 02 */ STRING_SELECTION_OPTION(language_set, NULL, &msg[MSG_SUB_MENU_41], language_options, + &emu_config.language, sizeof(language_options) / sizeof(language_options[0]) /* number of possible languages */, NULL, ACTION_TYPE, 2), /* 03 */ STRING_SELECTION_OPTION(NULL, show_card_space, &msg[MSG_SUB_MENU_43], NULL, &desert, 2, NULL, PASSIVE_TYPE | HIDEN_TYPE, 3), -- cgit v1.2.3 From a0d0c5e7a5bdc396b4c370a750273b6e3b963bb0 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Fri, 21 Dec 2012 03:50:10 -0500 Subject: Eliminate the latency of button press recognition, which was bad enough to lose keys entirely sometimes, and could otherwise delay a button press or release by 200 ms. This was the entire reason I created the fork, and I finally did it! It syncs the controls every scanline of a frame, which costs about 60,000 MIPS instructions per frame to deal with. Luckily, the processor runs at 396 MHz, which means the cost of checking the controls is 1% of the CPU's power. --- source/nds/ds2_main.c | 52 +++++++++++++++++++++++++-------------------------- source/nds/entry.cpp | 10 ++++++---- source/nds/gui.c | 1 + 3 files changed, 32 insertions(+), 31 deletions(-) (limited to 'source/nds') diff --git a/source/nds/ds2_main.c b/source/nds/ds2_main.c index 710215b..2d73313 100644 --- a/source/nds/ds2_main.c +++ b/source/nds/ds2_main.c @@ -15,19 +15,19 @@ * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - */ - -#include -#include "console.h" -#include "fs_api.h" + */ + +#include +#include "console.h" +#include "fs_api.h" #include "ds2io.h" #include "ds2_timer.h" #include "ds2_malloc.h" - -#define BLACK_COLOR RGB15(0, 0, 0) -#define WHITE_COLOR RGB15(31, 31, 31) - -extern int sfc_main (int argc, char **argv); + +#define BLACK_COLOR RGB15(0, 0, 0) +#define WHITE_COLOR RGB15(31, 31, 31) + +extern int sfc_main (int argc, char **argv); #if 0 void ddump_mem(unsigned char* addr, unsigned int len) @@ -42,24 +42,22 @@ void ddump_mem(unsigned char* addr, unsigned int len) } #endif +void ds2_main(void) +{ + int err; +ds2_setCPUclocklevel(13); + //Initial video and audio and other input and output + err = ds2io_initb(512, 22050, 0, 0); + if(err) goto _failure; - -void ds2_main(void) -{ - int err; -ds2_setCPUclocklevel(13); - //Initial video and audio and other input and output - err = ds2io_initb(512, 22050, 0, 0); - if(err) goto _failure; + //Initial file system + err = fat_init(); + if(err) goto _failure; - //Initial file system - err = fat_init(); - if(err) goto _failure; + //go to user main funtion + sfc_main (0, 0); - //go to user main funtion - sfc_main (0, 0); - _failure: - ds2_plug_exit(); -} - + ds2_plug_exit(); +} + diff --git a/source/nds/entry.cpp b/source/nds/entry.cpp index 24c0e03..467461b 100644 --- a/source/nds/entry.cpp +++ b/source/nds/entry.cpp @@ -90,6 +90,7 @@ void S9xParseDisplayArg (char **argv, int &ind, int) void S9xExit () { + ds2_setCPUclocklevel(13); // Crank it up to exit quickly if(Settings.SPC7110) (*CleanUp7110)(); @@ -382,15 +383,15 @@ void init_sfc_setting(void) Settings.SixteenBit = TRUE; Settings.SupportHiRes = FALSE; - Settings.NetPlay = FALSE; - Settings.ServerName [0] = 0; Settings.ThreadSound = FALSE; Settings.SoundSync = TRUE; Settings.AutoSaveDelay = 0; #ifdef _NETPLAY_SUPPORT + Settings.NetPlay = FALSE; + Settings.ServerName [0] = 0; Settings.Port = NP_DEFAULT_PORT; #endif - Settings.ApplyCheats =FALSE; + Settings.ApplyCheats = FALSE; Settings.TurboMode = FALSE; Settings.TurboSkipFrames = 40; Settings.StretchScreenshots = 1; @@ -1009,7 +1010,8 @@ unsigned int S9xReadJoypad (int which1) key |= (inputdata.key & (1< 679, though.) --- source/nds/bdf_font.c | 1 + source/nds/cheats3.cpp | 206 ------------------ source/nds/draw.c | 1 + source/nds/entry.cpp | 9 +- source/nds/gcheat.c | 574 ++++++++----------------------------------------- source/nds/gcheat.h | 47 +--- source/nds/gui.c | 93 ++++---- source/nds/gui.h | 72 +++---- 8 files changed, 173 insertions(+), 830 deletions(-) delete mode 100644 source/nds/cheats3.cpp (limited to 'source/nds') diff --git a/source/nds/bdf_font.c b/source/nds/bdf_font.c index b1e7ccd..773403a 100644 --- a/source/nds/bdf_font.c +++ b/source/nds/bdf_font.c @@ -18,6 +18,7 @@ */ //v1.1 +#include "port.h" #include #include "ds2_types.h" #include "ds2_malloc.h" diff --git a/source/nds/cheats3.cpp b/source/nds/cheats3.cpp deleted file mode 100644 index bdb5545..0000000 --- a/source/nds/cheats3.cpp +++ /dev/null @@ -1,206 +0,0 @@ -/* cheats3.cpp - * - * Copyright (C) 2010 dking - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public Licens e as - * published by the Free Software Foundation; either version 2 of - * the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - */ - -#include -#include -#include -#include "snes9x.h" -#include "cheats.h" -#include "memmap.h" -#include "gcheat.h" - -extern SCheatData Cheat; - -int S9xAddCheat_ex (unsigned int address, unsigned char* cheat_dat, unsigned int cheat_dat_len, - unsigned int cheat_cell_num, unsigned int part_id, unsigned int str_num) -{ - if(cheat_cell_num < MAX_CHEATS_T) - { - Cheat.c[cheat_cell_num].address = address; - Cheat.c[cheat_cell_num].enabled = FALSE; - - if(cheat_dat_len > 1) - memcpy(Cheat.c[cheat_cell_num].name, cheat_dat, cheat_dat_len); - else - Cheat.c[cheat_cell_num].byte = cheat_dat[0]; - - Cheat.c[cheat_cell_num].total_part = 0; //default are sub-part - Cheat.c[cheat_cell_num].part_id = part_id; - Cheat.c[cheat_cell_num].part_len = cheat_dat_len; - Cheat.c[cheat_cell_num].cheat_type = 0; //default are sub-part - Cheat.c[cheat_cell_num].name_id = str_num; - - return 0; - } - - return -1; -} - -void S9xAddCheat_ov(unsigned int cheat_cell_num, unsigned int total_part) -{ - if(cheat_cell_num < MAX_CHEATS_T) - { - Cheat.c[cheat_cell_num].total_part = total_part; //default are sub-part - Cheat.c[cheat_cell_num].cheat_type = 0x80; - } -} - -static unsigned int S9xGetSub_id(unsigned int start, unsigned int sub_part) -{ - unsigned int i, m, n; - - if(0 == sub_part) - return start; - - if((start+1) >= g_cheat_cell_num) - return start; - - m = 0; - for(i= start; i < g_cheat_cell_num; ) - { - n = Cheat.c[i].total_part; - i += n; - m += 1; - if(m == sub_part) break; - } - - return i; -} - -unsigned int S9xGetCheat_nameid(unsigned int start, unsigned int part) -{ -#if 0 - unsigned int m, n, i; - unsigned int ret; - unsigned int cell_num; - - cell_num = g_cheat_cell_num; - - ret = Cheat.c[start].name_id; - if((start+1) >= cell_num) - return ret; - - m = 0; - for(i = start; i < cell_num; ) { - if(m == part) break; - n = Cheat.c[i].total_part; - i += n; - m += 1; - } - - if(i < cell_num) - ret = Cheat.c[i].name_id; - - return ret; -#else - unsigned int i; - - i = S9xGetSub_id(start, part); - return Cheat.c[i].name_id; -#endif -} - -void S9xCheat_switch(unsigned int start, unsigned int sub_part, unsigned int enable) -{ - unsigned int i, m, n; - - if((start+1) >= g_cheat_cell_num) - return; - - i = S9xGetSub_id(start, sub_part); - m = Cheat.c[i].total_part; - for(n = 0; n < m; n++) - Cheat.c[i+n].enabled = enable; -} - -static inline void S9xApplyCheat_ex(unsigned int start, unsigned int num) -{ - unsigned int i, m; - unsigned int address, len; - - for(i = 0; i < num; i++) - { - address = Cheat.c[start+i].address; - len = Cheat.c[start+i].part_len; - - int block = (address >> MEMMAP_SHIFT) & MEMMAP_MASK; - unsigned char *ptr = Memory.Map [block]; - - if(1 == len) - { - if (ptr >= (uint8 *) CMemory::MAP_LAST) - *(ptr + (address & 0xffff)) = Cheat.c[start+i].byte; - else - S9xSetByte (Cheat.c[start+i].byte, address); - } - else - { - for(m= 0; m < len; m++) - { - if (ptr >= (uint8 *) CMemory::MAP_LAST) - *(ptr + (address & 0xffff)) = Cheat.c[start+i].name[m]; - else - S9xSetByte (Cheat.c[start+i].name[m], address); - } - } - } -} - -void S9xApplyCheats_ex(void) -{ - unsigned int i, m, n; - - if (Settings.ApplyCheats) - { - for(i= 0; i < g_cheat_cell_num; i++) - { - m = Cheat.c[i].total_part; - if(Cheat.c[i].enabled) - S9xApplyCheat_ex(i, m); - i += m; - } - } -} - -#if 1 -extern "C" void dump_mem(unsigned char* addr, unsigned int len); - -void S9x_dumpcheat(unsigned int id) -{ - cprintf("\nid %d------------\n", id); - cprintf("total %d; part %d\n", Cheat.c[id].total_part, Cheat.c[id].part_id); - cprintf("address: %08x; data: %d\n", Cheat.c[id].address, Cheat.c[id].part_len); - if(Cheat.c[id].part_len == 1) - cprintf("data: %02x\n", Cheat.c[id].byte); - else - dump_mem((unsigned char*)Cheat.c[id].name, Cheat.c[id].part_len); - cprintf(" ------\n"); -} -#endif - -void S9xCheat_Disable(void) -{ - Settings.ApplyCheats = FALSE; -} - -void S9xCheat_Enable(void) -{ - Settings.ApplyCheats = TRUE; -} - diff --git a/source/nds/draw.c b/source/nds/draw.c index b6c3f9b..9d1b8ec 100644 --- a/source/nds/draw.c +++ b/source/nds/draw.c @@ -22,6 +22,7 @@ * draw.cpp * basic program to draw some graphic ******************************************************************************/ +#include "port.h" #include #include #include "ds2_malloc.h" diff --git a/source/nds/entry.cpp b/source/nds/entry.cpp index 467461b..ea5f6ce 100644 --- a/source/nds/entry.cpp +++ b/source/nds/entry.cpp @@ -97,7 +97,8 @@ void S9xExit () S9xSetSoundMute (TRUE); S9xDeinitDisplay (); Memory.SaveSRAM (S9xGetFilename (".srm")); - S9xSaveCheatFile (S9xGetFilename (".cht")); + // S9xSaveCheatFile (S9xGetFilename (".chb")); // cheat binary file + // Do this when loading a cheat file! Memory.Deinit (); S9xDeinitAPU (); @@ -258,7 +259,6 @@ const char *S9xGetSnapshotDirectory () return ((const char*)DEFAULT_RTS_DIR); } - const char *S9xGetFilename (const char *ex) { static char filename [PATH_MAX + 1]; @@ -391,7 +391,7 @@ void init_sfc_setting(void) Settings.ServerName [0] = 0; Settings.Port = NP_DEFAULT_PORT; #endif - Settings.ApplyCheats = FALSE; + Settings.ApplyCheats = TRUE; Settings.TurboMode = FALSE; Settings.TurboSkipFrames = 40; Settings.StretchScreenshots = 1; @@ -457,8 +457,7 @@ int load_gamepak(char* file) Memory.LoadSRAM (S9xGetFilename (".srm")); // mdelay(50); // Delete this delay - //S9xLoadCheatFile (S9xGetFilename (".cht")); - S9xCheat_Disable(); + S9xLoadCheatFile (S9xGetFilename (".chb")); // cheat binary file, as opposed to text #ifdef _NETPLAY_SUPPORT if (strlen (Settings.ServerName) == 0) diff --git a/source/nds/gcheat.c b/source/nds/gcheat.c index 062ce9d..648bfda 100644 --- a/source/nds/gcheat.c +++ b/source/nds/gcheat.c @@ -1,9 +1,9 @@ /* gcheat.c * - * Copyright (C) 2010 dking + * Copyright (C) 2012 GBAtemp user Nebuleon. * * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public Licens e as + * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 2 of * the License, or (at your option) any later version. * @@ -17,511 +17,111 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ +#include "port.h" #include "string.h" #include "fs_api.h" #include "ds2_malloc.h" #include "gcheat.h" #include "charsets.h" +#include "cheats.h" -#define MAX_SFCCHEAT_NAME 24 +extern struct SCheatData Cheat; - -//GCHEAT_STRUCT gcheat[MAX_CHEATS]; -unsigned int g_cheat_cell_num; -unsigned int g_cheat_num; - -#define SKIP_SPACE(pt) while(' ' == *pt) pt++ - -static unsigned char* check_is_cht(unsigned char *str) -{ - unsigned char *pt, *pt1; - - if(*str == '\0') return NULL; - - pt = str; - while(*pt == ' ') pt++; //Skip leading space - if(*pt != '[') return NULL; //valid entry should be:[string] - - pt1 = strrchr(str, ']'); - if(pt1 == NULL) return NULL; - - while(*(--pt1) == ' '); - *(pt1+1) = '\0'; //Cut trailing space between string and ']' - - while(*(++pt) == ' '); //Cut space between '[' and string - - return pt; -} - -static unsigned int sscanf_hex_value(unsigned char* str, unsigned int *value) -{ - unsigned char *pt; - unsigned int tmp; - unsigned char ch; - unsigned int len; - - pt = str; - len = 0; - tmp = 0; - while(*pt && len < 8) - { - ch = *pt; - if(ch >= 'a' && ch <= 'f') ch = ch - 'a' + 0xa; - else if(ch >= 'A' && ch <= 'F') ch = ch - 'A' + 0xa; - else if(ch >= '0' && ch <= '9') ch = ch - '0'; - else if(ch == ' ') continue; - else break; - - tmp = (tmp << 4) | ch; - pt++; - len += 1; - } - - *value = tmp; - return len; -} - -/* -* Convert the src string to UTF8 coding dst string, and cut to length -*/ -int string2utf8(unsigned char *src, unsigned char* dst, unsigned int length) +// Reads a cheat text file in BSNES's format. +int NDSSFCLoadCheatFile(const char* filename) { - unsigned char *pt; - unsigned char ch; - unsigned short ucode; - unsigned int type; - unsigned int len; + FILE* fp = fopen(filename, "r"); + if (fp == NULL) + return -1; - len = 0; - type = 0; - pt = src; - while(*pt) + S9xDeleteCheats(); + + // The construction is "a","b","c" . + // a is ignored. In BSNES, it decides whether the code is enabled. + // b is a series of codes separated by +. Each of the codes is in the form + // accepted by the Game Genie, Pro Action Replay, or the GoldFinger. + // c is the cheat's description. + char line[256], code[24]; + char *description, *codes_ptr; + uint32 address; + uint8 byte; + uint8 bytes [3]; + bool8 sram; + uint8 num_bytes; + + while (fgets(line, sizeof(line), fp)) { - pt = utf8decode(pt, &ucode); - if(ucode < 0x4e00) { - if(ucode == 0 || ucode > 0x7F) { - type = 1; - break; - } - } else if(ucode > 0x9FCF) { - type = 1; - break; + char* ptr = &line[0]; + // Ignore a. + while (*ptr && *ptr != ',') + ptr++; + // If there was no comma, declare a bad file. + if (*ptr == '\0') { + fclose(fp); + return -2; } - else - len++; - - if(len >= 3) break; //There is enough UTF8, so it is, to save time(>_*) - } + *ptr++; // Past the comma + + if (*ptr && *ptr == '"') + ptr++; // Starting quote of b. + codes_ptr = ptr; // Save this for later. + while (*ptr && *ptr != ',') + ptr++; + // If there was no comma, declare a bad file. + if (*ptr == '\0') { + fclose(fp); + return -2; + } + *ptr++; // Past the comma + *(ptr - 1) = '\0'; // End the codes there + + uint32 i = 0; + description = ptr; // Skip starting " in description + while (*description && *description == '"') + description++; + ptr = description; + while (*ptr && !(*ptr == '\r' || *ptr == '\n' || *ptr == '"') && i < MAX_SFCCHEAT_NAME - 1) { + ptr++; // Remove trailing newline/quote in description + i++; // Clip the cheat name to MAX_SFCCHEAT_NAME chars + } + *ptr = '\0'; - if(type == 0) //UTF8 - { - while(*src) - { - ch = *src++; - *dst++ = ch; + uint32 n = 0, c; + // n is the number of cheat codes. Beware of MAX_CHEATS_T. - if(ch < 0x80) { - if(length > 1) length -= 1; - else break; - } else if (ch < 0xe0) { /* U-00000080 - U-000007FF, 2 bytes */ - if(length > 2) length -= 2; - else break; - *dst++ = *src++; - } else if (ch < 0xf0) { /* U-00000800 - U-0000FFFF, 3 bytes */ - if(length > 3) length -= 3; - else break; - *dst++ = *src++; - *dst++ = *src++; - } else if (ch < 0xf5) { /* U-00010000 - U-001FFFFF, 4 bytes */ - if(length > 4) length -= 4; - else break; - *dst++ = *src++; - *dst++ = *src++; - *dst++ = *src++; - } else { - break; + // List of cheat codes having the same description. + ptr = codes_ptr; + while (*ptr && !(*ptr == ',' || *ptr == '"')) { + if (n >= MAX_CHEATS_T) { + fclose(fp); + return 0; } - } - *dst = '\0'; - } - else //assume it is GBK code - { - //GBK to UTF8 - while(*src) - { - ch = *src; - if(ch < 0x80) - { - if(length > 1) length -= 1; - else break; - - *dst++= ch; - src ++; + i = 0; + while (*ptr && *ptr != '+' && i < sizeof(code) - 1) + code[i++] = *ptr++; + code[i] = '\0'; + if (!S9xGameGenieToRaw (code, &address, &byte)) { + S9xAddCheat (FALSE, TRUE, address, byte); + strncpy (Cheat.c[Cheat.num_cheats - 1].name, description, MAX_SFCCHEAT_NAME); + } + else if (!S9xProActionReplayToRaw (code, &address, &byte)) { + S9xAddCheat (FALSE, TRUE, address, byte); + strncpy (Cheat.c[Cheat.num_cheats - 1].name, description, MAX_SFCCHEAT_NAME); } - else + else if (!S9xGoldFingerToRaw (code, &address, &sram, &num_bytes, bytes)) { - ucode = charsets_gbk_to_ucs(src); - - if (ucode < 0x800) //2 bytes - { - if(length > 2) length -= 2; - else break; - - *dst++ = 0xC0 | ((ucode >> 6) & 0x1F); - *dst++ = 0x80 | (ucode & 0x3F); - } - else //3 bytes - { - if(length > 3) length -= 3; - else break; - - *dst++ = 0xE0 | (ucode >> 12); - *dst++ = 0x80 | ((ucode >>6) & 0x3F); - *dst++ = 0x80 | (ucode & 0x3F); + for (c = 0; c < num_bytes; c++) { + S9xAddCheat (FALSE, TRUE, address + c, bytes[c]); + strncpy (Cheat.c[Cheat.num_cheats - 1].name, description, 22); } - - src += 2; } - } - *dst = '\0'; - } - - return 0; -} - -int load_cheatname(const char* filename, unsigned int string_num, unsigned int string_len, MSG_TABLE* mssg_table) -{ - FILE *fp; - unsigned char current_line[256]; - unsigned char current_line_tmp[256]; - int len, m; - unsigned char** indexp; - unsigned char* msg; - unsigned char* pt; - - mssg_table->msg_index = (unsigned char**)malloc(string_num*4); - if(NULL == mssg_table->msg_index) - return -1; - - string_len = string_len + string_len/2; - mssg_table->msg_pool = (unsigned char*)malloc((string_len+31)&(~31)); - if(NULL == mssg_table->msg_pool) { - free((void*)mssg_table->msg_index); - return -1; - } - - fp = fopen(filename, "r"); - if(fp == NULL) { - free((void*)mssg_table->msg_index); - free((void*)mssg_table->msg_pool); - return -1; - } - - len = 0; - m= 0; - indexp = mssg_table->msg_index; - msg = mssg_table->msg_pool; - while(fgets(current_line, 256, fp)) - { - unsigned int str_len; - - if((pt = check_is_cht(current_line)) != NULL) - { - if(!strcasecmp(pt, "gameinfo")) - continue; - - string2utf8(pt, current_line_tmp, 255); - - str_len = strlen(current_line_tmp); - strncpy(msg+len, current_line_tmp, str_len); - - indexp[m++] = msg+len; - len += str_len; - msg[len] = '\0'; - len += 1; - - if(len >= string_len) break; - if(m >= string_num) break; - - while(fgets(current_line, 256, fp)) - { - str_len = strlen(current_line); - if(str_len < 4) break; - - if((pt = strchr(current_line, '=')) == NULL) //valid cheat item - break; - - *pt = '\0'; - pt = current_line; - - string2utf8(pt, current_line_tmp, 255); - - str_len = strlen(current_line_tmp); - strncpy(msg+len, current_line_tmp, str_len); - - indexp[m++] = msg+len; - len += str_len; - msg[len] = '\0'; - len += 1; - - if(len >= string_len) break; - if(m >= string_num) break; + else { + fclose(fp); + return -3; // Bad cheat format } - - if(len >= string_len) break; - if(m >= string_num) break; - } - } - - mssg_table -> msg_num = m; - fclose(fp); - -#if 0 -cprintf("string_len %d; len %d\n", string_len, len); -for(m= 0; m msg_num; m++) -{ -cprintf("msg%d:%s\n", m, indexp[m]); -} -#endif - - return 0; -} - -#define MAX_CHEAT_DATE_LEN (MAX_SFCCHEAT_NAME/2) //other part hold the saved data - -/* -* Load cheat file -*/ -int load_cheatfile(const char* filename, unsigned int *string_num, unsigned int *string_len, - GCHEAT_STRUCT *gcheat) -{ - FILE *cheats_file; - unsigned char current_line[256]; - unsigned char current_line_tmp[256]; - unsigned int current_line_len; - unsigned char *pt; - int gcheat_num; - - unsigned int str_num; - unsigned int str_len; - unsigned int cheat_cell_num; - int flag; - - cheats_file = fopen(filename, "r"); - if(NULL == cheats_file) - return -1; - g_cheat_cell_num = 0; - g_cheat_num = 0; - cheat_cell_num = 0; - gcheat_num = 0; - str_num = 0; - str_len = 0; - flag = 0; - - while(fgets(current_line, 256, cheats_file)) - { - if((pt = check_is_cht(current_line)) == NULL) //Check valid cht cheat - continue; - - if(!strcasecmp(pt, "gameinfo")) //maybe file end - continue; - - gcheat[gcheat_num].name_id = str_num; - gcheat[gcheat_num].item_id = cheat_cell_num; - gcheat[gcheat_num].item_num = 0; - - string2utf8(pt, current_line_tmp, CHEAT_NAME_LENGTH); - strcpy(gcheat[gcheat_num].name_shot, current_line_tmp); //store a cut name shot - //Initialize other parameter of gcheat - gcheat[gcheat_num].active = 0; - gcheat[gcheat_num].sub_active = 0; - - current_line_len = strlen(pt); - str_len += current_line_len +1; - str_num++; - - //Cheat items - while(fgets(current_line, 256, cheats_file) != NULL) - { - if(strlen(current_line) < 4) - break; - - if((pt = strchr(current_line, '=')) == NULL) //No valid content - break; - - //one sub item each pass - unsigned int first_part; //first part of a cheat item - unsigned int first_part_id; - unsigned int sub_part_id; - unsigned int hex_len; - - unsigned int cheat_addr; - unsigned char cheat_dat[MAX_CHEAT_DATE_LEN]; - unsigned int cheat_dat_len; - unsigned int str_num_saved; - - str_num_saved = str_num; - str_len += pt - current_line +1; - str_num++; - - first_part = 1; - first_part_id = cheat_cell_num; - sub_part_id = 0; - - //skip name part - pt += 1; - current_line_len = strlen(pt); - - //data part - while(1) - { - //fill current_line buffer as full as possible - if(current_line_len < (MAX_CHEAT_DATE_LEN*3+8)) - { //the data length can fill a cheat cell - if(NULL == strchr(pt, 0x0A)) { //this line not end - memmove(current_line, pt, current_line_len+1); - fgets(current_line+current_line_len, 256-current_line_len, cheats_file); - pt = current_line; - current_line_len = strlen(pt); - } - } -#if 0 -cprintf("------\n"); -cprintf("new %d:[%s]\n", current_line_len, pt); -dump_mem(pt, strlen(pt)); -cprintf("\n------\n"); -#endif - //get address - if(first_part) - { - hex_len = sscanf_hex_value(pt, &cheat_addr); - if(0 == hex_len) { - goto load_cheatfile_error; - } - - pt += hex_len; - current_line_len -= hex_len +1; - // strict to follow the formate - if(',' != *pt++ || '\0' == *pt || 0x0D == *pt || 0x0A == *pt) { - goto load_cheatfile_error; - } - - if(cheat_addr < 0x10000) - cheat_addr |= 0x7e0000; - else { - cheat_addr &= 0xffff; - cheat_addr |= 0x7f0000; - } - } - - //get data - unsigned int tmp, m; - - m = 0; - cheat_dat_len = 0; - while(m++ < MAX_CHEAT_DATE_LEN) - { - hex_len = sscanf_hex_value(pt, &tmp); - if(0 == hex_len) break; - - cheat_dat[cheat_dat_len++] = (unsigned char)tmp; - - pt += hex_len; - current_line_len -= hex_len +1; - if(',' == *pt) pt++; - } - - //In first part, get data error - if(0 == cheat_dat_len) { - if(0 == sub_part_id) - goto load_cheatfile_error; - } - else { - //record data - flag = S9xAddCheat_ex(cheat_addr, cheat_dat, cheat_dat_len, cheat_cell_num++, sub_part_id++, str_num_saved); - if(0 != flag) { - cheat_cell_num -= sub_part_id; - break; - } - } - - if(0 == *pt || 0x0D == *pt || 0x0A == *pt) break; //a line over - - first_part = 0; - if(';' == *pt) first_part = 1, pt += 1; //other address of the cheat cell - else cheat_addr += cheat_dat_len; //more data - } //data part - - //have no enough cheat_cell struct to store cheat - if(0 != flag) break; - - S9xAddCheat_ov(first_part_id, sub_part_id); - gcheat[gcheat_num].item_num += 1; - } //Cheat items - - if(0 != flag) break; - - gcheat_num += 1; - if(gcheat_num >= MAX_CHEATS) - break; - } - - g_cheat_cell_num = cheat_cell_num; - g_cheat_num = gcheat_num; - *string_num = str_num; - *string_len = str_len; - fclose(cheats_file); - -#if 0 -cprintf("g_cheat_num %d; g_cheat_cell_num %d\n", g_cheat_num, g_cheat_cell_num); - -int i; -for(i= 0; i < g_cheat_cell_num; i++) -S9x_dumpcheat(i); - -for(i= 0; i < g_cheat_num; i++) -{ - cprintf("cheat %d\n", i); - cprintf("item num %d; item id %d\n", gcheat[i].item_num, gcheat[i].item_id); -} -#endif - - return 0; - -load_cheatfile_error: - fclose(cheats_file); - return -1; -} - -void gcheat_Managment(GCHEAT_STRUCT *gcheat) -{ - unsigned int i, enable, m, en_flag; - unsigned int active, item_id, sub_active, item_num; - - //no cheat - if(0 == g_cheat_num || 0 == g_cheat_cell_num) { - S9xCheat_Disable(); - return; - } - - enable = 0; - for(i = 0; i < g_cheat_num; i++) - { - active = gcheat[i].active & 0x1; - item_id = gcheat[i].item_id; - item_num = gcheat[i].item_num; - sub_active = gcheat[i].sub_active; - - for(m = 0; m < item_num; m++) - { - en_flag = sub_active == m ? active : 0; - S9xCheat_switch(item_id, m, en_flag); } - - if(active) enable = 1; } - if(enable) - S9xCheat_Enable(); + fclose(fp); + return 0; } - diff --git a/source/nds/gcheat.h b/source/nds/gcheat.h index e5131f6..3c9e440 100644 --- a/source/nds/gcheat.h +++ b/source/nds/gcheat.h @@ -15,51 +15,24 @@ * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - */ - -#ifndef __GCHEAT_H__ -#define __GCHEAT_H__ + */ + +#ifndef __GCHEAT_H__ +#define __GCHEAT_H__ #ifdef __cplusplus extern "C" { #endif - -#define CHEAT_NAME_LENGTH (32) -#define MAX_CHEATS_PAGE 10 -#define CHEATS_PER_PAGE 4 -#define MAX_CHEATS (MAX_CHEATS_PAGE * CHEATS_PER_PAGE) -//Support EMU Cheat(emulator cheat) code -typedef struct -{ - u32 name_id; //name ID in another table - u32 active; //status - u16 item_num; //sub-item number - u16 sub_active; - u32 item_id; //There is another struct array to store the cheat data - char name_shot[CHEAT_NAME_LENGTH]; - u32 reserved; -} GCHEAT_STRUCT; +#include "cheats.h" -typedef struct -{ - unsigned char** msg_index; - unsigned char* msg_pool; - unsigned int msg_num; -} MSG_TABLE; - -extern GCHEAT_STRUCT gcheat[MAX_CHEATS]; -extern unsigned int g_cheat_cell_num; -extern unsigned int g_cheat_num; +#define CHEATS_PER_PAGE 4 +#define MAX_CHEATS_PAGE (MAX_CHEATS_T / CHEATS_PER_PAGE) -extern int load_cheatfile(const char* filename, unsigned int *string_num, - unsigned int *string_len, GCHEAT_STRUCT *gcheat); -extern int load_cheatname(const char* filename, unsigned int string_num, - unsigned int string_len, MSG_TABLE* mssg_table); -extern void gcheat_Managment(GCHEAT_STRUCT *gcheat); +extern int NDSSFCLoadCheatFile(const char* filename); #ifdef __cplusplus } #endif - -#endif //__GCHEAT_H__ + +#endif //__GCHEAT_H__ diff --git a/source/nds/gui.c b/source/nds/gui.c index 4a04efc..84f522f 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -23,6 +23,7 @@ #include #include +#include "port.h" #include "ds2_types.h" #include "ds2io.h" #include "ds2_malloc.h" @@ -35,6 +36,8 @@ #include "bitmap.h" #include "gcheat.h" +extern struct SCheatData Cheat; + char main_path[MAX_PATH]; char rom_path[MAX_PATH]; char gamepak_name[MAX_PATH]; @@ -69,7 +72,7 @@ char *language_options[] = { (char *) &lang[0], (char *) &lang[1], (char *) &lan EMU_CONFIG emu_config; //game configure file's header -#define GAME_CONFIG_HEADER "GSFC1.0" +#define GAME_CONFIG_HEADER "GSFC1.1" // 1.1 removed cheat names #define GAME_CONFIG_HEADER_SIZE 7 GAME_CONFIG game_config; @@ -110,7 +113,7 @@ static unsigned int savestate_index; NULL, \ &cheat_format_ptr[number], \ enable_disable_options, \ - &(game_config.cheats_flag[number].active), \ + &(Cheat.c[number].enabled), \ 2, \ NULL, \ line_number, \ @@ -1656,8 +1659,8 @@ u32 menu(u16 *screen) u32 first_load = 0; char tmp_filename[MAX_FILE]; char line_buffer[512]; - char cheat_format_str[MAX_CHEATS][41*4]; - char *cheat_format_ptr[MAX_CHEATS]; + char cheat_format_str[MAX_CHEATS_T][41*4]; + char *cheat_format_ptr[MAX_CHEATS_T]; MENU_TYPE *current_menu; MENU_OPTION_TYPE *current_option; @@ -2214,19 +2217,18 @@ u32 menu(u16 *screen) unsigned char **dynamic_cheat_pt = NULL; unsigned int dynamic_cheat_active; int dynamic_cheat_scroll_value= 0; - MSG_TABLE cheat_msg= {NULL, NULL}; void cheat_menu_init() { - for(i = 0; i < MAX_CHEATS; i++) + for(i = 0; i < MAX_CHEATS_T; i++) { - if(i >= g_cheat_num) + if(i >= Cheat.num_cheats) { sprintf(cheat_format_str[i], msg[MSG_CHEAT_MENU_NON_LOAD], i); } else { - sprintf(cheat_format_str[i], msg[MSG_CHEAT_MENU_LOADED], i, game_config.cheats_flag[i].name_shot); + sprintf(cheat_format_str[i], msg[MSG_CHEAT_MENU_LOADED], i, Cheat.c[i].name); } cheat_format_ptr[i]= cheat_format_str[i]; @@ -2237,13 +2239,11 @@ u32 menu(u16 *screen) void cheat_menu_end() { - if(!first_load) - gcheat_Managment(game_config.cheats_flag); } void dynamic_cheat_key() { - unsigned int m, n; + unsigned int m, n; switch(gui_action) { @@ -2455,11 +2455,12 @@ u32 menu(u16 *screen) unsigned int nums; nums = (CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1; - if(gui_action == CURSOR_SELECT && nums < g_cheat_num) + if(gui_action == CURSOR_SELECT && nums < Cheat.num_cheats) { unsigned int m; - nums = game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1].item_num; + // nums = game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1].item_num; + // REVISIT [Neb] if(dynamic_cheat_options) { @@ -2497,7 +2498,8 @@ u32 menu(u16 *screen) dynamic_cheat_options[0].action_function = NULL; dynamic_cheat_options[0].passive_function = NULL; dynamic_cheat_options[0].sub_menu = &cheats_menu; - dynamic_cheat_options[0].display_string = (char**)(dynamic_cheat_pt + game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1].name_id); + // dynamic_cheat_options[0].display_string = (char**)(dynamic_cheat_pt + game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1].name_id); + // REVISIT [Neb] dynamic_cheat_options[0].options = NULL; dynamic_cheat_options[0].current_option = NULL; dynamic_cheat_options[0].num_options = 0; @@ -2505,13 +2507,15 @@ u32 menu(u16 *screen) dynamic_cheat_options[0].line_number = 0; dynamic_cheat_options[0].option_type = SUBMENU_TYPE; - m = game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1].item_id; + // m = game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1].item_id; + // REVISIT [Neb] for(i= 0; i < nums; i++) { dynamic_cheat_options[i+1].action_function = dynamic_cheat_action; dynamic_cheat_options[i+1].passive_function = NULL; dynamic_cheat_options[i+1].sub_menu = NULL; - dynamic_cheat_options[i+1].display_string = (char**)(dynamic_cheat_pt + S9xGetCheat_nameid(m, i, g_cheat_cell_num)); + // dynamic_cheat_options[i+1].display_string = (char**)(dynamic_cheat_pt + S9xGetCheat_nameid(m, i, g_cheat_cell_num)); + // REVISIT [Neb] dynamic_cheat_options[i+1].options = NULL; dynamic_cheat_options[i+1].current_option = NULL; dynamic_cheat_options[i+1].num_options = 2; @@ -2520,10 +2524,11 @@ u32 menu(u16 *screen) dynamic_cheat_options[i+1].option_type = ACTION_TYPE; } - dynamic_cheat_active = game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + - current_option_num -1].active & 0x1; - dynamic_cheat_active |= game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + - current_option_num -1].sub_active << 16; + // dynamic_cheat_active = game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + + // current_option_num -1].active & 0x1; + // dynamic_cheat_active |= game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + + // current_option_num -1].sub_active << 16; + // REVISIT [Neb] //Initial srollable options int k; @@ -2585,7 +2590,8 @@ u32 menu(u16 *screen) unsigned int m, k; m = cheats_menu.focus_option-1; - game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + m].sub_active = dynamic_cheat_active >> 16; + // game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + m].sub_active = dynamic_cheat_active >> 16; + // REVISIT [Neb] k = SUBMENU_ROW_NUM +1; for(m= 0; m= MAX_CHEATS_T) { + if (Cheat.num_cheats >= MAX_CHEATS_T) { fclose(fp); return 0; } i = 0; - while (*ptr && *ptr != '+' && i < sizeof(code) - 1) + while (*ptr && !(*ptr == '+' || *ptr == ',' || *ptr == '"') && i < sizeof(code) - 1) code[i++] = *ptr++; + if (*ptr) + ptr++; // Go past the + , or " code[i] = '\0'; if (!S9xGameGenieToRaw (code, &address, &byte)) { S9xAddCheat (FALSE, TRUE, address, byte); @@ -112,7 +114,7 @@ int NDSSFCLoadCheatFile(const char* filename) { for (c = 0; c < num_bytes; c++) { S9xAddCheat (FALSE, TRUE, address + c, bytes[c]); - strncpy (Cheat.c[Cheat.num_cheats - 1].name, description, 22); + strncpy (Cheat.c[Cheat.num_cheats - 1].name, description, MAX_SFCCHEAT_NAME); } } else { diff --git a/source/nds/gui.c b/source/nds/gui.c index 84f522f..1b265b6 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -2618,10 +2618,12 @@ u32 menu(u16 *screen) if(load_file(file_ext, tmp_filename, DEFAULT_CHEAT_DIR) != -1) { - strcpy(line_buffer, DEFAULT_CHEAT_DIR); - strcat(line_buffer, "/"); - strcat(line_buffer, tmp_filename); + sprintf(line_buffer, "%s/%s", DEFAULT_CHEAT_DIR, tmp_filename); flag = NDSSFCLoadCheatFile(line_buffer); + + strcpy(line_buffer, (char *) S9xGetFilename (".chb")); + S9xSaveCheatFile (line_buffer); // cheat binary + if(0 != flag) { //load cheat file failure S9xDeleteCheats(); @@ -2630,12 +2632,9 @@ u32 menu(u16 *screen) return; } - strcpy(line_buffer, (char *) S9xGetFilename (".chb")); - - S9xSaveCheatFile (line_buffer); // cheat binary - menu_cheat_page = 0; cheat_menu_init(); + } } -- cgit v1.2.3 From f843d68bb65f8a532b365efc5cbdf5be65c5f517 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Mon, 24 Dec 2012 01:15:41 -0500 Subject: Make the GUI accept and save Snes9x's cheat file format. Improve support for saving the values present in ROM/RAM before a cheat is applied. Beautify the cheat selection menu, making it more tabular. --- source/nds/gcheat.c | 6 +- source/nds/gui.c | 171 ++++++++++++++-------------------------------------- 2 files changed, 49 insertions(+), 128 deletions(-) (limited to 'source/nds') diff --git a/source/nds/gcheat.c b/source/nds/gcheat.c index e3d0e8d..d0ada43 100644 --- a/source/nds/gcheat.c +++ b/source/nds/gcheat.c @@ -103,17 +103,17 @@ int NDSSFCLoadCheatFile(const char* filename) ptr++; // Go past the + , or " code[i] = '\0'; if (!S9xGameGenieToRaw (code, &address, &byte)) { - S9xAddCheat (FALSE, TRUE, address, byte); + S9xAddCheat (FALSE, FALSE, address, byte); strncpy (Cheat.c[Cheat.num_cheats - 1].name, description, MAX_SFCCHEAT_NAME); } else if (!S9xProActionReplayToRaw (code, &address, &byte)) { - S9xAddCheat (FALSE, TRUE, address, byte); + S9xAddCheat (FALSE, FALSE, address, byte); strncpy (Cheat.c[Cheat.num_cheats - 1].name, description, MAX_SFCCHEAT_NAME); } else if (!S9xGoldFingerToRaw (code, &address, &sram, &num_bytes, bytes)) { for (c = 0; c < num_bytes; c++) { - S9xAddCheat (FALSE, TRUE, address + c, bytes[c]); + S9xAddCheat (FALSE, FALSE, address + c, bytes[c]); strncpy (Cheat.c[Cheat.num_cheats - 1].name, description, MAX_SFCCHEAT_NAME); } } diff --git a/source/nds/gui.c b/source/nds/gui.c index 1b265b6..a8152c4 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -111,7 +111,7 @@ static unsigned int savestate_index; action_function, \ passive_function, \ NULL, \ - &cheat_format_ptr[number], \ + &cheat_data_ptr[number], \ enable_disable_options, \ &(Cheat.c[number].enabled), \ 2, \ @@ -1659,8 +1659,9 @@ u32 menu(u16 *screen) u32 first_load = 0; char tmp_filename[MAX_FILE]; char line_buffer[512]; - char cheat_format_str[MAX_CHEATS_T][41*4]; - char *cheat_format_ptr[MAX_CHEATS_T]; + char cheat_data_str[MAX_CHEATS_T][5]; + // ^ Holds the index inside Cheat, as a number in an ASCIIZ string + char* cheat_data_ptr[MAX_CHEATS_T]; MENU_TYPE *current_menu; MENU_OPTION_TYPE *current_option; @@ -2222,16 +2223,8 @@ u32 menu(u16 *screen) { for(i = 0; i < MAX_CHEATS_T; i++) { - if(i >= Cheat.num_cheats) - { - sprintf(cheat_format_str[i], msg[MSG_CHEAT_MENU_NON_LOAD], i); - } - else - { - sprintf(cheat_format_str[i], msg[MSG_CHEAT_MENU_LOADED], i, Cheat.c[i].name); - } - - cheat_format_ptr[i]= cheat_format_str[i]; + sprintf(cheat_data_str[i], "%d", i); + cheat_data_ptr[i] = &cheat_data_str[i][0]; } reload_cheats_page(); @@ -2239,6 +2232,17 @@ u32 menu(u16 *screen) void cheat_menu_end() { + // Honour current cheat selections. + uint32 i; + for (i = 0; i < Cheat.num_cheats; i++) { + if (Cheat.c[i].enabled) + S9xApplyCheat(i); + else + S9xRemoveCheat(i); + } + // Save current cheat selections to the cheat binary file. + strcpy(line_buffer, (char *) S9xGetFilename (".chb")); + S9xSaveCheatFile (line_buffer); // cheat binary } void dynamic_cheat_key() @@ -2452,102 +2456,13 @@ u32 menu(u16 *screen) void cheat_option_action() { - unsigned int nums; - - nums = (CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1; - if(gui_action == CURSOR_SELECT && nums < Cheat.num_cheats) - { - unsigned int m; - - // nums = game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1].item_num; - // REVISIT [Neb] - - if(dynamic_cheat_options) - { - free((void*)dynamic_cheat_options); - dynamic_cheat_options = NULL; - } - - if(dynamic_cheat_menu) - { - free((void*)dynamic_cheat_menu); - dynamic_cheat_menu = NULL; - } - - dynamic_cheat_options = (MENU_OPTION_TYPE*)malloc(sizeof(MENU_OPTION_TYPE)*(nums+1)); - if(dynamic_cheat_options == NULL) return; - - dynamic_cheat_menu = (MENU_TYPE*)malloc(sizeof(MENU_TYPE)); - if(dynamic_cheat_menu == NULL) - { - free((void*)dynamic_cheat_options); - dynamic_cheat_options = NULL; - return; - } - - //menu - dynamic_cheat_menu->init_function = NULL; - dynamic_cheat_menu->passive_function = dynamic_cheat_menu_passive; - dynamic_cheat_menu->key_function = dynamic_cheat_key; - dynamic_cheat_menu->end_function = dynamic_cheat_menu_end; - dynamic_cheat_menu->options = dynamic_cheat_options; - dynamic_cheat_menu->num_options = nums+1; - dynamic_cheat_menu->focus_option = 0; - dynamic_cheat_menu->screen_focus = 0; - //back option - dynamic_cheat_options[0].action_function = NULL; - dynamic_cheat_options[0].passive_function = NULL; - dynamic_cheat_options[0].sub_menu = &cheats_menu; - // dynamic_cheat_options[0].display_string = (char**)(dynamic_cheat_pt + game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1].name_id); - // REVISIT [Neb] - dynamic_cheat_options[0].options = NULL; - dynamic_cheat_options[0].current_option = NULL; - dynamic_cheat_options[0].num_options = 0; - dynamic_cheat_options[0].help_string = NULL; - dynamic_cheat_options[0].line_number = 0; - dynamic_cheat_options[0].option_type = SUBMENU_TYPE; - - // m = game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + current_option_num -1].item_id; - // REVISIT [Neb] - for(i= 0; i < nums; i++) - { - dynamic_cheat_options[i+1].action_function = dynamic_cheat_action; - dynamic_cheat_options[i+1].passive_function = NULL; - dynamic_cheat_options[i+1].sub_menu = NULL; - // dynamic_cheat_options[i+1].display_string = (char**)(dynamic_cheat_pt + S9xGetCheat_nameid(m, i, g_cheat_cell_num)); - // REVISIT [Neb] - dynamic_cheat_options[i+1].options = NULL; - dynamic_cheat_options[i+1].current_option = NULL; - dynamic_cheat_options[i+1].num_options = 2; - dynamic_cheat_options[i+1].help_string = NULL; - dynamic_cheat_options[i+1].line_number = i+1; - dynamic_cheat_options[i+1].option_type = ACTION_TYPE; - } - - // dynamic_cheat_active = game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + - // current_option_num -1].active & 0x1; - // dynamic_cheat_active |= game_config.cheats_flag[(CHEATS_PER_PAGE * menu_cheat_page) + - // current_option_num -1].sub_active << 16; - // REVISIT [Neb] - - //Initial srollable options - int k; - - draw_hscroll_init(down_screen_addr, 50, 9, 180, COLOR_TRANS, - COLOR_ACTIVE_ITEM, *dynamic_cheat_options[0].display_string); - - if(nums>5) nums = SUBMENU_ROW_NUM; - for(k= 0; k < nums; k++) - { - draw_hscroll_init(down_screen_addr, 23, 40 + k*27, 200, - COLOR_TRANS, COLOR_INACTIVE_ITEM, *dynamic_cheat_options[k+1].display_string); - } - dynamic_cheat_scroll_value= 0; - - choose_menu(dynamic_cheat_menu); - } } +#define CHEAT_NUMBER_X 26 +#define CHEAT_DESC_X 52 +#define CHEAT_DESC_SX 163 +#define CHEAT_ACTIVE_X 225 + void cheat_option_passive() { unsigned short color; @@ -2562,27 +2477,33 @@ u32 menu(u16 *screen) //sprintf("%A") will have problem ? strcpy(tmp_buf, *(display_option->display_string)); - pt = strrchr(tmp_buf, ':'); - if(pt != NULL) - sprintf(pt+1, "%s", *((u32*)(((u32 *)display_option->options)[*(display_option->current_option)]))); + // This is the number of the cheat to display - strcpy(line_buffer, tmp_buf); - pt = strrchr(line_buffer, ')'); - *pt = '\0'; - pt = strchr(line_buffer, '('); + int i = atoi(tmp_buf); - len = BDF_cut_string(pt+1, 0, 2); - if(len > 90) - { - len = BDF_cut_string(pt+1, 90, 1); - *(pt+1+len) = '\0'; - strcat(line_buffer, "..."); - } + sprintf(line_buffer, "%d.", i + 1); + PRINT_STRING_BG(down_screen_addr, line_buffer, color, COLOR_TRANS, CHEAT_NUMBER_X, 40 + display_option-> line_number*27); - pt = strrchr(tmp_buf, ')'); - strcat(line_buffer, pt); + if (i >= Cheat.num_cheats) { + PRINT_STRING_BG(down_screen_addr, msg[MSG_CHEAT_MENU_NON_LOAD], color, COLOR_TRANS, CHEAT_DESC_X, 40 + display_option-> line_number*27); + } + else { + strcpy(line_buffer, Cheat.c[i].name); + len = BDF_cut_string(line_buffer, 0, 2); + if(len > CHEAT_DESC_SX) + { + len = BDF_cut_string(line_buffer, CHEAT_DESC_SX, 1); + line_buffer[len] = '\0'; + strcat(line_buffer, "..."); + } + PRINT_STRING_BG(down_screen_addr, line_buffer, color, COLOR_TRANS, CHEAT_DESC_X, 40 + display_option-> line_number*27); - PRINT_STRING_BG(down_screen_addr, line_buffer, color, COLOR_TRANS, 26, 40 + display_option-> line_number*27); + if (Cheat.c[i].enabled) + strcpy(line_buffer, "+"); + else + strcpy(line_buffer, "-"); + PRINT_STRING_BG(down_screen_addr, line_buffer, color, COLOR_TRANS, CHEAT_ACTIVE_X, 40 + display_option-> line_number*27); + } } void dynamic_cheat_menu_end() @@ -3578,7 +3499,7 @@ u32 menu(u16 *screen) { for(i = 0; i < CHEATS_PER_PAGE; i++) { - cheats_options[i+1].display_string = &cheat_format_ptr[(CHEATS_PER_PAGE * menu_cheat_page) + i]; + cheats_options[i+1].display_string = &cheat_data_ptr[(CHEATS_PER_PAGE * menu_cheat_page) + i]; cheats_options[i+1].current_option = &(Cheat.c[(CHEATS_PER_PAGE * menu_cheat_page) + i].enabled); } } -- cgit v1.2.3 From e7ce8dd66c19de431fb347a0f3cd0ea867a802ce Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Mon, 24 Dec 2012 02:15:42 -0500 Subject: Bump to v. 1.09. Update the readme for cheats. Update the github link in source.txt. --- source/nds/gui.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index 979d99c..772775b 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -59,7 +59,7 @@ char *language_options[] = { (char *) &lang[0], (char *) &lang[1], (char *) &lan ******************************************************************************/ #define SUBMENU_ROW_NUM 6 -#define NDSSFC_VERSION "1.08" +#define NDSSFC_VERSION "1.09" #define SAVE_STATE_SLOT_NUM 10 -- cgit v1.2.3 From 1fd0171c5fd17cd48f6ef4104600c6f05b4e3004 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Mon, 24 Dec 2012 04:01:50 -0500 Subject: Bump version number to 1.10 for the APU half-carry bug and optimisations. --- source/nds/gui.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index 772775b..91e1aa3 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -59,7 +59,7 @@ char *language_options[] = { (char *) &lang[0], (char *) &lang[1], (char *) &lan ******************************************************************************/ #define SUBMENU_ROW_NUM 6 -#define NDSSFC_VERSION "1.09" +#define NDSSFC_VERSION "1.10" #define SAVE_STATE_SLOT_NUM 10 -- cgit v1.2.3 From 7f0e1fee814df6c44ced04246f511b0f91787673 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Tue, 25 Dec 2012 03:18:36 -0500 Subject: Wait for keys to be released after the yes/no dialog for deleting saved states, instead of delaying. --- source/nds/gui.c | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) (limited to 'source/nds') diff --git a/source/nds/gui.c b/source/nds/gui.c index 91e1aa3..964944b 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -2170,6 +2170,7 @@ u32 menu(u16 *screen) { if(draw_yesno_dialog(DOWN_SCREEN, 115, "Yes(A)", "No(B)")) { + wait_Allkey_release(0); for(i= 0; i < SAVE_STATE_SLOT_NUM; i++) { get_savestate_filename(i, tmp_filename); @@ -2198,8 +2199,10 @@ u32 menu(u16 *screen) sprintf(line_buffer, msg[MSG_DELETTE_SINGLE_SAVESTATE_WARING], delette_savestate_num); draw_string_vcenter(down_screen_addr, 36, 75, 190, COLOR_MSSG, line_buffer); - if(draw_yesno_dialog(DOWN_SCREEN, 115, "Yes(A)", "No(B)")) + if(draw_yesno_dialog(DOWN_SCREEN, 115, "Yes(A)", "No(B)")) { + wait_Allkey_release(0); clear_savestate_slot(delette_savestate_num); +} } else { @@ -2740,6 +2743,7 @@ u32 menu(u16 *screen) if(draw_yesno_dialog(DOWN_SCREEN, 115, "Yes", "No")) { + wait_Allkey_release(0); draw_message(down_screen_addr, bg_screenp, 28, 31, 227, 165, bg_screenp_color); draw_string_vcenter(down_screen_addr, 36, 80, 190, COLOR_MSSG, msg[MSG_DEFAULT_LOADING]); ds2_flipScreen(DOWN_SCREEN, 2); @@ -2803,11 +2807,10 @@ u32 menu(u16 *screen) ds2_clearScreen(UP_SCREEN, 0); draw_string_vcenter(up_screen_addr, 0, 80, 256, COLOR_WHITE, msg[MSG_NON_LOAD_GAME]); ds2_flipScreen(UP_SCREEN, 1); - mdelay(10); //FIXME: Stranger? } save_emu_config_file(); - // mdelay(500); // Delete this delay + wait_Allkey_release(0); } } @@ -3556,6 +3559,11 @@ u32 menu(u16 *screen) } else { + /* + * It's pretty complicated. These two flips are needed because, + * otherwise, the menu freezes if S9xAutoSaveSRAM was called after + * loading from a save state. + */ ds2_flipScreen(UP_SCREEN, 1); ds2_flipScreen(UP_SCREEN, 1); } @@ -3563,7 +3571,6 @@ u32 menu(u16 *screen) choose_menu(&main_menu); // Menu loop - // mdelay(50); // Delete this delay, shortened from 200 while(repeat) { -- cgit v1.2.3 From 9c1742f6cb2043d0ed6a61ab6de3bef0aad6dc56 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Tue, 25 Dec 2012 16:00:34 -0500 Subject: Universally use update method 2 for the lower screen and 0 for the upper screen. Method 1 causes problems after about 15 minutes; despite the double-buffering, screen updates start to tear in the middle consistently. --- source/nds/draw.c | 8 ++++---- source/nds/entry.cpp | 6 ++++-- source/nds/gui.c | 27 +++++++++------------------ 3 files changed, 17 insertions(+), 24 deletions(-) (limited to 'source/nds') diff --git a/source/nds/draw.c b/source/nds/draw.c index 9d1b8ec..2a9e440 100644 --- a/source/nds/draw.c +++ b/source/nds/draw.c @@ -811,7 +811,7 @@ u32 draw_yesno_dialog(enum SCREEN_ID screen, u32 sy, char *yes, char *no) // draw_string_vcenter(screen_address, i+1, sy+1, box_width, COLOR_WHITE, no); draw_string_vcenter((unsigned short*)screen_addr, 138, 130, 58, COLOR_WHITE, no); - ds2_flipScreen(screen, 1); + ds2_flipScreen(screen, 2); gui_action_type gui_action = CURSOR_NONE; while((gui_action != CURSOR_SELECT) && (gui_action != CURSOR_BACK)) @@ -860,7 +860,7 @@ void init_progress(enum SCREEN_ID screen, u32 total, char *text) drawboxfill((unsigned short*)screen_addr, progress_sx, progress_sy, progress_ex, progress_ey, COLOR16(15, 15, 15)); - ds2_flipScreen(_progress_screen_id, 1); + ds2_flipScreen(_progress_screen_id, 2); } // update progress bar @@ -883,7 +883,7 @@ void update_progress(void) drawboxfill(screen_addr, progress_sx, progress_sy, progress_sx+width, progress_ey, COLOR16(30, 19, 7)); - ds2_flipScreen(_progress_screen_id, 1); + ds2_flipScreen(_progress_screen_id, 2); } // display progress string @@ -908,7 +908,7 @@ void show_progress(char *text) // if (text[0] != '\0') // print_string_center(progress_sy - 21, COLOR_PROGRESS_TEXT, COLOR_DIALOG, text); - ds2_flipScreen(_progress_screen_id, 1); + ds2_flipScreen(_progress_screen_id, 2); // OSTimeDly(progress_wait); mdelay(500); diff --git a/source/nds/entry.cpp b/source/nds/entry.cpp index ea5f6ce..ce8d732 100644 --- a/source/nds/entry.cpp +++ b/source/nds/entry.cpp @@ -174,7 +174,10 @@ bool8 S9xDeinitUpdate (int Width, int Height, bool8 /*sixteen_bit*/) break; } - ds2_flipScreen(UP_SCREEN, 1); // synchronise to vblank to avoid tearing + ds2_flipScreen(UP_SCREEN, 0); + // A problem with update method 1 (wait, double buffer) means that, after + // about 15 minutes of play time, the screen starts to half-redraw every + // frame. With update method 0, this is mitigated. (Method 2 is too slow.) return (TRUE); } @@ -598,7 +601,6 @@ int sfc_main (int argc, char **argv) if (Settings.Paused) { S9xSetSoundMute (TRUE); - // mdelay(50); // Delete this delay unsigned short screen[256*192]; copy_screen((void*)screen, up_screen_addr, 0, 0, 256, 192); diff --git a/source/nds/gui.c b/source/nds/gui.c index 964944b..3438f62 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -1114,7 +1114,7 @@ s32 load_file(char **wildcards, char *result, char *default_dir_name) } redraw = 0; - ds2_flipScreen(DOWN_SCREEN, 2); //not switch down screen buffer + ds2_flipScreen(DOWN_SCREEN, 2); } //end if(0 != redraw) else if(0 != redraw) { unsigned int m, n; @@ -1142,7 +1142,7 @@ s32 load_file(char **wildcards, char *result, char *default_dir_name) } draw_hscroll(m+1, redraw); - ds2_flipScreen(DOWN_SCREEN, 2); //not switch down screen buffer + ds2_flipScreen(DOWN_SCREEN, 2); redraw = 0; } @@ -1162,7 +1162,7 @@ s32 load_file(char **wildcards, char *result, char *default_dir_name) { if(draw_hscroll(0, 1) <= 1) path_scroll = 0x8000; //scroll left } - ds2_flipScreen(DOWN_SCREEN, 2); //not switch down screen buffer + ds2_flipScreen(DOWN_SCREEN, 2); } mdelay(50); //about 50ms @@ -1176,7 +1176,7 @@ s32 load_file(char **wildcards, char *result, char *default_dir_name) manage_filelist_info(&filelist_info, -1); ds2_clearScreen(DOWN_SCREEN, COLOR_BLACK); - ds2_flipScreen(DOWN_SCREEN, 2); //not switch down screen buffer + ds2_flipScreen(DOWN_SCREEN, 2); return return_value; } @@ -3991,22 +3991,14 @@ u32 menu(u16 *screen) save_game_config_file(); } save_emu_config_file(); - // mdelay(100); // Delete this delay set_cpu_clock(clock_speed_number); - // mdelay(200); // Delete this delay - ds2_clearScreen(DUAL_SCREEN, 0); - ds2_flipScreen(DUAL_SCREEN, 1); + ds2_clearScreen(DOWN_SCREEN, 0); + ds2_flipScreen(DOWN_SCREEN, 1); copy_screen(up_screen_addr, (void*) screen, 0, 0, 256, 192); - ds2_flipScreen(UP_SCREEN, 1); // Flip again because otherwise it flickers + ds2_flipScreen(UP_SCREEN, 0); ds2_setBacklight(2); -//save game config -// save_game_config_file(); -// save_emu_config_file(); - - -// ds2_setCPUclocklevel(12); wait_Allkey_release(0); return return_value; @@ -4722,7 +4714,7 @@ void gui_init(u32 lang_id) } show_log(down_screen_addr); - ds2_flipScreen(DOWN_SCREEN, 1); + ds2_flipScreen(DOWN_SCREEN, 2); flag = icon_init(lang_id); if(0 != flag) @@ -4758,8 +4750,7 @@ void gui_init(u32 lang_id) return; gui_init_err: - ds2_flipScreen(DOWN_SCREEN, 1); + ds2_flipScreen(DOWN_SCREEN, 2); wait_Anykey_press(0); quit(); - while(1); } -- cgit v1.2.3 From 139c793b584a76acd42d72ec019d2cabab7d3ee7 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Tue, 25 Dec 2012 22:44:39 -0500 Subject: Smoother sound. Raise the sound sampling frequency to 48000 Hz. --- source/nds/ds2_main.c | 5 +++-- source/nds/ds2sound.h | 24 ++++++++++++++++++++++++ source/nds/entry.cpp | 24 ++++++------------------ 3 files changed, 33 insertions(+), 20 deletions(-) create mode 100644 source/nds/ds2sound.h (limited to 'source/nds') diff --git a/source/nds/ds2_main.c b/source/nds/ds2_main.c index 2d73313..7229727 100644 --- a/source/nds/ds2_main.c +++ b/source/nds/ds2_main.c @@ -23,6 +23,7 @@ #include "ds2io.h" #include "ds2_timer.h" #include "ds2_malloc.h" +#include "ds2sound.h" #define BLACK_COLOR RGB15(0, 0, 0) #define WHITE_COLOR RGB15(31, 31, 31) @@ -45,9 +46,9 @@ void ddump_mem(unsigned char* addr, unsigned int len) void ds2_main(void) { int err; -ds2_setCPUclocklevel(13); + ds2_setCPUclocklevel(13); //Initial video and audio and other input and output - err = ds2io_initb(512, 22050, 0, 0); + err = ds2io_initb(DS2_BUFFER_SIZE, SND_SAMPLE_RATE, 0, 0); if(err) goto _failure; //Initial file system diff --git a/source/nds/ds2sound.h b/source/nds/ds2sound.h new file mode 100644 index 0000000..cf37f6f --- /dev/null +++ b/source/nds/ds2sound.h @@ -0,0 +1,24 @@ +// The sound buffer sizes used on the DS2's side, for each value of +// Settings.SoundPlaybackRate. +#define DS2_BUFFER_SIZE_1 256 +#define DS2_BUFFER_SIZE_2 256 +#define DS2_BUFFER_SIZE_3 256 +#define DS2_BUFFER_SIZE_4 512 +#define DS2_BUFFER_SIZE_5 512 +#define DS2_BUFFER_SIZE_6 1024 +#define DS2_BUFFER_SIZE_7 1024 + +// The sampling rate for the sound, in Hz, for each value of +// Settings.SoundPlaybackRate. +#define SND_SAMPLE_RATE_1 8000 +#define SND_SAMPLE_RATE_2 11025 +#define SND_SAMPLE_RATE_3 16000 +#define SND_SAMPLE_RATE_4 22050 +#define SND_SAMPLE_RATE_5 32000 +#define SND_SAMPLE_RATE_6 44100 +#define SND_SAMPLE_RATE_7 48000 + +// Settings in use. The number should match in all three settings. +#define DS2_BUFFER_SIZE DS2_BUFFER_SIZE_7 +#define SND_SAMPLE_RATE SND_SAMPLE_RATE_7 +#define SNES9X_SRATE_ID 7 diff --git a/source/nds/entry.cpp b/source/nds/entry.cpp index ce8d732..a8e2217 100644 --- a/source/nds/entry.cpp +++ b/source/nds/entry.cpp @@ -20,6 +20,7 @@ #include "draw.h" #include "gui.h" +#include "ds2sound.h" void S9xProcessSound (unsigned int); @@ -359,9 +360,9 @@ void init_sfc_setting(void) Settings.JoystickEnabled = FALSE; #endif - Settings.SoundPlaybackRate = 4; //2 = 11025, 4 = 22050, 6 = 44100 + Settings.SoundPlaybackRate = SNES9X_SRATE_ID; // -> ds2sound.h for defs Settings.Stereo = TRUE; - Settings.SoundBufferSize = 0; + Settings.SoundBufferSize = DS2_BUFFER_SIZE; Settings.CyclesPercentage = 100; Settings.DisableSoundEcho = FALSE; //sound settings @@ -767,28 +768,15 @@ void S9xSyncSpeed () #endif } -/* -* Open sound device -*/ -static int Rates[8] = -{ - 0, 8000, 11025, 16000, 22050, 32000, 44100, 48000 -}; - -static int BufferSizes [8] = -{ - 0, 256, 256, 256, 512, 512, 1024, 1024 -}; - bool8 S9xOpenSoundDevice (int mode, bool8 stereo, int buffer_size) { so.sixteen_bit = TRUE; so.stereo = stereo; - so.playback_rate = Rates[mode & 0x07]; + so.playback_rate = SND_SAMPLE_RATE; S9xSetPlaybackRate (so.playback_rate); if (buffer_size == 0) - buffer_size = BufferSizes [mode & 7]; + buffer_size = DS2_BUFFER_SIZE; if (buffer_size > MAX_BUFFER_SIZE / 4) buffer_size = MAX_BUFFER_SIZE / 4; @@ -936,7 +924,7 @@ void S9xProcessSound (unsigned int) // block_generate_sound = FALSE; unsigned short *dst_pt = audiobuff; - unsigned short *dst_pt1 = dst_pt + 512; + unsigned short *dst_pt1 = dst_pt + DS2_BUFFER_SIZE; /* Feed the samples to the soundcard until nothing is left */ for(;;) -- cgit v1.2.3 From 0f60f047f5146c76a73c8a299b4405929bf3909f Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Wed, 26 Dec 2012 15:40:35 -0500 Subject: Add the update methods for the upper and lower screen into defines. --- source/nds/entry.cpp | 6 +++--- source/nds/gui.c | 48 ++++++++++++++++++++++++------------------------ source/nds/gui.h | 6 +++++- 3 files changed, 32 insertions(+), 28 deletions(-) (limited to 'source/nds') diff --git a/source/nds/entry.cpp b/source/nds/entry.cpp index a8e2217..9d0f0bc 100644 --- a/source/nds/entry.cpp +++ b/source/nds/entry.cpp @@ -175,7 +175,7 @@ bool8 S9xDeinitUpdate (int Width, int Height, bool8 /*sixteen_bit*/) break; } - ds2_flipScreen(UP_SCREEN, 0); + ds2_flipScreen(UP_SCREEN, UP_SCREEN_UPDATE_METHOD); // A problem with update method 1 (wait, double buffer) means that, after // about 15 minutes of play time, the screen starts to half-redraw every // frame. With update method 0, this is mitigated. (Method 2 is too slow.) @@ -586,9 +586,9 @@ int sfc_main (int argc, char **argv) { if (!Settings.Paused #ifdef DEBUGGER - || (CPU.Flags & (DEBUG_MODE_FLAG | SINGLE_STEP_FLAG)) + || (CPU.Flags & (DEBUG_MODE_FLAG | SINGLE_STEP_FLAG) #endif - ) + ) S9xMainLoop (); diff --git a/source/nds/gui.c b/source/nds/gui.c index 3438f62..9aa16bb 100644 --- a/source/nds/gui.c +++ b/source/nds/gui.c @@ -1114,7 +1114,7 @@ s32 load_file(char **wildcards, char *result, char *default_dir_name) } redraw = 0; - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); } //end if(0 != redraw) else if(0 != redraw) { unsigned int m, n; @@ -1142,7 +1142,7 @@ s32 load_file(char **wildcards, char *result, char *default_dir_name) } draw_hscroll(m+1, redraw); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); redraw = 0; } @@ -1162,7 +1162,7 @@ s32 load_file(char **wildcards, char *result, char *default_dir_name) { if(draw_hscroll(0, 1) <= 1) path_scroll = 0x8000; //scroll left } - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); } mdelay(50); //about 50ms @@ -1176,7 +1176,7 @@ s32 load_file(char **wildcards, char *result, char *default_dir_name) manage_filelist_info(&filelist_info, -1); ds2_clearScreen(DOWN_SCREEN, COLOR_BLACK); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); return return_value; } @@ -1233,7 +1233,7 @@ u32 play_screen_snapshot(void) { draw_message(down_screen_addr, screenp, 28, 31, 227, 165, color_bg); draw_string_vcenter(down_screen_addr, 36, 55, 190, COLOR_MSSG, msg[MSG_NO_SLIDE]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); if(screenp) free((void*)screenp); //construct filelist_info struct @@ -1260,7 +1260,7 @@ u32 play_screen_snapshot(void) draw_string_vcenter(down_screen_addr, 36, 115, 190, COLOR_MSSG, msg[MSG_PLAY_SLIDE4]); draw_string_vcenter(down_screen_addr, 36, 130, 190, COLOR_MSSG, msg[MSG_PLAY_SLIDE5]); draw_string_vcenter(down_screen_addr, 36, 145, 190, COLOR_MSSG, msg[MSG_PLAY_SLIDE6]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); repeat= 1; i= 0; @@ -1749,7 +1749,7 @@ u32 menu(u16 *screen) draw_message(down_screen_addr, bg_screenp, 28, 31, 227, 165, bg_screenp_color); draw_string_vcenter(down_screen_addr, 36, 100, 190, COLOR_MSSG, msg[MSG_LOADING_GAME]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); ds2_setCPUclocklevel(13); int load_result = load_gamepak(&line_buffer); @@ -1817,7 +1817,7 @@ u32 menu(u16 *screen) draw_message(down_screen_addr, bg_screenp, 28, 31, 227, 165, bg_screenp_color); draw_string_vcenter(down_screen_addr, 36, 100, 190, COLOR_MSSG, msg[MSG_LOADING_GAME]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); ds2_setCPUclocklevel(13); int load_result = load_gamepak(args[1]); @@ -2047,7 +2047,7 @@ u32 menu(u16 *screen) draw_message(down_screen_addr, NULL, 28, 31, 227, 165, 0); draw_string_vcenter(down_screen_addr, 36, 100, 190, COLOR_MSSG, msg[MSG_SAVESTATE_DOING]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); int flag = save_state(tmp_filename, (void*)screen); //clear message @@ -2063,7 +2063,7 @@ u32 menu(u16 *screen) savestate_index = slot_index; } - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); //save game config reorder_latest_file(); @@ -2100,7 +2100,7 @@ u32 menu(u16 *screen) { draw_message(down_screen_addr, bg_screenp, 28, 31, 227, 165, bg_screenp_color); draw_string_vcenter(down_screen_addr, 36, 80, 190, COLOR_MSSG, msg[MSG_SAVESTATE_FILE_BAD]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); wait_Allkey_release(0); if(gui_action == CURSOR_SELECT) @@ -2186,7 +2186,7 @@ u32 menu(u16 *screen) { draw_message(down_screen_addr, bg_screenp, 28, 31, 227, 165, bg_screenp_color); draw_string_vcenter(down_screen_addr, 36, 90, 190, COLOR_MSSG, msg[MSG_DELETTE_SAVESTATE_NOTHING]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); mdelay(500); } } @@ -2207,7 +2207,7 @@ u32 menu(u16 *screen) else { draw_string_vcenter(down_screen_addr, 36, 90, 190, COLOR_MSSG, msg[MSG_DELETTE_SAVESTATE_NOTHING]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); mdelay(500); } } @@ -2578,18 +2578,18 @@ u32 menu(u16 *screen) if(!first_load) { draw_string_vcenter(down_screen_addr, 36, 70, 190, COLOR_MSSG, msg[MSG_SAVE_SNAPSHOT]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); if(save_ss_bmp(screen)) draw_string_vcenter(down_screen_addr, 36, 90, 190, COLOR_MSSG, msg[MSG_SAVE_SNAPSHOT_COMPLETE]); else draw_string_vcenter(down_screen_addr, 36, 90, 190, COLOR_MSSG, msg[MSG_SAVE_SNAPSHOT_FAILURE]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); mdelay(500); } else { draw_string_vcenter(down_screen_addr, 36, 90, 190, COLOR_MSSG, msg[MSG_SAVESTATE_SLOT_EMPTY]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); mdelay(500); } } @@ -2746,7 +2746,7 @@ u32 menu(u16 *screen) wait_Allkey_release(0); draw_message(down_screen_addr, bg_screenp, 28, 31, 227, 165, bg_screenp_color); draw_string_vcenter(down_screen_addr, 36, 80, 190, COLOR_MSSG, msg[MSG_DEFAULT_LOADING]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); sprintf(line_buffer, "%s/%s", main_path, EMU_CONFIG_FILENAME); remove(line_buffer); @@ -2777,7 +2777,7 @@ u32 menu(u16 *screen) draw_string_vcenter(down_screen_addr, 36, 80, 190, COLOR_MSSG, msg[MSG_EMU_VERSION0]); sprintf(line_buffer, "%s %s", msg[MSG_EMU_VERSION1], NDSSFC_VERSION); draw_string_vcenter(down_screen_addr, 36, 95, 190, COLOR_MSSG, line_buffer); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); wait_Anykey_press(0); } @@ -2797,7 +2797,7 @@ u32 menu(u16 *screen) draw_message(down_screen_addr, bg_screenp, 28, 31, 227, 165, bg_screenp_color); draw_string_vcenter(down_screen_addr, 36, 75, 190, COLOR_MSSG, msg[MSG_CHANGE_LANGUAGE]); draw_string_vcenter(down_screen_addr, 36, 95, 190, COLOR_MSSG, msg[MSG_CHANGE_LANGUAGE_WAITING]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); load_language_msg(LANGUAGE_PACK, emu_config.language); gui_change_icon(emu_config.language); @@ -3405,7 +3405,7 @@ u32 menu(u16 *screen) draw_message(down_screen_addr, bg_screenp, 28, 31, 227, 165, 0); draw_string_vcenter(down_screen_addr, 36, 100, 190, COLOR_MSSG, msg[MSG_LOADING_GAME]); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); if(gamepak_name[0] != 0) { @@ -3977,7 +3977,7 @@ u32 menu(u16 *screen) break; } // end swith - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); } // end while destroy_dynamic_cheats(); if(bg_screenp != NULL) free((void*)bg_screenp); @@ -3996,7 +3996,7 @@ u32 menu(u16 *screen) ds2_clearScreen(DOWN_SCREEN, 0); ds2_flipScreen(DOWN_SCREEN, 1); copy_screen(up_screen_addr, (void*) screen, 0, 0, 256, 192); - ds2_flipScreen(UP_SCREEN, 0); + ds2_flipScreen(UP_SCREEN, UP_SCREEN_UPDATE_METHOD); ds2_setBacklight(2); wait_Allkey_release(0); @@ -4714,7 +4714,7 @@ void gui_init(u32 lang_id) } show_log(down_screen_addr); - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); flag = icon_init(lang_id); if(0 != flag) @@ -4750,7 +4750,7 @@ void gui_init(u32 lang_id) return; gui_init_err: - ds2_flipScreen(DOWN_SCREEN, 2); + ds2_flipScreen(DOWN_SCREEN, DOWN_SCREEN_UPDATE_METHOD); wait_Anykey_press(0); quit(); } diff --git a/source/nds/gui.h b/source/nds/gui.h index 3b222d1..9ebaf26 100644 --- a/source/nds/gui.h +++ b/source/nds/gui.h @@ -24,6 +24,9 @@ #include "fs_api.h" #include "gcheat.h" +#define UP_SCREEN_UPDATE_METHOD 0 +#define DOWN_SCREEN_UPDATE_METHOD 2 + #define MAX_GAMEPAD_MAP 16 #ifdef __cplusplus @@ -96,7 +99,8 @@ extern char rom_path[MAX_PATH]; extern u32 game_enable_audio; /****************************************************************************** - ******************************************************************************/ extern char g_default_rom_dir[MAX_PATH]; + ******************************************************************************/ +extern char g_default_rom_dir[MAX_PATH]; extern char DEFAULT_RTS_DIR[MAX_PATH]; extern char DEFAULT_CFG_DIR[MAX_PATH]; extern char DEFAULT_SS_DIR[MAX_PATH]; -- cgit v1.2.3 From 6b36e79013d4c9273a96a9783a2bccdb516f174a Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Thu, 27 Dec 2012 18:02:03 -0500 Subject: Speed up rendering by an unknown amount. gfx.cpp, others: Avoid always checking for Settings.SixteenBit if FOREVER_16_BIT is defined. port.h: Define FOREVER_16_BIT below PIXEL_FORMAT. --- source/nds/entry.cpp | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'source/nds') diff --git a/source/nds/entry.cpp b/source/nds/entry.cpp index 9d0f0bc..1589c21 100644 --- a/source/nds/entry.cpp +++ b/source/nds/entry.cpp @@ -384,7 +384,9 @@ void init_sfc_setting(void) Settings.ControllerOption = SNES_JOYPAD; Settings.Transparency = TRUE; +#ifndef FOREVER_16_BIT Settings.SixteenBit = TRUE; +#endif Settings.SupportHiRes = FALSE; Settings.ThreadSound = FALSE; @@ -792,6 +794,7 @@ bool8 S9xOpenSoundDevice (int mode, bool8 stereo, int buffer_size) void S9xGenerateSound () { +#if 0 int bytes_so_far = so.sixteen_bit ? (so.samples_mixed_so_far << 1) : so.samples_mixed_so_far; @@ -853,10 +856,12 @@ void S9xGenerateSound () S9xProcessSound (0); pending_signal = FALSE; } +#endif } void S9xProcessSound (unsigned int) { +#if 0 unsigned short *audiobuff; if (!Settings.APUEnabled || so.mute_sound ) @@ -957,6 +962,7 @@ void S9xProcessSound (unsigned int) } so.samples_mixed_so_far -= sample_count; +#endif } void Init_Timer (void) -- cgit v1.2.3 From 963c3459e51264ccf0cc501a41e45de6e71eeea3 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Thu, 27 Dec 2012 18:10:31 -0500 Subject: Accidentally committed the previous revision with sound functions emptied. --- source/nds/entry.cpp | 4 ---- 1 file changed, 4 deletions(-) (limited to 'source/nds') diff --git a/source/nds/entry.cpp b/source/nds/entry.cpp index 1589c21..b4467a1 100644 --- a/source/nds/entry.cpp +++ b/source/nds/entry.cpp @@ -794,7 +794,6 @@ bool8 S9xOpenSoundDevice (int mode, bool8 stereo, int buffer_size) void S9xGenerateSound () { -#if 0 int bytes_so_far = so.sixteen_bit ? (so.samples_mixed_so_far << 1) : so.samples_mixed_so_far; @@ -856,12 +855,10 @@ void S9xGenerateSound () S9xProcessSound (0); pending_signal = FALSE; } -#endif } void S9xProcessSound (unsigned int) { -#if 0 unsigned short *audiobuff; if (!Settings.APUEnabled || so.mute_sound ) @@ -962,7 +959,6 @@ void S9xProcessSound (unsigned int) } so.samples_mixed_so_far -= sample_count; -#endif } void Init_Timer (void) -- cgit v1.2.3 From c01a2a42168695233ecc69c4a60ed918e7701fb9 Mon Sep 17 00:00:00 2001 From: Nebuleon Fumika Date: Fri, 28 Dec 2012 01:45:40 -0500 Subject: Keep the audio processing unit (APU) enabled even when the user disabled the audio for a game. This allows some games that synchronise on the APU's actions to continue working. --- source/nds/entry.cpp | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-) (limited to 'source/nds') diff --git a/source/nds/entry.cpp b/source/nds/entry.cpp index b4467a1..33566d5 100644 --- a/source/nds/entry.cpp +++ b/source/nds/entry.cpp @@ -341,12 +341,10 @@ void game_disableAudio() { if( game_enable_audio == 1) { - Settings.APUEnabled = Settings.NextAPUEnabled = TRUE; S9xSetSoundMute (FALSE); } else { - Settings.APUEnabled = Settings.NextAPUEnabled = FALSE; S9xSetSoundMute (TRUE); } } @@ -510,8 +508,6 @@ int load_gamepak(char* file) */ // mdelay(50); // Delete this delay - if (!Settings.APUEnabled) - S9xSetSoundMute (FALSE); return 0; } @@ -535,9 +531,6 @@ int sfc_main (int argc, char **argv) S9xInitSound (Settings.SoundPlaybackRate, Settings.Stereo, Settings.SoundBufferSize); - if (!Settings.APUEnabled) - S9xSetSoundMute (TRUE); - #ifdef GFX_MULTI_FORMAT // S9xSetRenderPixelFormat (RGB565); S9xSetRenderPixelFormat (BGR555); @@ -861,7 +854,7 @@ void S9xProcessSound (unsigned int) { unsigned short *audiobuff; - if (!Settings.APUEnabled || so.mute_sound ) + if (so.mute_sound || !game_enable_audio) return; if(ds2_checkAudiobuff() > 4) -- cgit v1.2.3