Proper handling of UTF-8

Note: This commit may be slightly broken, I'm just splitting up it and the next one at the end.
This commit is contained in:
Pk11 2021-08-01 23:23:01 -05:00 committed by d0k3
parent 0e46d4fca8
commit 2f00e5dfe7
10 changed files with 83 additions and 82 deletions

View File

@ -90,7 +90,7 @@ static void DrawKey(const TouchBox* key, const bool pressed, const u32 uppercase
const u32 f_offs_y = (key->h - FONT_HEIGHT_EXT) / 2; const u32 f_offs_y = (key->h - FONT_HEIGHT_EXT) / 2;
DrawRectangle(BOT_SCREEN, key->x, key->y, key->w, key->h, color); DrawRectangle(BOT_SCREEN, key->x, key->y, key->w, key->h, color);
DrawString(BOT_SCREEN, keystr, key->x + f_offs_x, key->y + f_offs_y, COLOR_SWKBD_CHARS, color, false); DrawString(BOT_SCREEN, keystr, key->x + f_offs_x, key->y + f_offs_y, COLOR_SWKBD_CHARS, color);
} }
static void DrawKeyBoardBox(TouchBox* swkbd, u32 color) { static void DrawKeyBoardBox(TouchBox* swkbd, u32 color) {
@ -227,7 +227,7 @@ bool ShowKeyboard(char* inputstr, const u32 max_size, const char *format, ...) {
TouchBox* textbox = swkbd_alphabet; // always use this textbox TouchBox* textbox = swkbd_alphabet; // always use this textbox
static bool show_instr = true; static bool show_instr = true;
static const char* instr = "Keyboard Controls:\n \n\x1B/\x1A - Move cursor\nR - Caps / Capslock\nX - Delete char\nY - Insert char\nA - Submit\nB - Cancel\n \nSELECT switches to\nclassic prompt"; static const char* instr = "Keyboard Controls:\n \n←/→ - Move cursor\nR - Caps / Capslock\nX - Delete char\nY - Insert char\nA - Submit\nB - Cancel\n \nSELECT switches to\nclassic prompt";
if (show_instr) { if (show_instr) {
ShowPrompt(false, instr); ShowPrompt(false, instr);
show_instr = false; show_instr = false;

View File

@ -23,7 +23,7 @@ enum {
}; };
// special key strings // special key strings
#define SWKBD_KEYSTR "", "DEL", "INS", "SUBMIT", "CAPS", "#$@", "123", "ABC", "\x1b", "\x1a", "ESC", "SWITCH" #define SWKBD_KEYSTR "", "DEL", "INS", "SUBMIT", "CAPS", "#$@", "123", "ABC", "←", "→", "ESC", "SWITCH"
#define COLOR_SWKBD_NORMAL COLOR_GREY #define COLOR_SWKBD_NORMAL COLOR_GREY
#define COLOR_SWKBD_PRESSED COLOR_LIGHTGREY #define COLOR_SWKBD_PRESSED COLOR_LIGHTGREY

View File

@ -57,8 +57,8 @@ void DrawRectangle(u16 *screen, int x, int y, u32 width, u32 height, u32 color);
void DrawBitmap(u16 *screen, int x, int y, u32 w, u32 h, const u16* bitmap); void DrawBitmap(u16 *screen, int x, int y, u32 w, u32 h, const u16* bitmap);
void DrawQrCode(u16 *screen, const u8* qrcode); void DrawQrCode(u16 *screen, const u8* qrcode);
void DrawCharacter(u16 *screen, int character, int x, int y, u32 color, u32 bgcolor); void DrawCharacter(u16 *screen, u32 character, int x, int y, u32 color, u32 bgcolor);
void DrawString(u16 *screen, const char *str, int x, int y, u32 color, u32 bgcolor, bool fix_utf8); void DrawString(u16 *screen, const char *str, int x, int y, u32 color, u32 bgcolor);
void DrawStringF(u16 *screen, int x, int y, u32 color, u32 bgcolor, const char *format, ...); void DrawStringF(u16 *screen, int x, int y, u32 color, u32 bgcolor, const char *format, ...);
void DrawStringCenter(u16 *screen, u32 color, u32 bgcolor, const char *format, ...); void DrawStringCenter(u16 *screen, u32 color, u32 bgcolor, const char *format, ...);
@ -69,8 +69,8 @@ u32 GetFontHeight(void);
void MultiLineString(char* dest, const char* orig, int llen, int maxl); void MultiLineString(char* dest, const char* orig, int llen, int maxl);
void WordWrapString(char* str, int llen); void WordWrapString(char* str, int llen);
void ResizeString(char* dest, const char* orig, int nsize, int tpos, bool align_right); void ResizeString(char* dest, const char* orig, int nlength, int tpos, bool align_right);
void TruncateString(char* dest, const char* orig, int nsize, int tpos); void TruncateString(char* dest, const char* orig, int nlength, int tpos);
void FormatNumber(char* str, u64 number); void FormatNumber(char* str, u64 number);
void FormatBytes(char* str, u64 bytes); void FormatBytes(char* str, u64 bytes);

View File

@ -34,7 +34,7 @@ bool GoodRenamer(DirEntry* entry, bool ask) {
return false; return false;
if (ask) { // ask for confirmatiom if (ask) { // ask for confirmatiom
char oldname_tr[32+1]; char oldname_tr[32 * 4 + 1];
char newname_ww[256]; char newname_ww[256];
TruncateString(oldname_tr, entry->name, 32, 8); TruncateString(oldname_tr, entry->name, 32, 8);
strncpy(newname_ww, goodname, 256); strncpy(newname_ww, goodname, 256);

View File

@ -127,7 +127,7 @@ bool FileUnlock(const char* path) {
if (!(DriveType(path) & DRV_FAT)) return true; // can't really check this if (!(DriveType(path) & DRV_FAT)) return true; // can't really check this
if ((res = fx_open(&file, path, FA_READ | FA_OPEN_EXISTING)) != FR_OK) { if ((res = fx_open(&file, path, FA_READ | FA_OPEN_EXISTING)) != FR_OK) {
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
if (GetMountState() && (res == FR_LOCKED) && if (GetMountState() && (res == FR_LOCKED) &&
(ShowPrompt(true, "%s\nFile is currently mounted.\nUnmount to unlock?", pathstr))) { (ShowPrompt(true, "%s\nFile is currently mounted.\nUnmount to unlock?", pathstr))) {
@ -460,7 +460,7 @@ bool PathMoveCopyRec(char* dest, char* orig, u32* flags, bool move, u8* buffer,
if (move && (to_virtual || fno.fattrib & AM_VRT)) return false; // trying to move a virtual file if (move && (to_virtual || fno.fattrib & AM_VRT)) return false; // trying to move a virtual file
// path string (for output) // path string (for output)
char deststr[36 + 1]; char deststr[36 * 4 + 1];
TruncateString(deststr, dest, 36, 8); TruncateString(deststr, dest, 36, 8);
// the copy process takes place here // the copy process takes place here
@ -608,7 +608,7 @@ bool PathMoveCopy(const char* dest, const char* orig, u32* flags, bool move) {
char lorig[256]; char lorig[256];
strncpy(ldest, dest, 256); strncpy(ldest, dest, 256);
strncpy(lorig, orig, 256); strncpy(lorig, orig, 256);
char deststr[36 + 1]; char deststr[36 * 4 + 1];
TruncateString(deststr, ldest, 36, 8); TruncateString(deststr, ldest, 36, 8);
// moving only for regular FAT drives (= not alias drives) // moving only for regular FAT drives (= not alias drives)
@ -748,8 +748,8 @@ bool PathCopy(const char* destdir, const char* orig, u32* flags) {
return false; return false;
snprintf(dest, 255, "%s/%s", destdir, dvfile.name); snprintf(dest, 255, "%s/%s", destdir, dvfile.name);
} else if (osize < dvfile.size) { // if origin is smaller than destination... } else if (osize < dvfile.size) { // if origin is smaller than destination...
char deststr[36 + 1]; char deststr[36 * 4 + 1];
char origstr[36 + 1]; char origstr[36 * 4 + 1];
char osizestr[32]; char osizestr[32];
char dsizestr[32]; char dsizestr[32];
TruncateString(deststr, dest, 36, 8); TruncateString(deststr, dest, 36, 8);
@ -821,7 +821,7 @@ bool FileSelectorWorker(char* result, const char* text, const char* path, const
GetDirContents(contents, path_local); GetDirContents(contents, path_local);
while (pos < contents->n_entries) { while (pos < contents->n_entries) {
char opt_names[_MAX_FS_OPT+1][32+1]; char opt_names[_MAX_FS_OPT+1][32 * 4 + 1];
DirEntry* res_entry[MAX_DIR_ENTRIES+1] = { NULL }; DirEntry* res_entry[MAX_DIR_ENTRIES+1] = { NULL };
u32 n_opt = 0; u32 n_opt = 0;
for (; pos < contents->n_entries; pos++) { for (; pos < contents->n_entries; pos++) {
@ -871,7 +871,7 @@ bool FileSelectorWorker(char* result, const char* text, const char* path, const
} }
} }
if (!n_found) { // not a single matching entry found if (!n_found) { // not a single matching entry found
char pathstr[32+1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path_local, 32, 8); TruncateString(pathstr, path_local, 32, 8);
ShowPrompt(false, "%s\nNo usable entries found.", pathstr); ShowPrompt(false, "%s\nNo usable entries found.", pathstr);
return false; return false;

View File

@ -51,7 +51,7 @@ typedef struct {
u32 BootFirmHandler(const char* bootpath, bool verbose, bool delete) { u32 BootFirmHandler(const char* bootpath, bool verbose, bool delete) {
char pathstr[32+1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, bootpath, 32, 8); TruncateString(pathstr, bootpath, 32, 8);
size_t firm_size = FileGetSize(bootpath); size_t firm_size = FileGetSize(bootpath);
@ -231,7 +231,7 @@ void DrawTopBar(const char* curr_path) {
const u32 bartxt_start = (FONT_HEIGHT_EXT >= 10) ? 1 : (FONT_HEIGHT_EXT >= 7) ? 2 : 3; const u32 bartxt_start = (FONT_HEIGHT_EXT >= 10) ? 1 : (FONT_HEIGHT_EXT >= 7) ? 2 : 3;
const u32 bartxt_x = 2; const u32 bartxt_x = 2;
const u32 len_path = SCREEN_WIDTH_TOP - 120; const u32 len_path = SCREEN_WIDTH_TOP - 120;
char tempstr[64]; char tempstr[64 * 4];
// top bar - current path // top bar - current path
DrawRectangle(TOP_SCREEN, 0, 0, SCREEN_WIDTH_TOP, 12, COLOR_TOP_BAR); DrawRectangle(TOP_SCREEN, 0, 0, SCREEN_WIDTH_TOP, 12, COLOR_TOP_BAR);
@ -282,7 +282,7 @@ void DrawUserInterface(const char* curr_path, DirEntry* curr_entry, u32 curr_pan
const u32 instr_x = (SCREEN_WIDTH_MAIN - (34*FONT_WIDTH_EXT)) / 2; const u32 instr_x = (SCREEN_WIDTH_MAIN - (34*FONT_WIDTH_EXT)) / 2;
const u32 len_info = (SCREEN_WIDTH_MAIN - ((SCREEN_WIDTH_MAIN >= 400) ? 80 : 20)) / 2; const u32 len_info = (SCREEN_WIDTH_MAIN - ((SCREEN_WIDTH_MAIN >= 400) ? 80 : 20)) / 2;
const u32 str_len_info = min(63, len_info / FONT_WIDTH_EXT); const u32 str_len_info = min(63, len_info / FONT_WIDTH_EXT);
char tempstr[64]; char tempstr[256];
static u32 state_prev = 0xFFFFFFFF; static u32 state_prev = 0xFFFFFFFF;
u32 state_curr = u32 state_curr =
@ -359,14 +359,14 @@ void DrawUserInterface(const char* curr_path, DirEntry* curr_entry, u32 curr_pan
char instr[512]; char instr[512];
snprintf(instr, 512, "%s\n%s%s%s%s%s%s%s%s", snprintf(instr, 512, "%s\n%s%s%s%s%s%s%s%s",
FLAVOR " " VERSION, // generic start part FLAVOR " " VERSION, // generic start part
(*curr_path) ? ((clipboard->n_entries == 0) ? "L - MARK files (use with \x18\x19\x1A\x1B)\nX - DELETE / [+R] RENAME file(s)\nY - COPY files / [+R] CREATE entry\n" : (*curr_path) ? ((clipboard->n_entries == 0) ? "L - MARK files (use with ↑↓→←)\nX - DELETE / [+R] RENAME file(s)\nY - COPY files / [+R] CREATE entry\n" :
"L - MARK files (use with \x18\x19\x1A\x1B)\nX - DELETE / [+R] RENAME file(s)\nY - PASTE files / [+R] CREATE entry\n") : "L - MARK files (use with ↑↓→←)\nX - DELETE / [+R] RENAME file(s)\nY - PASTE files / [+R] CREATE entry\n") :
((GetWritePermissions() > PERM_BASE) ? "R+Y - Relock write permissions\n" : ""), ((GetWritePermissions() > PERM_BASE) ? "R+Y - Relock write permissions\n" : ""),
(*curr_path) ? "" : (GetMountState()) ? "R+X - Unmount image\n" : "", (*curr_path) ? "" : (GetMountState()) ? "R+X - Unmount image\n" : "",
(*curr_path) ? "" : (CheckSDMountState()) ? "R+B - Unmount SD card\n" : "R+B - Remount SD card\n", (*curr_path) ? "" : (CheckSDMountState()) ? "R+B - Unmount SD card\n" : "R+B - Remount SD card\n",
(*curr_path) ? "R+A - Directory options\n" : "R+A - Drive options\n", (*curr_path) ? "R+A - Directory options\n" : "R+A - Drive options\n",
"R+L - Make a Screenshot\n", "R+L - Make a Screenshot\n",
"R+\x1B\x1A - Switch to prev/next pane\n", "R+←→ - Switch to prev/next pane\n",
(clipboard->n_entries) ? "SELECT - Clear Clipboard\n" : "SELECT - Restore Clipboard\n", // only if clipboard is full (clipboard->n_entries) ? "SELECT - Clear Clipboard\n" : "SELECT - Restore Clipboard\n", // only if clipboard is full
"START - Reboot / [+R] Poweroff\nHOME button for HOME menu"); // generic end part "START - Reboot / [+R] Poweroff\nHOME button for HOME menu"); // generic end part
DrawStringF(MAIN_SCREEN, instr_x, SCREEN_HEIGHT - 4 - GetDrawStringHeight(instr), COLOR_STD_FONT, COLOR_STD_BG, instr); DrawStringF(MAIN_SCREEN, instr_x, SCREEN_HEIGHT - 4 - GetDrawStringHeight(instr), COLOR_STD_FONT, COLOR_STD_BG, instr);
@ -386,17 +386,17 @@ void DrawDirContents(DirStruct* contents, u32 cursor, u32* scroll) {
*scroll = (contents->n_entries > lines) ? contents->n_entries - lines : 0; *scroll = (contents->n_entries > lines) ? contents->n_entries - lines : 0;
for (u32 i = 0; pos_y < SCREEN_HEIGHT; i++) { for (u32 i = 0; pos_y < SCREEN_HEIGHT; i++) {
char tempstr[str_width + 1]; char tempstr[str_width * 4 + 1];
u32 offset_i = *scroll + i; u32 offset_i = *scroll + i;
u32 color_font = COLOR_WHITE; u32 color_font = COLOR_WHITE;
if (offset_i < contents->n_entries) { if (offset_i < contents->n_entries) {
DirEntry* curr_entry = &(contents->entry[offset_i]); DirEntry* curr_entry = &(contents->entry[offset_i]);
char namestr[str_width - 10 + 1]; char namestr[str_width * 4 - 10 + 1];
char bytestr[10 + 1]; char bytestr[10 + 1];
color_font = (cursor != offset_i) ? COLOR_ENTRY(curr_entry) : COLOR_STD_FONT; color_font = (cursor != offset_i) ? COLOR_ENTRY(curr_entry) : COLOR_STD_FONT;
FormatBytes(bytestr, curr_entry->size); FormatBytes(bytestr, curr_entry->size);
ResizeString(namestr, curr_entry->name, str_width - 10, str_width - 20, false); ResizeString(namestr, curr_entry->name, str_width - 10, str_width - 20, false);
snprintf(tempstr, str_width + 1, "%s%10.10s", namestr, snprintf(tempstr, str_width * 4 + 1, "%s%10.10s", namestr,
(curr_entry->type == T_DIR) ? "(dir)" : (curr_entry->type == T_DOTDOT) ? "(..)" : bytestr); (curr_entry->type == T_DIR) ? "(dir)" : (curr_entry->type == T_DOTDOT) ? "(..)" : bytestr);
} else snprintf(tempstr, str_width + 1, "%-*.*s", str_width, str_width, ""); } else snprintf(tempstr, str_width + 1, "%-*.*s", str_width, str_width, "");
DrawStringF(ALT_SCREEN, pos_x, pos_y, color_font, COLOR_STD_BG, "%s", tempstr); DrawStringF(ALT_SCREEN, pos_x, pos_y, color_font, COLOR_STD_BG, "%s", tempstr);
@ -570,7 +570,7 @@ u32 FileHexViewer(const char* path) {
} }
static bool show_instr = true; static bool show_instr = true;
static const char* instr = "Hexeditor Controls:\n \n\x18\x19\x1A\x1B(+R) - Scroll\nR+Y - Switch view\nX - Search / goto...\nA - Enter edit mode\nA+\x18\x19\x1A\x1B - Edit value\nB - Exit\n"; static const char* instr = "Hexeditor Controls:\n ↑↓→←(+R) - Scroll\nR+Y - Switch view\nX - Search / goto...\nA - Enter edit mode\nA+↑↓→← - Edit value\nB - Exit\n";
if (show_instr) { // show one time instructions if (show_instr) { // show one time instructions
ShowPrompt(false, instr); ShowPrompt(false, instr);
show_instr = false; show_instr = false;
@ -709,7 +709,8 @@ u32 FileHexViewer(const char* path) {
if (x_off >= 0) DrawStringF(screen, x_off - x0, y, cutoff ? COLOR_HVOFFS : COLOR_HVOFFSI, if (x_off >= 0) DrawStringF(screen, x_off - x0, y, cutoff ? COLOR_HVOFFS : COLOR_HVOFFSI,
COLOR_STD_BG, "%08X", (unsigned int) offset + curr_pos); COLOR_STD_BG, "%08X", (unsigned int) offset + curr_pos);
if (x_ascii >= 0) { if (x_ascii >= 0) {
DrawString(screen, ascii, x_ascii - x0, y, COLOR_HVASCII, COLOR_STD_BG, false); for (u32 i = 0; i < cols; i++)
DrawCharacter(screen, ascii[i], x_ascii - x0 + (FONT_WIDTH_EXT * i), y, COLOR_HVASCII, COLOR_STD_BG);
for (u32 i = (u32) marked0; i < (u32) marked1; i++) for (u32 i = (u32) marked0; i < (u32) marked1; i++)
DrawCharacter(screen, ascii[i % cols], x_ascii - x0 + (FONT_WIDTH_EXT * i), y, COLOR_MARKED, COLOR_STD_BG); DrawCharacter(screen, ascii[i % cols], x_ascii - x0 + (FONT_WIDTH_EXT * i), y, COLOR_MARKED, COLOR_STD_BG);
if (edit_mode && ((u32) cursor / cols == row)) DrawCharacter(screen, ascii[cursor % cols], if (edit_mode && ((u32) cursor / cols == row)) DrawCharacter(screen, ascii[cursor % cols],
@ -844,7 +845,7 @@ u32 FileHexViewer(const char* path) {
u32 Sha256Calculator(const char* path) { u32 Sha256Calculator(const char* path) {
u32 drvtype = DriveType(path); u32 drvtype = DriveType(path);
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
u8 sha256[32]; u8 sha256[32];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
if (!FileGetSha256(path, sha256, 0, 0)) { if (!FileGetSha256(path, sha256, 0, 0)) {
@ -879,7 +880,7 @@ u32 Sha256Calculator(const char* path) {
} }
u32 CmacCalculator(const char* path) { u32 CmacCalculator(const char* path) {
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
if (IdentifyFileType(path) != GAME_CMD) { if (IdentifyFileType(path) != GAME_CMD) {
u8 cmac[16] __attribute__((aligned(4))); u8 cmac[16] __attribute__((aligned(4)));
@ -930,7 +931,7 @@ u32 StandardCopy(u32* cursor, u32* scroll) {
DrawDirContents(current_dir, (*cursor = i), scroll); DrawDirContents(current_dir, (*cursor = i), scroll);
if (PathCopy(OUTPUT_PATH, path, &flags)) n_success++; if (PathCopy(OUTPUT_PATH, path, &flags)) n_success++;
else { // on failure: show error, break else { // on failure: show error, break
char currstr[32+1]; char currstr[32 * 4 + 1];
TruncateString(currstr, path, 32, 12); TruncateString(currstr, path, 32, 12);
ShowPrompt(false, "%s\nFailed copying item", currstr); ShowPrompt(false, "%s\nFailed copying item", currstr);
break; break;
@ -939,7 +940,7 @@ u32 StandardCopy(u32* cursor, u32* scroll) {
} }
if (n_success) ShowPrompt(false, "%lu items copied to %s", n_success, OUTPUT_PATH); if (n_success) ShowPrompt(false, "%lu items copied to %s", n_success, OUTPUT_PATH);
} else { } else {
char pathstr[32+1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, curr_entry->path, 32, 8); TruncateString(pathstr, curr_entry->path, 32, 8);
if (!PathCopy(OUTPUT_PATH, curr_entry->path, &flags)) if (!PathCopy(OUTPUT_PATH, curr_entry->path, &flags))
ShowPrompt(false, "%s\nFailed copying item", pathstr); ShowPrompt(false, "%s\nFailed copying item", pathstr);
@ -1012,12 +1013,12 @@ u32 DirFileAttrMenu(const char* path, const char *name) {
"[%c] %ssystem [%c] %sarchive\n" "[%c] %ssystem [%c] %sarchive\n"
"[%c] %svirtual\n" "[%c] %svirtual\n"
"%s", "%s",
(new_attrib & AM_RDO) ? 'X' : ' ', vrt ? "" : "\x18 ", (new_attrib & AM_RDO) ? 'X' : ' ', vrt ? "" : "",
(new_attrib & AM_HID) ? 'X' : ' ', vrt ? "" : "\x19 ", (new_attrib & AM_HID) ? 'X' : ' ', vrt ? "" : "",
(new_attrib & AM_SYS) ? 'X' : ' ', vrt ? "" : "\x1A ", (new_attrib & AM_SYS) ? 'X' : ' ', vrt ? "" : "",
(new_attrib & AM_ARC) ? 'X' : ' ', vrt ? "" : "\x1B ", (new_attrib & AM_ARC) ? 'X' : ' ', vrt ? "" : "",
vrt ? 'X' : ' ', vrt ? "" : " ", vrt ? 'X' : ' ', vrt ? "" : " ",
vrt ? "" : " \n(\x18\x19\x1A\x1B to change attributes)\n" vrt ? "" : " \n(↑↓→← to change attributes)\n"
); );
} }
@ -1141,7 +1142,7 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
keyinstallable || bootable || scriptable || fontable || viewable || installable || agbexportable || keyinstallable || bootable || scriptable || fontable || viewable || installable || agbexportable ||
agbimportable || cia_installable || tik_installable || tik_dumpable; agbimportable || cia_installable || tik_installable || tik_dumpable;
char pathstr[32+1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, file_path, 32, 8); TruncateString(pathstr, file_path, 32, 8);
char tidstr[32] = { 0 }; char tidstr[32] = { 0 };
@ -1205,7 +1206,7 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
(filetype & BIN_LEGKEY) ? "Build " KEYDB_NAME : (filetype & BIN_LEGKEY) ? "Build " KEYDB_NAME :
(filetype & BIN_NCCHNFO)? "NCCHinfo options..." : (filetype & BIN_NCCHNFO)? "NCCHinfo options..." :
(filetype & TXT_SCRIPT) ? "Execute GM9 script" : (filetype & TXT_SCRIPT) ? "Execute GM9 script" :
(filetype & FONT_PBM) ? "Font options..." : (filetype & FONT_RIFF) ? "Font options..." :
(filetype & GFX_PNG) ? "View PNG file" : (filetype & GFX_PNG) ? "View PNG file" :
(filetype & HDR_NAND) ? "Rebuild NCSD header" : (filetype & HDR_NAND) ? "Rebuild NCSD header" :
(filetype & NOIMG_NAND) ? "Rebuild NCSD header" : "???"; (filetype & NOIMG_NAND) ? "Rebuild NCSD header" : "???";
@ -1288,7 +1289,7 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
return 0; return 0;
} }
else if (user_select == inject) { // -> inject data from clipboard else if (user_select == inject) { // -> inject data from clipboard
char origstr[18 + 1]; char origstr[18 * 4 + 1];
TruncateString(origstr, clipboard->entry[0].name, 18, 10); TruncateString(origstr, clipboard->entry[0].name, 18, 10);
u64 offset = ShowHexPrompt(0, 8, "Inject data from %s?\nSpecify offset below.", origstr); u64 offset = ShowHexPrompt(0, 8, "Inject data from %s?\nSpecify offset below.", origstr);
if (offset != (u64) -1) { if (offset != (u64) -1) {
@ -1466,7 +1467,7 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
if (!(filetype & BIN_KEYDB) && (CryptGameFile(path, inplace, false) == 0)) n_success++; if (!(filetype & BIN_KEYDB) && (CryptGameFile(path, inplace, false) == 0)) n_success++;
else if ((filetype & BIN_KEYDB) && (CryptAesKeyDb(path, inplace, false) == 0)) n_success++; else if ((filetype & BIN_KEYDB) && (CryptAesKeyDb(path, inplace, false) == 0)) n_success++;
else { // on failure: show error, continue else { // on failure: show error, continue
char lpathstr[32+1]; char lpathstr[32 * 4 + 1];
TruncateString(lpathstr, path, 32, 8); TruncateString(lpathstr, path, 32, 8);
if (ShowPrompt(true, "%s\nDecryption failed\n \nContinue?", lpathstr)) continue; if (ShowPrompt(true, "%s\nDecryption failed\n \nContinue?", lpathstr)) continue;
else break; else break;
@ -1515,7 +1516,7 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
if (!(filetype & BIN_KEYDB) && (CryptGameFile(path, inplace, true) == 0)) n_success++; if (!(filetype & BIN_KEYDB) && (CryptGameFile(path, inplace, true) == 0)) n_success++;
else if ((filetype & BIN_KEYDB) && (CryptAesKeyDb(path, inplace, true) == 0)) n_success++; else if ((filetype & BIN_KEYDB) && (CryptAesKeyDb(path, inplace, true) == 0)) n_success++;
else { // on failure: show error, continue else { // on failure: show error, continue
char lpathstr[32+1]; char lpathstr[32 * 4 + 1];
TruncateString(lpathstr, path, 32, 8); TruncateString(lpathstr, path, 32, 8);
if (ShowPrompt(true, "%s\nEncryption failed\n \nContinue?", lpathstr)) continue; if (ShowPrompt(true, "%s\nEncryption failed\n \nContinue?", lpathstr)) continue;
else break; else break;
@ -1553,7 +1554,7 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
if (((user_select != cxi_dump) && (BuildCiaFromGameFile(path, force_legit) == 0)) || if (((user_select != cxi_dump) && (BuildCiaFromGameFile(path, force_legit) == 0)) ||
((user_select == cxi_dump) && (DumpCxiSrlFromGameFile(path) == 0))) n_success++; ((user_select == cxi_dump) && (DumpCxiSrlFromGameFile(path) == 0))) n_success++;
else { // on failure: show error, continue else { // on failure: show error, continue
char lpathstr[32+1]; char lpathstr[32 * 4 + 1];
TruncateString(lpathstr, path, 32, 8); TruncateString(lpathstr, path, 32, 8);
if (ShowPrompt(true, "%s\nBuild %s failed\n \nContinue?", lpathstr, type)) continue; if (ShowPrompt(true, "%s\nBuild %s failed\n \nContinue?", lpathstr, type)) continue;
else break; else break;
@ -1613,7 +1614,7 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
(install_tik && (InstallTicketFile(path, to_emunand) == 0))) (install_tik && (InstallTicketFile(path, to_emunand) == 0)))
n_success++; n_success++;
else { // on failure: show error, continue else { // on failure: show error, continue
char lpathstr[32+1]; char lpathstr[32 * 4 + 1];
TruncateString(lpathstr, path, 32, 8); TruncateString(lpathstr, path, 32, 8);
if (ShowPrompt(true, "%s\nInstall failed\n \nContinue?", lpathstr)) continue; if (ShowPrompt(true, "%s\nInstall failed\n \nContinue?", lpathstr)) continue;
else break; else break;
@ -1693,7 +1694,7 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
if ((filetype & IMG_NAND) && (ValidateNandDump(path) == 0)) n_success++; if ((filetype & IMG_NAND) && (ValidateNandDump(path) == 0)) n_success++;
else if (VerifyGameFile(path) == 0) n_success++; else if (VerifyGameFile(path) == 0) n_success++;
else { // on failure: show error, continue else { // on failure: show error, continue
char lpathstr[32+1]; char lpathstr[32 * 4 + 1];
TruncateString(lpathstr, path, 32, 8); TruncateString(lpathstr, path, 32, 8);
if (ShowPrompt(true, "%s\nVerification failed\n \nContinue?", lpathstr)) { if (ShowPrompt(true, "%s\nVerification failed\n \nContinue?", lpathstr)) {
if (!(filetype & (GAME_CIA|GAME_TMD|GAME_NCSD|GAME_NCCH))) if (!(filetype & (GAME_CIA|GAME_TMD|GAME_NCSD|GAME_NCCH)))
@ -1828,7 +1829,7 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
n_success++; n_success++;
savings += prevsize - FileGetSize(path); savings += prevsize - FileGetSize(path);
} else { // on failure: show error, continue (should not happen) } else { // on failure: show error, continue (should not happen)
char lpathstr[32+1]; char lpathstr[32 * 4 + 1];
TruncateString(lpathstr, path, 32, 8); TruncateString(lpathstr, path, 32, 8);
if (ShowPrompt(true, "%s\nTrimming failed\n \nContinue?", lpathstr)) { if (ShowPrompt(true, "%s\nTrimming failed\n \nContinue?", lpathstr)) {
ShowProgress(0, n_marked, path); // restart progress bar ShowProgress(0, n_marked, path); // restart progress bar
@ -2039,12 +2040,12 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
return 0; return 0;
} }
else if (user_select == font) { // set font else if (user_select == font) { // set font
u8* pbm = (u8*) malloc(0x10000); // arbitrary, should be enough by far u8* riff = (u8*) malloc(0x10000); // arbitrary, should be enough by far
if (!pbm) return 1; if (!riff) return 1;
u32 pbm_size = FileGetData(file_path, pbm, 0x10000, 0); u32 riff_size = FileGetData(file_path, riff, 0x10000, 0);
if (pbm_size) SetFontFromPbm(pbm, pbm_size); if (riff_size) SetFontFromRiff(riff, riff_size);
ClearScreenF(true, true, COLOR_STD_BG); ClearScreenF(true, true, COLOR_STD_BG);
free(pbm); free(riff);
return 0; return 0;
} }
else if (user_select == view) { // view gfx else if (user_select == view) { // view gfx
@ -2069,8 +2070,8 @@ u32 FileHandlerMenu(char* current_path, u32* cursor, u32* scroll, PaneData** pan
return 0; return 0;
} }
else if (user_select == setup) { // set as default (font) else if (user_select == setup) { // set as default (font)
if (filetype & FONT_PBM) { if (filetype & FONT_RIFF) {
if (SetAsSupportFile("font.pbm", file_path)) if (SetAsSupportFile("font.riff", file_path))
ShowPrompt(false, "%s\nFont will be active on next boot", pathstr); ShowPrompt(false, "%s\nFont will be active on next boot", pathstr);
} }
return 0; return 0;
@ -2280,7 +2281,7 @@ u32 GodMode(int entrypoint) {
#endif #endif
// init font // init font
if (!SetFontFromPbm(NULL, 0)) return exit_mode; if (!SetFontFromRiff(NULL, 0)) return exit_mode;
// show splash screen (if enabled) // show splash screen (if enabled)
ClearScreenF(true, true, COLOR_STD_BG); ClearScreenF(true, true, COLOR_STD_BG);
@ -2300,12 +2301,12 @@ u32 GodMode(int entrypoint) {
SetScreenBrightness(brightness); SetScreenBrightness(brightness);
// custom font handling // custom font handling
if (CheckSupportFile("font.pbm")) { if (CheckSupportFile("font.riff")) {
u8* pbm = (u8*) malloc(0x10000); // arbitrary, should be enough by far u8* riff = (u8*) malloc(0x10000); // arbitrary, should be enough by far
if (pbm) { if (riff) {
u32 pbm_size = LoadSupportFile("font.pbm", pbm, 0x10000); u32 riff_size = LoadSupportFile("font.riff", riff, 0x10000);
if (pbm_size) SetFontFromPbm(pbm, pbm_size); if (riff_size) SetFontFromRiff(riff, riff_size);
free(pbm); free(riff);
} }
} }
@ -2458,7 +2459,7 @@ u32 GodMode(int entrypoint) {
if (fixcmac > 0) optionstr[fixcmac-1] = "Fix CMACs for drive"; if (fixcmac > 0) optionstr[fixcmac-1] = "Fix CMACs for drive";
if (dirnfo > 0) optionstr[dirnfo-1] = (*current_path) ? "Show directory info" : "Show drive info"; if (dirnfo > 0) optionstr[dirnfo-1] = (*current_path) ? "Show directory info" : "Show drive info";
if (stdcpy > 0) optionstr[stdcpy-1] = "Copy to " OUTPUT_PATH; if (stdcpy > 0) optionstr[stdcpy-1] = "Copy to " OUTPUT_PATH;
char namestr[32+1]; char namestr[32 * 4 + 1];
TruncateString(namestr, (*current_path) ? curr_entry->path : curr_entry->name, 32, 8); TruncateString(namestr, (*current_path) ? curr_entry->path : curr_entry->name, 32, 8);
int user_select = ShowSelectPrompt(n_opt, optionstr, "%s", namestr); int user_select = ShowSelectPrompt(n_opt, optionstr, "%s", namestr);
if (user_select == tman) { if (user_select == tman) {
@ -2497,7 +2498,7 @@ u32 GodMode(int entrypoint) {
u32 user_select = 1; u32 user_select = 1;
if (curr_drvtype & DRV_SEARCH) { // special menu for search drive if (curr_drvtype & DRV_SEARCH) { // special menu for search drive
static const char* optionstr[2] = { "Open this folder", "Open containing folder" }; static const char* optionstr[2] = { "Open this folder", "Open containing folder" };
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, curr_entry->path, 32, 8); TruncateString(pathstr, curr_entry->path, 32, 8);
user_select = ShowSelectPrompt(2, optionstr, "%s", pathstr); user_select = ShowSelectPrompt(2, optionstr, "%s", pathstr);
} }
@ -2628,7 +2629,7 @@ u32 GodMode(int entrypoint) {
if (n_errors) ShowPrompt(false, "Failed deleting %u/%u path(s)", n_errors, n_marked); if (n_errors) ShowPrompt(false, "Failed deleting %u/%u path(s)", n_errors, n_marked);
} }
} else if (curr_entry->type != T_DOTDOT) { } else if (curr_entry->type != T_DOTDOT) {
char namestr[36+1]; char namestr[36 * 4 + 1];
TruncateString(namestr, curr_entry->name, 28, 12); TruncateString(namestr, curr_entry->name, 28, 12);
if (ShowPrompt(true, "Delete \"%s\"?", namestr)) { if (ShowPrompt(true, "Delete \"%s\"?", namestr)) {
ShowString("Deleting files, please wait..."); ShowString("Deleting files, please wait...");
@ -2666,7 +2667,7 @@ u32 GodMode(int entrypoint) {
u32 flags = 0; u32 flags = 0;
u32 user_select; u32 user_select;
if (clipboard->n_entries == 1) { if (clipboard->n_entries == 1) {
char namestr[20+1]; char namestr[20 * 4 + 1];
TruncateString(namestr, clipboard->entry[0].name, 20, 12); TruncateString(namestr, clipboard->entry[0].name, 20, 12);
snprintf(promptstr, 64, "Paste \"%s\" here?", namestr); snprintf(promptstr, 64, "Paste \"%s\" here?", namestr);
} else snprintf(promptstr, 64, "Paste %lu paths here?", clipboard->n_entries); } else snprintf(promptstr, 64, "Paste %lu paths here?", clipboard->n_entries);
@ -2674,7 +2675,7 @@ u32 GodMode(int entrypoint) {
ShowSelectPrompt(2, optionstr, "%s", promptstr) : (ShowPrompt(true, "%s", promptstr) ? 1 : 0); ShowSelectPrompt(2, optionstr, "%s", promptstr) : (ShowPrompt(true, "%s", promptstr) ? 1 : 0);
if (user_select) { if (user_select) {
for (u32 c = 0; c < clipboard->n_entries; c++) { for (u32 c = 0; c < clipboard->n_entries; c++) {
char namestr[36+1]; char namestr[36 * 4 + 1];
TruncateString(namestr, clipboard->entry[c].name, 36, 12); TruncateString(namestr, clipboard->entry[c].name, 36, 12);
flags &= ~ASK_ALL; flags &= ~ASK_ALL;
if (c < clipboard->n_entries - 1) flags |= ASK_ALL; if (c < clipboard->n_entries - 1) flags |= ASK_ALL;
@ -2700,7 +2701,7 @@ u32 GodMode(int entrypoint) {
ShowPrompt(false, "Not allowed in alias path"); ShowPrompt(false, "Not allowed in alias path");
} else if ((pad_state & BUTTON_X) && (curr_entry->type != T_DOTDOT)) { // rename a file } else if ((pad_state & BUTTON_X) && (curr_entry->type != T_DOTDOT)) { // rename a file
char newname[256]; char newname[256];
char namestr[20+1]; char namestr[20 * 4 + 1];
TruncateString(namestr, curr_entry->name, 20, 12); TruncateString(namestr, curr_entry->name, 20, 12);
snprintf(newname, 255, "%s", curr_entry->name); snprintf(newname, 255, "%s", curr_entry->name);
if (ShowKeyboardOrPrompt(newname, 256, "Rename %s?\nEnter new name below.", namestr)) { if (ShowKeyboardOrPrompt(newname, 256, "Rename %s?\nEnter new name below.", namestr)) {
@ -2724,7 +2725,7 @@ u32 GodMode(int entrypoint) {
((type != 2) || ((fsize = ShowNumberPrompt(0, "Create a new %s here?\nEnter file size below.", typestr)) != (u64) -1))) { ((type != 2) || ((fsize = ShowNumberPrompt(0, "Create a new %s here?\nEnter file size below.", typestr)) != (u64) -1))) {
if (((type == 1) && !DirCreate(current_path, ename)) || if (((type == 1) && !DirCreate(current_path, ename)) ||
((type == 2) && !FileCreateDummy(current_path, ename, fsize))) { ((type == 2) && !FileCreateDummy(current_path, ename, fsize))) {
char namestr[36+1]; char namestr[36 * 4 + 1];
TruncateString(namestr, ename, 36, 12); TruncateString(namestr, ename, 36, 12);
ShowPrompt(false, "Failed creating %s:\n%s", typestr, namestr); ShowPrompt(false, "Failed creating %s:\n%s", typestr, namestr);
} else { } else {

View File

@ -527,7 +527,7 @@ u32 VerifyNcchFile(const char* path, u32 offset, u32 size) {
ExeFsHeader exefs; ExeFsHeader exefs;
FIL file; FIL file;
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
// open file, get NCCH, ExeFS header // open file, get NCCH, ExeFS header
@ -727,7 +727,7 @@ u32 VerifyNcsdFile(const char* path) {
NcsdHeader ncsd; NcsdHeader ncsd;
// path string // path string
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
// load NCSD header // load NCSD header
@ -760,7 +760,7 @@ u32 VerifyCiaFile(const char* path) {
if (!cia) return 1; if (!cia) return 1;
// path string // path string
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
// load CIA stub // load CIA stub
@ -805,7 +805,7 @@ u32 VerifyTmdFile(const char* path, bool cdn) {
bool ignore_missing_dlc = false; bool ignore_missing_dlc = false;
// path string // path string
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
// content path string // content path string
@ -905,7 +905,7 @@ u32 VerifyTadFile(const char* path) {
} }
u32 VerifyFirmFile(const char* path) { u32 VerifyFirmFile(const char* path) {
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
void* firm_buffer = (void*) malloc(FIRM_MAX_SIZE); void* firm_buffer = (void*) malloc(FIRM_MAX_SIZE);
@ -953,7 +953,7 @@ u32 VerifyBossFile(const char* path) {
FIL file; FIL file;
UINT btr; UINT btr;
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
// read file header // read file header
@ -2897,7 +2897,7 @@ u32 InstallTicketFile(const char* path, bool to_emunand) {
return 1; return 1;
// path string // path string
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
// check ticket db // check ticket db
@ -3389,7 +3389,7 @@ u32 ShowGameCheckerInfo(const char* path) {
if (!tmd) return 1; if (!tmd) return 1;
// path string // path string
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
// CIA / TIE specific stuff // CIA / TIE specific stuff

View File

@ -456,7 +456,7 @@ u32 RecursiveFixFileCmacWorker(char* path) {
u32 err = 0; u32 err = 0;
if (fvx_opendir(&pdir, path) == FR_OK) { // process folder contents if (fvx_opendir(&pdir, path) == FR_OK) { // process folder contents
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
char* fname = path + strnlen(path, 255); char* fname = path + strnlen(path, 255);
*(fname++) = '/'; *(fname++) = '/';

View File

@ -318,7 +318,7 @@ u32 ValidateNandDump(const char* path) {
FIL file; FIL file;
// truncated path string // truncated path string
char pathstr[32 + 1]; char pathstr[32 * 4 + 1];
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
// open file // open file
@ -500,7 +500,7 @@ u32 SafeRestoreNandDump(const char* path) {
} }
u32 SafeInstallFirmBuffered(const char* path, u32 slots, u8* buffer, u32 bufsiz) { u32 SafeInstallFirmBuffered(const char* path, u32 slots, u8* buffer, u32 bufsiz) {
char pathstr[32 + 1]; // truncated path string char pathstr[32 * 4 + 1]; // truncated path string
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
// load / check FIRM // load / check FIRM
@ -610,7 +610,7 @@ u32 SafeInstallKeyDb(const char* path) {
static const u8 perfect_sha[] = { KEYDB_PERFECT_HASH }; static const u8 perfect_sha[] = { KEYDB_PERFECT_HASH };
u8 keydb[KEYDB_PERFECT_SIZE] __attribute__((aligned(4))); u8 keydb[KEYDB_PERFECT_SIZE] __attribute__((aligned(4)));
char pathstr[32 + 1]; // truncated path string char pathstr[32 * 4 + 1]; // truncated path string
TruncateString(pathstr, path, 32, 8); TruncateString(pathstr, path, 32, 8);
// already installed? // already installed?

View File

@ -24,7 +24,7 @@
#define _VAR_CNT_LEN 256 #define _VAR_CNT_LEN 256
#define _VAR_NAME_LEN 32 #define _VAR_NAME_LEN 32
#define _VAR_MAX_BUFF 256 #define _VAR_MAX_BUFF 256
#define _ERR_STR_LEN 32 #define _ERR_STR_LEN 256
#define _CHOICE_STR_LEN 32 #define _CHOICE_STR_LEN 32
#define _CHOICE_MAX_N 12 #define _CHOICE_MAX_N 12
@ -1624,7 +1624,7 @@ void MemTextView(const char* text, u32 len, char* line0, int off_disp, int lno,
if (ar) memcpy(txtstr + p_ar, ar_str, strnlen(ar_str, 16)); if (ar) memcpy(txtstr + p_ar, ar_str, strnlen(ar_str, 16));
// draw line number & text // draw line number & text
DrawString(TOP_SCREEN, txtstr, x_txt, y, color_text, COLOR_STD_BG, false); DrawString(TOP_SCREEN, txtstr, x_txt, y, color_text, COLOR_STD_BG);
if (TV_LNOS > 0) { // line number if (TV_LNOS > 0) { // line number
if (ptr != ptr_next) if (ptr != ptr_next)
DrawStringF(TOP_SCREEN, x_lno, y, ((ptr == text) || (*(ptr-1) == '\n')) ? COLOR_TVOFFS : COLOR_TVOFFSL, COLOR_STD_BG, "%0*lu", TV_LNOS, nln); DrawStringF(TOP_SCREEN, x_lno, y, ((ptr == text) || (*(ptr-1) == '\n')) ? COLOR_TVOFFS : COLOR_TVOFFSL, COLOR_STD_BG, "%0*lu", TV_LNOS, nln);
@ -1634,7 +1634,7 @@ void MemTextView(const char* text, u32 len, char* line0, int off_disp, int lno,
// colorize comment if is_script // colorize comment if is_script
if ((cmt_start > 0) && ((u32) cmt_start < TV_LLEN_DISP)) { if ((cmt_start > 0) && ((u32) cmt_start < TV_LLEN_DISP)) {
memset(txtstr, ' ', cmt_start); memset(txtstr, ' ', cmt_start);
DrawString(TOP_SCREEN, txtstr, x_txt, y, script_color_comment, COLOR_TRANSPARENT, false); DrawString(TOP_SCREEN, txtstr, x_txt, y, script_color_comment, COLOR_TRANSPARENT);
} }
// colorize arrows // colorize arrows
@ -1660,7 +1660,7 @@ bool MemTextViewer(const char* text, u32 len, u32 start, bool as_script) {
ClearScreenF(true, true, COLOR_STD_BG); ClearScreenF(true, true, COLOR_STD_BG);
// instructions // instructions
static const char* instr = "Textviewer Controls:\n \n\x18\x19\x1A\x1B(+R) - Scroll\nR+Y - Toggle wordwrap\nR+X - Goto line #\nB - Exit\n"; static const char* instr = "Textviewer Controls:\n \n↑↓→←(+R) - Scroll\nR+Y - Toggle wordwrap\nR+X - Goto line #\nB - Exit\n";
ShowString(instr); ShowString(instr);
// set script colors // set script colors
@ -1824,7 +1824,7 @@ bool FileTextViewer(const char* path, bool as_script) {
} }
bool ExecuteGM9Script(const char* path_script) { bool ExecuteGM9Script(const char* path_script) {
char path_str[32+1]; char path_str[32 * 4 + 1];
TruncateString(path_str, path_script, 32, 12); TruncateString(path_str, path_script, 32, 12);