Add some file saving/loading

This commit is contained in:
Přemysl Eric Janouch 2014-10-27 18:03:16 +01:00
parent 28a93ad693
commit 5cebe379c8
1 changed files with 100 additions and 13 deletions

View File

@ -518,6 +518,8 @@ end:
*h = my_h - my_y;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
static const char *
color_to_ansi (uint8_t color)
{
@ -555,6 +557,7 @@ export_ansi (app_context_t *app)
if (!fp)
{
display ("Error opening file for writing.");
beep ();
return;
}
@ -582,6 +585,8 @@ export_ansi (app_context_t *app)
fclose (fp);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
enum
{
MIRC_NONE = -1,
@ -631,6 +636,7 @@ export_irc (app_context_t *app)
if (!fp)
{
display ("Error opening file for writing.");
beep ();
return;
}
@ -655,6 +661,93 @@ export_irc (app_context_t *app)
fclose (fp);
}
// --- Loading, saving ---------------------------------------------------------
static void
load (app_context_t *app)
{
FILE *fp = fopen ("drawing.bin", "rb");
if (!fp)
{
display ("Error opening file for reading.");
beep ();
return;
}
// Client cannot load at all, the server would have send the new bitmap out
if (app->mode != NETWORK_MODE_STANDALONE)
{
display ("Cannot load bitmaps in networked mode.");
beep ();
return;
}
// Some way of loading/saving is better than no way, let's just do our job.
// The format neither standardised nor effective but it works for us.
// We just eat everything and make sure to not crash.
int x, y;
size_t w, h;
if (fscanf (fp, "%d %d %zu %zu", &x, &y, &w, &h) != 4)
goto error;
size_t size = w * h;
uint8_t *bitmap = calloc (size, sizeof *bitmap);
if (!bitmap)
goto error;
char c;
uint8_t pixel = 0;
bool have_nibble = false;
size_t loaded = 0;
while (loaded < size && (c = fgetc (fp)) != EOF)
{
static const char digits[] = "0123456789abcdef";
const char *value = strchr (digits, c);
if (value && c != '\0')
{
pixel = pixel << 4 | (value - digits);
if (have_nibble)
bitmap[loaded++] = pixel;
have_nibble = !have_nibble;
}
}
free (app->bitmap);
app->bitmap = bitmap;
app->bitmap_h = h; app->bitmap_x = x;
app->bitmap_w = w; app->bitmap_y = y;
redraw_canvas (app);
error:
fclose (fp);
}
static void
save (app_context_t *app)
{
FILE *fp = fopen ("drawing.bin", "wb");
if (!fp)
{
display ("Error opening file for writing.");
return;
}
int x = app->bitmap_x, y = app->bitmap_y;
size_t w = app->bitmap_w, h = app->bitmap_h;
fprintf (fp, "%d %d %zu %zu\n", x, y, w, h);
for (size_t row = 0; row < h; row++)
{
for (size_t column = 0; column < w; column++)
fprintf (fp, "%02x", BITMAP_PIXEL (app, column, row));
fputc ('\n', fp);
}
fclose (fp);
}
// --- Event handlers ----------------------------------------------------------
static void
@ -730,19 +823,11 @@ on_key (app_context_t *app, termo_key_t *key)
switch (key->code.sym)
{
case TERMO_SYM_UP:
move_canvas (app, 0, -1);
break;
case TERMO_SYM_DOWN:
move_canvas (app, 0, 1);
break;
case TERMO_SYM_LEFT:
move_canvas (app, -1, 0);
break;
case TERMO_SYM_RIGHT:
move_canvas (app, 1, 0);
default:
break;
case TERMO_SYM_UP: move_canvas (app, 0, -1); break;
case TERMO_SYM_DOWN: move_canvas (app, 0, 1); break;
case TERMO_SYM_LEFT: move_canvas (app, -1, 0); break;
case TERMO_SYM_RIGHT: move_canvas (app, 1, 0); break;
default: break;
}
return true;
}
@ -756,6 +841,8 @@ on_key (app_context_t *app, termo_key_t *key)
if (key->modifiers)
return true;
if (key->code.codepoint == 'l') load (app);
if (key->code.codepoint == 's') save (app);
if (key->code.codepoint == 'e') export_ansi (app);
if (key->code.codepoint == 'E') export_irc (app);
return true;