1010
Check-in [dc570350e4]
Not logged in
Public Repositories
mwm's Repositories

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Generalize the help system before rewriting it.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1:dc570350e403379e1d66645e5caa056b2cf2c175
User & Date: mwm 2016-11-06 15:24:56
Context
2016-11-07
11:47
Finish up the help system. check-in: a0ca976006 user: mwm tags: trunk
2016-11-06
15:24
Generalize the help system before rewriting it. check-in: dc570350e4 user: mwm tags: trunk
11:31
Update some comments. check-in: f3ecf097c2 user: mwm tags: trunk
Changes
Hide Diffs Unified Diffs Ignore Whitespace Patch

Changes to Tiny-1010.ino.

124
125
126
127
128
129
130
131






132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148



149
150
151
152
153
154
155
...
246
247
248
249
250
251
252

253
254
255
256
257
258
259
...
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
...
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
...
378
379
380
381
382
383
384
385
386
387
388


389
390
391
392












393
394
395
396
397
398
399
...
431
432
433
434
435
436
437

438
439
440
441

442
443
444
445
446
447
448



449
450
451
452
453
454
455
456
457
458
459

460
461
462
463
464
465
466
...
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524









525
526
527
528
529
530
531
532
533
534
535
536
     {2, 3, sixes[7]},
     {2, 2, fours[3]},	// small 2x2 corners
     {2, 2, fours[4]},
     {2, 2, fours[5]},
     {2, 2, fours[6]},
};








// The game
typedef enum {PAUSED, DONE, SELECTING, MOVING} game_state;
const byte WAIT_LEN = 3;

struct game_data {
     unsigned long high, score;
     byte delay;
     int8_t waiting[WAIT_LEN];	// Shapes ready to be played.
     byte x, y;	// And it's location on the board.
     byte board[BOARD_SIZE][BOARD_SIZE];
} game;

// Ephemeral values.
game_state state;	// Current game state
byte selected;	        // substate indicator





// The menu
enum {HELP, RESUME, NEW};
const char *const
menu[] = {" Help ",
          "Resume",
          " New  ",
          NULL};
................................................................................
     for (byte w = 0; w < WAIT_LEN; w += 1)
          if (game.waiting[w] >= 0 && find_clear(&shapes[game.waiting[w]])) {
               state = SELECTING;
               return;
          }
     state = DONE;
     selected = NEW;

}


void
reset_game(void) {
     game.delay = 100;
     game.score = 0;
................................................................................

     new_shapes();
     state = SELECTING;
}

void
do_menu(void) {
     void draw_page_msg(const char *const, boolean clear = true);

     switch (selected) {
     case NEW:
          reset_game();
          // Fall through to
     case RESUME:
          state = SELECTING;
          select_next();
          break;
     case HELP:
          draw_page_msg("   Selecting\n"
                        "\30\31: Change shape\n"
                        "\32: Use shape\nA: Fit & use shape\nB: Pause",
                        true);
          draw_page_msg("    Moving Shape\n\30\31\33\32: Move shape\n"
                        "\33: Deselect shape\nA: Place shape\nB: Pause",
                        true);
          selected = RESUME;
          break;
     }
}

/* Code to draw things on the display */
// Coloring in things that aren't on the board.
void
................................................................................
void
draw_msg(const char *const msg, byte top = 18) {
     arduboy.setCursor(0, top);
     arduboy.print(msg);
}

void
draw_page_msg(const char *const msg, boolean clear = false) {
     if (clear)
          arduboy.clear();
    
     draw_msg(msg, 0);
     arduboy.print("\n\nPress A");
     arduboy.display();

     // use pollButtons since we do what the button asks.
     do arduboy.pollButtons();
     while (!arduboy.justPressed(A_BUTTON));
}

void
draw_menu(const char *const title) {
     draw_msg(title);
     arduboy.print("\n\n\33 ");
     arduboy.print(menu[selected]);
     arduboy.print(" \32");
}

byte
draw_game(void) {
................................................................................
     draw_board();
     arduboy.print("Score\n");
     arduboy.print(game.score);
     arduboy.setCursor(0, 44); 
     arduboy.print("High\n");
     arduboy.print(game.high);


     switch (state) {
     case DONE:
          blue = RGB_ON;


          draw_menu("Game over!");
          break;
     case PAUSED:
          draw_menu("Paused");












          break;
     default:
          for (byte i = 0; i < WAIT_LEN; i += 1) {
               arduboy.setCursor(BLOCK_SIZE, (i + 3) * BLOCK_SIZE);
               arduboy.write(i == selected ? '+' : game.waiting[i] < 0 ? ' ' : '-');
          }
          color_shape(s, 32 - s->width * BLOCK_SIZE / 2,
................................................................................
          EEPROM.put(saved_game, game);
          EEPROM.write(store, flagbyte);
          EEPROM.write(store + 1, flagbyte);
     } else {
          EEPROM.get(saved_game, game);
          state = DONE;
          selected = NEW;

          for (byte i = 0; i < WAIT_LEN; i += 1) {
               if (game.waiting[i] >= 0) {
                    state = PAUSED;
                    selected = RESUME;

                    break;
               }
          }
     }

     draw_board();
     draw_page_msg("\n\n1010 v1.0\n by mwm", false);



     arduboy.initRandomSeed();
}

void
loop(void) {
     const shape *const s = &shapes[game.waiting[selected]];
     const byte can_place = draw_game();

     arduboy.pollButtons();
     if (arduboy.justPressed(B_BUTTON)) {
          state = PAUSED;

          selected = RESUME;
          return;
     }

     switch (state) {
     case SELECTING:
          if (arduboy.justPressed(UP_BUTTON))
................................................................................
               game.waiting[i] = -1;
          if (arduboy.justPressed(A_BUTTON))
               do_menu();
          else if (arduboy.justPressed(LEFT_BUTTON)
                   || arduboy.justPressed(RIGHT_BUTTON))
               selected = selected == NEW ? HELP : NEW;
          break;
     case PAUSED:
          if (arduboy.justPressed(A_BUTTON)) {
               do_menu();
          } else if (arduboy.justPressed(LEFT_BUTTON)) {
               if (selected)
                    selected -= 1;
               else
                    selected = sizeof(menu) / sizeof(char *) - 2;
          } else if (arduboy.justPressed(RIGHT_BUTTON)) {
               selected = (selected + 1) % (sizeof(menu) / sizeof(char *) - 1);
          }
          break;









     }

     EEPROM.put(saved_game, game);
     if (state == MOVING) {
          unsigned long end = millis() + game.delay;
          // Used pressed as the button just exists the loop.
          while (millis() < end)
               if (arduboy.pressed(A_BUTTON) || arduboy.pressed(B_BUTTON))
                    break;
     }
}









>
>
>
>
>
>

|











|
|

<
>
>
>







 







>







 







<
<









|
<
<
<
<
<
<
|







 







<
<
<
<
<
<
<
<
<
<
<
<
<
|
<
|







 







<



>
>
|

|
<
>
>
>
>
>
>
>
>
>
>
>
>







 







>


|

>






|
>
>
>










|
>







 







|











>
>
>
>
>
>
>
>
>











<
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153

154
155
156
157
158
159
160
161
162
163
...
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
...
272
273
274
275
276
277
278


279
280
281
282
283
284
285
286
287
288






289
290
291
292
293
294
295
296
...
343
344
345
346
347
348
349













350

351
352
353
354
355
356
357
358
...
365
366
367
368
369
370
371

372
373
374
375
376
377
378
379

380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
...
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
...
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549

     {2, 3, sixes[7]},
     {2, 2, fours[3]},	// small 2x2 corners
     {2, 2, fours[4]},
     {2, 2, fours[5]},
     {2, 2, fours[6]},
};


const char *help[] = {
     "   Selecting\n\30\31: Change shape\n\32: Use shape\nA: Fit & use shape\nB: Pause",
     "  Moving Shape\n\30\31\33\32: Move shape\n\33: Deselect shape\nA: Place shape\nB: Pause",
     NULL
};

// The game
typedef enum {MENU, DONE, SELECTING, MOVING, PAGING} game_state;
const byte WAIT_LEN = 3;

struct game_data {
     unsigned long high, score;
     byte delay;
     int8_t waiting[WAIT_LEN];	// Shapes ready to be played.
     byte x, y;	// And it's location on the board.
     byte board[BOARD_SIZE][BOARD_SIZE];
} game;

// Ephemeral values.
game_state state;		// Current game state
byte selected;	        	// substate indicator


const char *prompt;		// Menu prompt
#define PAUSED		"  Paused"
#define GAMEOVER 	"Game over!";
// The menu
enum {HELP, RESUME, NEW};
const char *const
menu[] = {" Help ",
          "Resume",
          " New  ",
          NULL};
................................................................................
     for (byte w = 0; w < WAIT_LEN; w += 1)
          if (game.waiting[w] >= 0 && find_clear(&shapes[game.waiting[w]])) {
               state = SELECTING;
               return;
          }
     state = DONE;
     selected = NEW;
     prompt = GAMEOVER;
}


void
reset_game(void) {
     game.delay = 100;
     game.score = 0;
................................................................................

     new_shapes();
     state = SELECTING;
}

void
do_menu(void) {


     switch (selected) {
     case NEW:
          reset_game();
          // Fall through to
     case RESUME:
          state = SELECTING;
          select_next();
          break;
     case HELP:
          state = PAGING;






          selected = 0;
          break;
     }
}

/* Code to draw things on the display */
// Coloring in things that aren't on the board.
void
................................................................................
void
draw_msg(const char *const msg, byte top = 18) {
     arduboy.setCursor(0, top);
     arduboy.print(msg);
}

void













draw_menu(void) {

     draw_msg(prompt);
     arduboy.print("\n\n\33 ");
     arduboy.print(menu[selected]);
     arduboy.print(" \32");
}

byte
draw_game(void) {
................................................................................
     draw_board();
     arduboy.print("Score\n");
     arduboy.print(game.score);
     arduboy.setCursor(0, 44); 
     arduboy.print("High\n");
     arduboy.print(game.high);


     switch (state) {
     case DONE:
          blue = RGB_ON;
          // Fall through
     case MENU:
          draw_menu();
          break;
     case PAGING:

          arduboy.clear();
          draw_msg(help[selected], 0);
          if (selected) {
               arduboy.setCursor(0, 56);
               arduboy.write('\33');
          }
          arduboy.setCursor(62, 56);
          arduboy.write('\30');
          if (help[selected + 1] != NULL) {
               arduboy.setCursor(120, 56);
               arduboy.write('\32');
          }
          break;
     default:
          for (byte i = 0; i < WAIT_LEN; i += 1) {
               arduboy.setCursor(BLOCK_SIZE, (i + 3) * BLOCK_SIZE);
               arduboy.write(i == selected ? '+' : game.waiting[i] < 0 ? ' ' : '-');
          }
          color_shape(s, 32 - s->width * BLOCK_SIZE / 2,
................................................................................
          EEPROM.put(saved_game, game);
          EEPROM.write(store, flagbyte);
          EEPROM.write(store + 1, flagbyte);
     } else {
          EEPROM.get(saved_game, game);
          state = DONE;
          selected = NEW;
          prompt = GAMEOVER;
          for (byte i = 0; i < WAIT_LEN; i += 1) {
               if (game.waiting[i] >= 0) {
                    state = MENU;
                    selected = RESUME;
                    prompt = PAUSED;
                    break;
               }
          }
     }

     draw_board();
     arduboy.print("\n\n1010 v1.0\n by mwm\n\nPress A");
     arduboy.display();
     do arduboy.pollButtons();
     while (!arduboy.justPressed(A_BUTTON));
     arduboy.initRandomSeed();
}

void
loop(void) {
     const shape *const s = &shapes[game.waiting[selected]];
     const byte can_place = draw_game();

     arduboy.pollButtons();
     if (arduboy.justPressed(B_BUTTON)) {
          prompt = PAUSED;
          state = MENU;
          selected = RESUME;
          return;
     }

     switch (state) {
     case SELECTING:
          if (arduboy.justPressed(UP_BUTTON))
................................................................................
               game.waiting[i] = -1;
          if (arduboy.justPressed(A_BUTTON))
               do_menu();
          else if (arduboy.justPressed(LEFT_BUTTON)
                   || arduboy.justPressed(RIGHT_BUTTON))
               selected = selected == NEW ? HELP : NEW;
          break;
     case MENU:
          if (arduboy.justPressed(A_BUTTON)) {
               do_menu();
          } else if (arduboy.justPressed(LEFT_BUTTON)) {
               if (selected)
                    selected -= 1;
               else
                    selected = sizeof(menu) / sizeof(char *) - 2;
          } else if (arduboy.justPressed(RIGHT_BUTTON)) {
               selected = (selected + 1) % (sizeof(menu) / sizeof(char *) - 1);
          }
          break;
     case PAGING:
          if (arduboy.justPressed(LEFT_BUTTON) && selected)
              selected -= 1;
          else if (arduboy.justPressed(RIGHT_BUTTON) & help[selected + 1] != NULL)
               selected += 1;
          else if (arduboy.justPressed(UP_BUTTON)) {
               state = MENU;
               selected = HELP;
          }
     }

     EEPROM.put(saved_game, game);
     if (state == MOVING) {
          unsigned long end = millis() + game.delay;
          // Used pressed as the button just exists the loop.
          while (millis() < end)
               if (arduboy.pressed(A_BUTTON) || arduboy.pressed(B_BUTTON))
                    break;
     }
}