[Tux4kids-commits] r760 - in tuxtype/trunk: . data/images/tux data/sounds src

dbruce-guest at alioth.debian.org dbruce-guest at alioth.debian.org
Tue Oct 14 01:12:38 UTC 2008


Author: dbruce-guest
Date: 2008-10-14 01:12:38 +0000 (Tue, 14 Oct 2008)
New Revision: 760

Added:
   tuxtype/trunk/data/images/tux/win1.png
   tuxtype/trunk/data/sounds/cheer.wav
Modified:
   tuxtype/trunk/ChangeLog
   tuxtype/trunk/ChangeLog~
   tuxtype/trunk/data/images/tux/Makefile.am
   tuxtype/trunk/data/images/tux/Makefile.in
   tuxtype/trunk/data/sounds/Makefile.am
   tuxtype/trunk/data/sounds/Makefile.in
   tuxtype/trunk/src/SDL_extras.c
   tuxtype/trunk/src/alphabet.c
   tuxtype/trunk/src/globals.h
   tuxtype/trunk/src/loaders.c
   tuxtype/trunk/src/main.c
   tuxtype/trunk/src/practice.c
Log:
more improvements to 'practice' activity



Modified: tuxtype/trunk/ChangeLog
===================================================================
--- tuxtype/trunk/ChangeLog	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/ChangeLog	2008-10-14 01:12:38 UTC (rev 760)
@@ -1,3 +1,10 @@
+13 Oct 2008 - svn revision 760
+[ David Bruce <davidstuartbruce at gmail.com> ]
+        - Lots more work on fullscreen mode with Fish Cascade working but a little slow
+        - Practice activity extensively reworked - wrapping of arbitrary length phrases,
+          rearrangement of screen layout, fullscreen mode supported, animated Tux icons,
+          onscreen display of time, chars, words per min, accuracy with gettext support.
+
 22 Aug 2008 - svn revision 668
 [ David Bruce <davidstuartbruce at gmail.com> ]
         - Extensive revision to support fullscreen mode at resolution of OS rather than only 640x480.

Modified: tuxtype/trunk/ChangeLog~
===================================================================
--- tuxtype/trunk/ChangeLog~	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/ChangeLog~	2008-10-14 01:12:38 UTC (rev 760)
@@ -7,6 +7,10 @@
         - Using GNU iconv() instead of Unicode Inc.'s conversion code
         - SDL_extras brought in from tuxmath for DrawButton(), streamlined BlackOutline(), etc.
 
+18 Aug 2008 -svn revision 652
+[ Mobin Mohan <mobinmohan at gmail.com> ]
+	-GUI for editing wordlist Implemented
+
 18 Aug 2008 - svn revision 647
 [ Sreyas Kurumanghat <k.sreyas at gmail.com ]
 	- Added features to practice game. Now pressing the down arrow presents the next phrase for practice and the escape key quits from the game.

Modified: tuxtype/trunk/data/images/tux/Makefile.am
===================================================================
--- tuxtype/trunk/data/images/tux/Makefile.am	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/data/images/tux/Makefile.am	2008-10-14 01:12:38 UTC (rev 760)
@@ -36,4 +36,5 @@
 walk2.png\
 walk3.png\
 win0.png\
+win1.png\
 yipe0.png

Modified: tuxtype/trunk/data/images/tux/Makefile.in
===================================================================
--- tuxtype/trunk/data/images/tux/Makefile.in	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/data/images/tux/Makefile.in	2008-10-14 01:12:38 UTC (rev 760)
@@ -214,6 +214,7 @@
 walk2.png\
 walk3.png\
 win0.png\
+win1.png\
 yipe0.png
 
 all: all-am

Added: tuxtype/trunk/data/images/tux/win1.png
===================================================================
(Binary files differ)


Property changes on: tuxtype/trunk/data/images/tux/win1.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Modified: tuxtype/trunk/data/sounds/Makefile.am
===================================================================
--- tuxtype/trunk/data/sounds/Makefile.am	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/data/sounds/Makefile.am	2008-10-14 01:12:38 UTC (rev 760)
@@ -7,6 +7,7 @@
   alarm.wav \
   bite.wav \
   buzz.wav \
+  cheer.wav \
   click.wav \
   excuseme.wav \
   explosion.wav \

Modified: tuxtype/trunk/data/sounds/Makefile.in
===================================================================
--- tuxtype/trunk/data/sounds/Makefile.in	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/data/sounds/Makefile.in	2008-10-14 01:12:38 UTC (rev 760)
@@ -184,6 +184,7 @@
   alarm.wav \
   bite.wav \
   buzz.wav \
+  cheer.wav \
   click.wav \
   excuseme.wav \
   explosion.wav \

Added: tuxtype/trunk/data/sounds/cheer.wav
===================================================================
(Binary files differ)


Property changes on: tuxtype/trunk/data/sounds/cheer.wav
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Modified: tuxtype/trunk/src/SDL_extras.c
===================================================================
--- tuxtype/trunk/src/SDL_extras.c	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/src/SDL_extras.c	2008-10-14 01:12:38 UTC (rev 760)
@@ -324,6 +324,7 @@
 
 SDLPango_Context *context = NULL;
 
+
 void init_SDLPango_Context()
 {
    if((context =  SDLPango_CreateContext_GivenFontDesc(settings.theme_font_name))==NULL)
@@ -331,6 +332,8 @@
    SDLPango_SetBaseDirection(context, SDLPANGO_DIRECTION_LTR);
    SDLPango_SetDpi(context, 125.0, 125.0);
 }
+
+
 void free_SDLPango_Context()
 {
   if(context != NULL)
@@ -426,10 +429,18 @@
 #else
   if( context != NULL)
   {
-    SDLPango_SetDefaultColor(context, MATRIX_TRANSPARENT_BACK_WHITE_LETTER);
+    /* convert color arg: */
+    SDLPango_Matrix* color_matrix = SDL_Colour_to_SDLPango_Matrix(c);
+
+    if (color_matrix)
+      SDLPango_SetDefaultColor(context, color_matrix);
+    else  /* fall back to just using white if conversion fails: */
+      SDLPango_SetDefaultColor(context, MATRIX_TRANSPARENT_BACK_WHITE_LETTER);
+
     white_letters = SDLPango_CreateSurfaceDraw(context);
   }
-  else {
+  else
+  {
     white_letters = TTF_RenderUTF8_Blended(font, t, *c);
   }
 #endif

Modified: tuxtype/trunk/src/alphabet.c
===================================================================
--- tuxtype/trunk/src/alphabet.c	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/src/alphabet.c	2008-10-14 01:12:38 UTC (rev 760)
@@ -28,17 +28,7 @@
 #include "funcs.h"
 
 
-/* NOTE these are externed in globals.h so not static */
-/* the colors we use throughout the game */
-SDL_Color black;
-SDL_Color gray;
-SDL_Color dark_blue;
-SDL_Color red;
-SDL_Color white;
-SDL_Color yellow;
 
-
-
 /* An individual item in the list of cached unicode characters that are rendered at   */
 /* the start of each game.                                                            */
 typedef struct uni_glyph {

Modified: tuxtype/trunk/src/globals.h
===================================================================
--- tuxtype/trunk/src/globals.h	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/src/globals.h	2008-10-14 01:12:38 UTC (rev 760)
@@ -62,6 +62,7 @@
 
 #endif //  __GLOBALS_H__
 
+/* FIXME get rid of these 'evil' macros */
 #define NEXT_FRAME(SPRITE) if ((SPRITE)->num_frames) (SPRITE)->cur = (((SPRITE)->cur)+1) % (SPRITE)->num_frames;
 #define REWIND(SPRITE) (SPRITE)->cur = 0;
 

Modified: tuxtype/trunk/src/loaders.c
===================================================================
--- tuxtype/trunk/src/loaders.c	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/src/loaders.c	2008-10-14 01:12:38 UTC (rev 760)
@@ -448,8 +448,12 @@
     return;
  
   for (x = 0; x < gfx->num_frames; x++)
-    SDL_FreeSurface(gfx->frame[x]);
-  SDL_FreeSurface(gfx->default_img);
+  {
+    if (gfx->frame[x])
+      SDL_FreeSurface(gfx->frame[x]);
+  }
+  if (gfx->default_img)
+    SDL_FreeSurface(gfx->default_img);
   free(gfx);
 }
 

Modified: tuxtype/trunk/src/main.c
===================================================================
--- tuxtype/trunk/src/main.c	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/src/main.c	2008-10-14 01:12:38 UTC (rev 760)
@@ -21,9 +21,15 @@
 
 SDL_Surface* screen;
 
-
 SDL_Event  event;
 
+/* the colors we use throughout the game */
+SDL_Color black;
+SDL_Color gray;
+SDL_Color dark_blue;
+SDL_Color red;
+SDL_Color white;
+SDL_Color yellow;
 
 
 /********************

Modified: tuxtype/trunk/src/practice.c
===================================================================
--- tuxtype/trunk/src/practice.c	2008-10-09 00:39:42 UTC (rev 759)
+++ tuxtype/trunk/src/practice.c	2008-10-14 01:12:38 UTC (rev 760)
@@ -6,8 +6,8 @@
 copyright            : (C) 2003 by Jesse Andrews
 email                : jdandr2 at uky.edu
 
-Revised extensively: 2007
-David Bruce <dbruce at tampabay.rr.com>
+Revised extensively: 2007 and 2008
+David Bruce <davidstuartbruce at gmail.com>
 Revised extensively: 2008
 Sreyas Kurumanghat <k.sreyas at gmail.com>
 ***************************************************************************/
@@ -27,39 +27,79 @@
 #define MAX_PHRASES 256
 #define MAX_PHRASE_LENGTH 256
 #define MAX_WRAP_LINES 10
+#define TEXT_HEIGHT 28
+#define SPRITE_FRAME_TIME 200
+/* "Local globals" for practice.c */
+static int fontsize = 0;
+static int bigfontsize = 0;
 
-/* "Local globals" for practice.c */
+/* Surfaces for things we want to pre-render: */
 static SDL_Surface* hands = NULL;
 static SDL_Surface* hand_shift[3] = {NULL};
 static SDL_Surface* keyboard = NULL;
 static SDL_Surface* keypress1 = NULL;
 static SDL_Surface* keypress2 = NULL;
 static SDL_Surface* hand[11] = {NULL};
-static TTF_Font* font = NULL;
+static sprite* tux_stand = NULL;
+static sprite* tux_win = NULL;
+static TTF_Font* smallfont = NULL;
 static TTF_Font* bigfont = NULL;
+static SDL_Surface* time_label_srfc = NULL;
+static SDL_Surface* chars_label_srfc = NULL;
+static SDL_Surface* cpm_label_srfc = NULL;
+static SDL_Surface* wpm_label_srfc = NULL;
+static SDL_Surface* errors_label_srfc = NULL;
+static SDL_Surface* accuracy_label_srfc = NULL;
 
+
 static wchar_t phrases[MAX_PHRASES][MAX_PHRASE_LENGTH];
 static Mix_Chunk* wrong = NULL;
+static Mix_Chunk* cheer = NULL;
 
+
+static int phrase_draw_width = 0; /* How wide before text needs wrapping */
+static int num_phrases = 0;
+
+
 /* Locations for blitting  */
-static int phrase_draw_width = 0; /* How wide before text needs wrapping */
+
+/* Three main areas within window: */
+static SDL_Rect left_pane;
+static SDL_Rect top_pane;
+static SDL_Rect bottom_pane;
+
+/* Locations within left pane: */
+static SDL_Rect tux_loc;
+static SDL_Rect time_label;
+static SDL_Rect time_rect;
+static SDL_Rect chars_typed_label;
+static SDL_Rect chars_typed_rect;
+static SDL_Rect cpm_label;
+static SDL_Rect cpm_rect;
+static SDL_Rect wpm_label;
+static SDL_Rect wpm_rect;
+static SDL_Rect errors_label;
+static SDL_Rect errors_rect;
+static SDL_Rect accuracy_label;
+static SDL_Rect accuracy_rect;
+
+/* Locations within top pane: */
 static SDL_Rect phr_text_rect;
 static SDL_Rect user_text_rect;
-static SDL_Rect keytime_rect;
-static SDL_Rect totaltime_rect;
-static SDL_Rect congrats_rect;
+
+/* Locations within bottom pane: */
+static SDL_Rect hand_loc;
 static SDL_Rect nextletter_rect;
-static SDL_Rect mydest;
-static SDL_Rect hand_loc;
-static SDL_Rect letter_loc;
+//static SDL_Rect letter_loc;
 static SDL_Rect keyboard_loc;
 
+
 /*local function prototypes: */
 static int load_phrases(const char* phrase_file);
-static int num_phrases = 0;
 static int find_next_wrap(const wchar_t* wstr, const TTF_Font* font, int width);
 static int get_phrase(const wchar_t* phr);
 static void recalc_positions(void);
+static void calc_font_sizes(void);
 static int practice_load_media(void);
 static void practice_unload_media(void);
 static void print_at(const wchar_t* pphrase, int wrap, int x, int y);
@@ -86,20 +126,26 @@
   */
 
   /* FIXME make variable names more descriptive */
-  Uint32 start = 0, a = 0;
+  Uint32 start = 0, a = 0, tuxtime = 0;
   int quit = 0,
       i = 0,
       cursor = 0,
       wrap_pt = 0,
       prev_wrap = 0,
-      z = 0,
       total = 0,
       state = 0;
+  int correct_chars = 0;
+  int wrong_chars = 0;
+  float accuracy = 0;
   int cur_phrase = 0;
   int keytimes[MAX_PHRASE_LENGTH] = {0};
   int next_line = 0;
-  char keytime_str[20],
-       totaltime_str[20];
+  char time_str[20];
+  char chars_typed_str[20];
+  char cpm_str[20];
+  char wpm_str[20];
+  char errors_str[20];
+  char accuracy_str[20];
   SDL_Surface* tmpsurf = NULL;
 
   /* Load all needed graphics, strings, sounds.... */
@@ -112,7 +158,7 @@
   /* Set up positions for blitting: */
   recalc_positions();
 
-  start = SDL_GetTicks();
+  start = tuxtime = SDL_GetTicks();
 
 
   /* Begin main event loop for "Practice" activity:  -------- */
@@ -127,13 +173,18 @@
        /* reset other variables related to progress within phrase: */
         for (i = 0; i < MAX_PHRASE_LENGTH; i++)
           keytimes[i] = 0;
-        keytime_str[0] = '\0';
-        totaltime_str[0] = '\0';
+        time_str[0] = '\0';
+        chars_typed_str[0] = '\0';
+        cpm_str[0] = '\0';
+        wpm_str[0] = '\0';
+        errors_str[0] = '\0';
+        accuracy_str[0] = '\0';
         total = 0;
         cursor = 0;
         wrap_pt = 0;
         prev_wrap = 0;
-
+        correct_chars = 0;
+        wrong_chars = 0;
         /* No 'break;' so we drop through to do case 1 as well : */
 
       /* state == 1 means complete redraw needed                          */
@@ -144,13 +195,25 @@
         /* Draw bkgd before we start */
         /* NOTE the keyboard and hands will get drawn when we drop through to case 2: */
         SDL_BlitSurface(CurrentBkgd(), NULL, screen, NULL);
-//        SDL_BlitSurface(keyboard, NULL, screen, &keyboard_loc);
-//        SDL_BlitSurface(hands, NULL, screen, &hand_loc);
+        /* Note - the validity of all these surfaces is tested */
+        /* in Practice_Load_Media(), so we should be safe.     */
+
+        /* Draw Tux:   */
+        SDL_BlitSurface(tux_stand->frame[tux_stand->cur], NULL, screen, &tux_loc);
+        /* Draw all the labels for the typing stats: */
+        SDL_BlitSurface(time_label_srfc, NULL, screen, &time_label);
+        SDL_BlitSurface(chars_label_srfc, NULL, screen, &chars_typed_label);
+        SDL_BlitSurface(cpm_label_srfc, NULL, screen, &cpm_label);
+        SDL_BlitSurface(wpm_label_srfc, NULL, screen, &wpm_label);
+        SDL_BlitSurface(errors_label_srfc, NULL, screen, &errors_label);
+        SDL_BlitSurface(accuracy_label_srfc, NULL, screen, &accuracy_label);
+
+
         /* Draw the phrase to be typed up to the next wrapping point: */
         wrap_pt = find_next_wrap(&phrases[cur_phrase][prev_wrap],
-                                  font, phrase_draw_width);
+                                  smallfont, phrase_draw_width);
         tmpsurf = BlackOutline_w(&phrases[cur_phrase][prev_wrap],
-                                  font, &white, wrap_pt + 1);
+                                  smallfont, &white, wrap_pt + 1);
         if (tmpsurf)
         {
           SDL_BlitSurface(tmpsurf, NULL, screen, &phr_text_rect);
@@ -159,7 +222,7 @@
         }
         /* Draw the text the player has typed so far: */
         tmpsurf = BlackOutline_w(&phrases[cur_phrase][prev_wrap],
-                                  font, &white,
+                                  smallfont, &white,
                                   cursor - prev_wrap);
         if (tmpsurf)
         {
@@ -168,22 +231,13 @@
           tmpsurf = NULL;
         }
 
-        /* Draw strings for time displays: */
-        tmpsurf = BlackOutline(keytime_str, font, &white);
+        tmpsurf = BlackOutline(time_str, smallfont, &white);
         if (tmpsurf)
         {
-          SDL_BlitSurface(tmpsurf, NULL, screen, &keytime_rect);
+          SDL_BlitSurface(tmpsurf, NULL, screen, &time_rect);
           SDL_FreeSurface(tmpsurf);
-          tmpsurf = NULL;	
-        }
-        tmpsurf = BlackOutline(totaltime_str, font, &white);
-        if (tmpsurf)
-        {
-          SDL_BlitSurface(tmpsurf, NULL, screen, &totaltime_rect);
-          SDL_FreeSurface(tmpsurf);
           tmpsurf = NULL;
         }
-//        SDL_BlitSurface(keyboard, NULL, screen, &keyboard_loc);
 
       /* state == 2 means user has pressed key, either correct or incorrect */
       case 2:
@@ -523,32 +577,48 @@
         /* Record elapsed time for this keypress and update running total: */
         a = SDL_GetTicks();
         keytimes[cursor] = a - start;
-        total += keytimes[cursor];
-        sprintf(keytime_str, "%.2f", (float) keytimes[cursor] / 1000);
-        sprintf(totaltime_str, "%.2f", (float) total / 1000);
         start = a;
 
+        total += keytimes[cursor];
+        sprintf(time_str, "%.2f sec", (float) total / 1000);
+        sprintf(chars_typed_str, "%d", correct_chars);
+        sprintf(cpm_str, "%.1f", (float) correct_chars /((float)total/60000));
+        sprintf(wpm_str, "%.1f", (float) ((float) correct_chars/5) /((float) total/60000));
+        sprintf(errors_str, "%d", wrong_chars);
 
+        /* Calculate accuracy, avoiding divide-by-zero error: */
+        if (correct_chars + wrong_chars == 0)
+          accuracy = 1;
+        else
+          accuracy = (float)correct_chars/((float) (correct_chars + wrong_chars));
+        sprintf(accuracy_str, "%.1f%%", accuracy * 100); 
+
+
         /****************************************************/
         /*  ---------- If user typed correct character, handle it: --------------- */
         if (phrases[cur_phrase][cursor] == event.key.keysym.unicode)
         {
           cursor++;
+          correct_chars++;
 
- //         state = 2;
-
+          /* Handle wrapping if we are at the end of the current display. */
+          /* NOTE now also checking for space at end of line so we wrap   */
+          /* automatically without waiting for user to type invisible     */
+          /* space                                                        */
           if (cursor >= prev_wrap + wrap_pt + 2) /* wrap onto next line */
           {
             /* This will cause the next line of the phrase to be drawn: */
             prev_wrap = prev_wrap + wrap_pt + 2;
             state = 1;
-
-/*            user_text_rect.x = 40;
-            user_text_rect.y = user_text_rect.y + user_text_rect.h;
-            mydest.y = user_text_rect.y;
-            mydest.h = screen->h - mydest.y;
-            next_line = 1;*/
           }
+          else if ((cursor == prev_wrap + wrap_pt + 1) /* skip terminal space */
+               && (phrases[cur_phrase][cursor] == ' '))
+          {
+            /* Need to increment cursor another time in this case: */
+            cursor ++;
+            prev_wrap = prev_wrap + wrap_pt + 2;
+            state = 1;
+          }
           else
             state = 2;
 
@@ -556,7 +626,7 @@
           /* except we don't want to redraw keyboard to avoid flicker:    */
 
           tmpsurf = BlackOutline_w(&phrases[cur_phrase][prev_wrap],
-                                   font, &white,
+                                   smallfont, &white,
                                    cursor - prev_wrap);
 
           if (tmpsurf)
@@ -568,44 +638,94 @@
           }
 
 
-          /* Draw strings for time displays: */
-          tmpsurf = BlackOutline(keytime_str, font, &white);
+          tmpsurf = BlackOutline(time_str, smallfont, &white);
           if (tmpsurf)
           {
-            SDL_BlitSurface(CurrentBkgd(), &keytime_rect, screen, &keytime_rect);
-            SDL_BlitSurface(tmpsurf, NULL, screen, &keytime_rect);
+            SDL_BlitSurface(CurrentBkgd(), &time_rect, screen, &time_rect);
+            SDL_BlitSurface(tmpsurf, NULL, screen, &time_rect);
             SDL_FreeSurface(tmpsurf);
-            tmpsurf = NULL;	
+            tmpsurf = NULL;
           }
 
-          tmpsurf = BlackOutline(totaltime_str, font, &white);
+          tmpsurf = BlackOutline(chars_typed_str, smallfont, &white);
           if (tmpsurf)
           {
-            SDL_BlitSurface(CurrentBkgd(), &totaltime_rect, screen, &totaltime_rect);
-            SDL_BlitSurface(tmpsurf, NULL, screen, &totaltime_rect);
+            SDL_BlitSurface(CurrentBkgd(), &chars_typed_rect, screen, &chars_typed_rect);
+            SDL_BlitSurface(tmpsurf, NULL, screen, &chars_typed_rect);
             SDL_FreeSurface(tmpsurf);
             tmpsurf = NULL;
           }
 
+          tmpsurf = BlackOutline(cpm_str, smallfont, &white);
+          if (tmpsurf)
+          {
+            SDL_BlitSurface(CurrentBkgd(), &cpm_rect, screen, &cpm_rect);
+            SDL_BlitSurface(tmpsurf, NULL, screen, &cpm_rect);
+            SDL_FreeSurface(tmpsurf);
+            tmpsurf = NULL;
+          }
+
+          tmpsurf = BlackOutline(wpm_str, smallfont, &white);
+          if (tmpsurf)
+          {
+            SDL_BlitSurface(CurrentBkgd(), &wpm_rect, screen, &wpm_rect);
+            SDL_BlitSurface(tmpsurf, NULL, screen, &wpm_rect);
+            SDL_FreeSurface(tmpsurf);
+            tmpsurf = NULL;
+          }
+
+          tmpsurf = BlackOutline(errors_str, smallfont, &white);
+          if (tmpsurf)
+          {
+            SDL_BlitSurface(CurrentBkgd(), &errors_rect, screen, &errors_rect);
+            SDL_BlitSurface(tmpsurf, NULL, screen, &errors_rect);
+            SDL_FreeSurface(tmpsurf);
+            tmpsurf = NULL;
+          }
+
+          tmpsurf = BlackOutline(accuracy_str, smallfont, &white);
+          if (tmpsurf)
+          {
+            SDL_BlitSurface(CurrentBkgd(), &accuracy_rect, screen, &accuracy_rect);
+            SDL_BlitSurface(tmpsurf, NULL, screen, &accuracy_rect);
+            SDL_FreeSurface(tmpsurf);
+            tmpsurf = NULL;
+          }
+
+          SDL_Flip(screen);
+
+          /* If player has completed phrase, celebrate! */
           if (cursor == wcslen(phrases[cur_phrase]))
           {
-            tmpsurf = BlackOutline(gettext("Great!"), font, &white);
-            if (tmpsurf)
+            /* Draw Tux celebrating: */
             {
-              /* Center message on intended point: */
-              int save_x = congrats_rect.x;
-              congrats_rect.x -= tmpsurf->w/2;
-              SDL_BlitSurface(tmpsurf, NULL, screen, &congrats_rect);
-              SDL_FreeSurface(tmpsurf);
-              tmpsurf = NULL;
-              /* reset rect to prior value: */
-              congrats_rect.x = save_x;
+              int i = 0;
+              int done = 0;
+
+              PlaySound(cheer);
+
+              while (!done)
+              {
+                while (SDL_PollEvent(&event))
+                {
+                  if ((event.type == SDL_KEYDOWN)
+                    ||(event.type == SDL_MOUSEBUTTONDOWN))
+                    done = 1;
+                }
+
+                /* Draw Tux: */
+                SDL_BlitSurface(CurrentBkgd(), &tux_loc, screen, &tux_loc);
+                if (tux_win && tux_win->frame[tux_win->cur])
+                  SDL_BlitSurface(tux_win->frame[tux_win->cur], NULL, screen, &tux_loc);
+                SDL_UpdateRect(screen, tux_loc.x, tux_loc.y, tux_loc.w, tux_loc.h);
+                NEXT_FRAME(tux_win);
+                SDL_Delay(200);
+              }
             }
 
-            SDL_Flip(screen);
-            SDL_Delay(1200);
-  //          next_line = 0;
-  //          quit = 2;
+//            SDL_Flip(screen);
+//            SDL_Delay(1200);
+
             /* Go on to next phrase, or back to first one if all done */
             if (cur_phrase < num_phrases)
               cur_phrase++;
@@ -627,14 +747,31 @@
           }
           state = 2;
 
+          /* Don't count shift keys as wrong: */
           if (event.key.keysym.sym != SDLK_RSHIFT
            && event.key.keysym.sym != SDLK_LSHIFT)
+          {
+            wrong_chars++;
             PlaySound(wrong);
+          }
         }
         
       } /* End of "if(event.type == SDL_KEYDOWN)" block  --*/
 
     }  /* ----- End of SDL_PollEvent() loop -------------- */
+
+    /* Draw next tux frame if appropriate: */
+    if ((SDL_GetTicks() - tuxtime) > SPRITE_FRAME_TIME)
+    {
+      tuxtime = SDL_GetTicks();
+
+      SDL_BlitSurface(CurrentBkgd(), &tux_loc, screen, &tux_loc);
+
+      if (tux_stand && tux_stand->frame[tux_stand->cur])
+        SDL_BlitSurface(tux_stand->frame[tux_stand->cur], NULL, screen, &tux_loc);
+      NEXT_FRAME(tux_stand);
+    }
+
     SDL_UpdateRect(screen, 0, 0, 0, 0);
 //    SDL_Flip(screen);
     SDL_Delay(30); /* FIXME should keep frame rate constant */
@@ -656,6 +793,12 @@
 /*                                                                      */
 /************************************************************************/
 
+/* Select appropriate font sizes based on the screen we're working with: */
+static void calc_font_sizes(void)
+{
+  fontsize = (screen->h)/18;
+  bigfontsize = fontsize * 3;
+}
 
 static int practice_load_media(void)
 {
@@ -683,26 +826,48 @@
     hand[i] = LoadImage(fn, IMG_ALPHA);
     if (!hand[i])
       load_failed = 1;
-  }  /* load needed sounds: */
+  }
 
-  wrong = LoadSound("tock.wav");
+  /* load tux sprites: */
+  tux_win = LoadSprite("tux/win", IMG_COLORKEY);
+  tux_stand = LoadSprite("tux/stand", IMG_COLORKEY);
+  /* load needed sounds: */
+  wrong = LoadSound("buzz.wav");
+  cheer = LoadSound("cheer.wav");
 
   /* load needed fonts: */
-  font = LoadFont(settings.theme_font_name, 30);
-  bigfont = LoadFont(settings.theme_font_name, 80);
+  calc_font_sizes();
+  smallfont = LoadFont(settings.theme_font_name, fontsize);
+  bigfont = LoadFont(settings.theme_font_name, bigfontsize);
 
+  /* create labels: */
+  time_label_srfc = BlackOutline(_("Time"), smallfont, &yellow);
+  chars_label_srfc = BlackOutline(_("Chars"), smallfont, &yellow);
+  cpm_label_srfc = BlackOutline(_("CPM"), smallfont, &yellow);
+  wpm_label_srfc = BlackOutline(_("WPM"), smallfont, &yellow);
+  errors_label_srfc = BlackOutline(_("Errors"), smallfont, &yellow);
+  accuracy_label_srfc = BlackOutline(_("Accuracy"), smallfont, &yellow);
+
   /* Get out if anything failed to load: */
   if (load_failed
     ||!num_phrases
     ||!hands
     ||!CurrentBkgd()
+    ||!tux_win
+    ||!tux_stand
     ||!wrong
-    ||!font
+    ||!smallfont
     ||!bigfont
     ||!keyboard
     ||!hand_shift[0]
     ||!hand_shift[1]
-    ||!hand_shift[2])
+    ||!hand_shift[2]
+    ||!time_label_srfc
+    ||!chars_label_srfc
+    ||!cpm_label_srfc
+    ||!wpm_label_srfc
+    ||!errors_label_srfc
+    ||!accuracy_label_srfc)
   {
     fprintf(stderr, "practice_load_media() - failed to load needed media \n");
     practice_unload_media;
@@ -712,7 +877,7 @@
 
   /* Now render letters for glyphs in alphabet: */
   /* FIXME do we need this? */
-  RenderLetters(font);
+//  RenderLetters(font);
   //TTF_CloseFont(font);  /* Don't need it after rendering done */
   //font = NULL;
   GenerateKeyboard(keyboard);
@@ -725,63 +890,176 @@
 
 static void recalc_positions(void)
 {
-  /* we can't just use phr_text_rect.w to calc wrap */
-  /* because SDL_BlitSurface() clobbers it: */
-  phrase_draw_width = screen->w * 0.9;
+  if (!keyboard
+    ||!tux_win
+    ||!tux_win->frame[0]
+    ||!hand[0])
+  {
+    fprintf(stderr, "recalc_positions() - needed ptr invalid - returning\n");
+  } 
 
-  phr_text_rect.x = screen->w * 0.1;
-  phr_text_rect.y = screen->h * 0.1;
+  /* Screen is divided into three areas or 'panes' : */
+  /*
+        *************************************
+        *        *                          *
+        * left   *           top            *
+        *        *                          *
+        *        ****************************
+        *        *                          *
+        *        *                          *
+        *        *          bottom          *
+        *        *                          *
+        *        *                          *
+        *************************************
+  */
 
-  user_text_rect.x = screen->w * 0.1;
-  user_text_rect.y = phr_text_rect.y + 60;
-  user_text_rect.w = screen->w * 0.8;
-  user_text_rect.h = 30;    /* FIXME ideally should calculate from font height */
+  left_pane.x = 0;
+  left_pane.y = 0;
+  left_pane.w = screen->w * 0.25;
+  left_pane.h = screen->h;
 
+  top_pane.x = screen->w * 0.25;
+  top_pane.y = 0;
+  top_pane.w = screen->w * 0.75;
+  top_pane.h = screen->h * 0.4;
 
-  keytime_rect.x = 50;
-  keytime_rect.y = screen->h - 80;
-  keytime_rect.w = 100;
-  keytime_rect.h = 30;
+  bottom_pane.x = screen->w * 0.25;
+  bottom_pane.y = screen->h * 0.4;
+  bottom_pane.w = screen->w * 0.75;
+  bottom_pane.h = screen->h * 0.6;
 
-  totaltime_rect.x = screen->w - 160;
-  totaltime_rect.y = screen->h - 80;
-  totaltime_rect.w = 100;
-  totaltime_rect.h = 30;
+  /* Set up all the locations within the left pane: */
+  tux_loc.x = left_pane.x + 5;
+  tux_loc.y = left_pane.y + 5;
+  tux_loc.w = tux_stand->frame[0]->w;
+  tux_loc.h = tux_stand->frame[0]->h;
 
-  congrats_rect.x = screen->w/2;
-  congrats_rect.y = 200;//screen->h - 80;
+  time_label.x = left_pane.x + 5;
+  time_label.y = tux_loc.y + tux_loc.h + 5;
+  time_label.w = left_pane.w - 5;
+  time_label.h = fontsize;
 
-  /* This is just a rectangle to redraw everything from the user's text on down: */
-  mydest.x = 0;
-  mydest.y = user_text_rect.y;
-  mydest.w = screen->w;
-  mydest.h = screen->h-mydest.y;
+  time_rect.x = left_pane.x + 5;
+  time_rect.y = time_label.y + time_label.h;
+  time_rect.w = left_pane.w - 5;
+  time_rect.h = fontsize;
 
-  hand_loc.x = (screen->w/2) - (hand[0]->w/2);
-  hand_loc.y = screen->h - (hand[0]->h) - 20;
+  chars_typed_label.x = left_pane.x + 5;
+  chars_typed_label.y = time_rect.y + time_rect.h;
+  chars_typed_label.w = left_pane.w - 5;
+  chars_typed_label.h = fontsize;
+
+  chars_typed_rect.x = left_pane.x + 5;
+  chars_typed_rect.y = chars_typed_label.y + chars_typed_label.h;
+  chars_typed_rect.w = left_pane.w - 5;
+  chars_typed_rect.h = fontsize;
+
+  cpm_label.x = left_pane.x + 5;
+  cpm_label.y = chars_typed_rect.y + chars_typed_rect.h;
+  cpm_label.w = left_pane.w - 5;
+  cpm_label.h = fontsize;
+
+  cpm_rect.x = left_pane.x + 5;
+  cpm_rect.y = cpm_label.y + cpm_label.h;
+  cpm_rect.w = left_pane.w - 5;
+  cpm_rect.h = fontsize;
+
+  wpm_label.x = left_pane.x + 5;
+  wpm_label.y = cpm_rect.y + cpm_rect.h;
+  wpm_label.w = left_pane.w - 5;
+  wpm_label.h = fontsize;
+
+  wpm_rect.x = left_pane.x + 5;
+  wpm_rect.y = wpm_label.y + wpm_label.h;
+  wpm_rect.w = left_pane.w - 5;
+  wpm_rect.h = fontsize;
+
+  errors_label.x = left_pane.x + 5;
+  errors_label.y = wpm_rect.y + wpm_rect.h;
+  errors_label.w = left_pane.w - 5;
+  errors_label.h = fontsize;
+
+  errors_rect.x = left_pane.x + 5;
+  errors_rect.y = errors_label.y + errors_label.h;
+  errors_rect.w = left_pane.w - 5;
+  errors_rect.h = fontsize;
+
+  accuracy_label.x = left_pane.x + 5;
+  accuracy_label.y = errors_rect.y + errors_rect.h;
+  accuracy_label.w = left_pane.w - 5;
+  accuracy_label.h = fontsize;
+
+  accuracy_rect.x = left_pane.x + 5;
+  accuracy_rect.y = accuracy_label.y + accuracy_label.h;
+  accuracy_rect.w = left_pane.w - 5;
+  accuracy_rect.h = fontsize;
+
+  /* Set up all the locations within the top pane: */
+  phr_text_rect.x = top_pane.x + 5;
+  phr_text_rect.y = top_pane.y + top_pane.h * 0.3;
+  phr_text_rect.w = top_pane.w - 5;
+  phr_text_rect.h = fontsize;
+
+  /* we can't just use phr_text_rect.w to calc wrap */
+  /* because SDL_BlitSurface() clobbers it: */
+  phrase_draw_width = phr_text_rect.w;
+
+  user_text_rect.x = top_pane.x + 5;
+  user_text_rect.y = top_pane.y + top_pane.h * 0.6;
+  user_text_rect.w = top_pane.w - 5;
+  user_text_rect.h = fontsize;
+
+  /* Set up all the locations within the bottom pane: */
+  keyboard_loc.x = bottom_pane.x + bottom_pane.w/4 - keyboard->w/4;
+  keyboard_loc.y = bottom_pane.y + 5;
+  keyboard_loc.w = keyboard->w;
+  keyboard_loc.h = keyboard->h;
+
+  hand_loc.x = keyboard_loc.x;
+  hand_loc.y = keyboard_loc.y + keyboard_loc.h + 20;
   hand_loc.w = (hand[0]->w);
   hand_loc.h = (hand[0]->h);
 
-  /****     Position of keyboard image       */
-  keyboard_loc.x = screen->w/2 -keyboard->w/2 - 50;
-  keyboard_loc.y = screen->h * 0.4;
-  keyboard_loc.w = screen->w/8;
-  keyboard_loc.h = screen->h/8;
 
-  nextletter_rect.x = keyboard_loc.x + keyboard->w + 20;
-  nextletter_rect.y = keyboard_loc.y;
-  nextletter_rect.w = 80;
-  nextletter_rect.h = 80;
+  nextletter_rect.x = keyboard_loc.x + keyboard_loc.w - 80;
+  nextletter_rect.y = keyboard_loc.y + keyboard_loc.h;
+  nextletter_rect.w = bigfontsize * 1.5;
+  nextletter_rect.h = bigfontsize;
 
 }
 
+
 static void practice_unload_media(void)
 {
   int i;
 
   FreeBothBkgds();
-  FreeLetters(); 
+//  FreeLetters(); 
 
+  if (time_label_srfc)
+    SDL_FreeSurface(time_label_srfc);
+  time_label_srfc = NULL;
+
+  if (chars_label_srfc)
+    SDL_FreeSurface(chars_label_srfc);
+  chars_label_srfc = NULL;
+
+  if (cpm_label_srfc)
+    SDL_FreeSurface(cpm_label_srfc);
+  cpm_label_srfc = NULL;
+
+  if (wpm_label_srfc)
+    SDL_FreeSurface(wpm_label_srfc);
+  wpm_label_srfc = NULL;
+
+  if (errors_label_srfc)
+    SDL_FreeSurface(errors_label_srfc);
+  errors_label_srfc = NULL;
+
+  if (accuracy_label_srfc)
+    SDL_FreeSurface(accuracy_label_srfc);
+  accuracy_label_srfc = NULL;
+
   if (hands)
     SDL_FreeSurface(hands);
   hands = NULL;
@@ -797,9 +1075,9 @@
     SDL_FreeSurface(keyboard);
   keyboard = NULL;
 
-  if (font)
-    TTF_CloseFont(font);
-  font = NULL;
+  if (smallfont)
+    TTF_CloseFont(smallfont);
+  smallfont = NULL;
 
   if (bigfont)
     TTF_CloseFont(bigfont);
@@ -812,6 +1090,22 @@
     hand[i] = NULL;
   }
 
+  if (tux_stand)
+  {
+    FreeSprite(tux_stand);
+    tux_stand = NULL;
+  }
+
+  if (tux_win)
+  {
+    FreeSprite(tux_win);
+    tux_win = NULL;
+  }
+
+  if (cheer)
+    Mix_FreeChunk(cheer);
+  cheer = NULL;
+
   if (wrong)
     Mix_FreeChunk(wrong);
   wrong = NULL;
@@ -970,7 +1264,7 @@
     /* Need to convert to UTF8 because couldn't get UNICODE version to work: */
     ConvertToUTF8(buf, UTF8buf);
     /*  Now check width of string: */
-    if (-1 == TTF_SizeUTF8(font, UTF8buf, &test_w, NULL))
+    if (-1 == TTF_SizeUTF8(smallfont, UTF8buf, &test_w, NULL))
     {
       /* An error occurred: */
       return -1;
@@ -1134,7 +1428,7 @@
   {
     LOG("Wrap not needed\n");
 
-    tmp = BlackOutline_w(pphrase, font, &white, wrap);
+    tmp = BlackOutline_w(pphrase, smallfont, &white, wrap);
     if (tmp)
     {
       SDL_BlitSurface(tmp, NULL, screen, &dst);
@@ -1146,7 +1440,7 @@
   {
     LOG("Line length exceeded - wrap required\n");
 
-    tmp = BlackOutline_w(pphrase, font, &white, wrap + 1);
+    tmp = BlackOutline_w(pphrase, smallfont, &white, wrap + 1);
     if (tmp)
     {
       SDL_BlitSurface(tmp, NULL, screen, &dst);
@@ -1155,7 +1449,7 @@
       tmp = NULL;
     }
 
-    tmp = BlackOutline_w(pphrase+wrap+1, font, &white, wcslen(pphrase));
+    tmp = BlackOutline_w(pphrase+wrap+1, smallfont, &white, wcslen(pphrase));
     if (tmp)
     {
       SDL_BlitSurface(tmp, NULL, screen, &dst);




More information about the Tux4kids-commits mailing list