Return the center of the image instead of the top-left corner
[cascardo/movie.git] / movie.c
diff --git a/movie.c b/movie.c
index 8bba5ac..f5ef008 100644 (file)
--- a/movie.c
+++ b/movie.c
  *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
  */
 
+#define WIDTH 800
+#define HEIGHT 600
 
+#include <stdio.h>
+#include <stdlib.h>
 #include <SDL.h>
 #include <SDL_image.h>
 
+#define SWAP(x, y) do { \
+       x ^= y; y ^= x; x ^= y; \
+       } while (0)
+
+#define ABS(x) ((x) < 0 ? -(x) : (x))
+
+#define IS_CENTER(cx, cy, x, y) \
+       ((x + WIDTH/2 == cx) && (y + HEIGHT/2 == cy))
+
+SDL_Rect *points;
+int psize;
+
+void
+ReadPoints (char *filename)
+{
+  FILE *file;
+  char *buffer;
+  char *next;
+  size_t len;
+  int i;
+  file = fopen (filename, "r");
+  fscanf (file, "%d\n", &psize);
+  points = malloc (sizeof (SDL_Rect) * psize);
+  if (points == NULL)
+    abort ();
+  buffer = NULL;
+  len = 0;
+  for (i = 0; i < psize; i++)
+  {
+    getline (&buffer, &len, file);
+    points[i].x = strtol (buffer, &next, 0);
+    points[i].y = strtol (next+1, NULL, 0);
+  }
+  fclose (file);
+}
+
+SDL_Rect *
+GetNextPoint (void)
+{
+  static SDL_Rect rect = {0, 0, WIDTH, HEIGHT};
+  static int cur = -1;
+  static int inc, err, thre, swap;
+  static int x1, y1, x2, y2;
+  static int x, y;
+  int next;
+  next = (cur + 1) % psize;
+  if ((points[next].x == rect.x && points[next].y == rect.y) || cur == -1)
+  {
+    cur = next;
+    next = (cur + 1) % psize;
+    err = 0;
+    swap = 0;
+    x1 = points[cur].x;
+    y1 = points[cur].y;
+    x2 = points[next].x;
+    y2 = points[next].y;
+    inc = y2 - y1;
+    thre = x2 - x1;
+    if (ABS (inc) > ABS (thre))
+    {
+      SWAP (inc, thre);
+      SWAP (x1, y1);
+      SWAP (x2, y2);
+      swap = 1;
+    }
+    x = x1;
+    y = y1;
+  }
+  rect.x = (swap ? y : x);
+  rect.y = (swap ? x : y);
+  (x2 < x1) ? x-- : x++;
+  err += ABS (inc);
+  if (err >= ABS (thre))
+  {
+    err -= ABS (thre);
+    y += (inc < 0) ? -1 : 1;
+  }
+  return &rect;
+}
+
+void
+ShowPoint (SDL_Surface *screen, SDL_Surface *image, SDL_Rect *rect)
+{
+  SDL_BlitSurface (image, rect, screen, NULL);
+  SDL_UpdateRect (screen, 0, 0, 0, 0);
+}
+
+Uint32
+ShowNext (Uint32 interval, void *data)
+{
+  SDL_UserEvent event;
+  event.type = SDL_USEREVENT;
+  event.code = 0;
+  SDL_PushEvent ((SDL_Event *) &event);
+  return 33;
+}
+
 int
 main (int argc, char **argv)
 {
-  SDL_Surface *image;
   SDL_Surface *screen;
+  SDL_Surface *image;
   SDL_Event event;
+  ReadPoints ("pro-gnu");
   SDL_Init (SDL_INIT_VIDEO | SDL_INIT_TIMER);
-  screen = SDL_SetVideoMode (800, 600, 32, SDL_HWSURFACE | SDL_DOUBLEBUF | SDL_FULLSCREEN);
+  screen = SDL_SetVideoMode (800, 600, 32, SDL_HWSURFACE | SDL_DOUBLEBUF);
   image = IMG_Load ("/home/cascardo/fotos/debconf.jpg");
-  SDL_BlitSurface (image, NULL, screen, NULL);
-  SDL_UpdateRect (screen, 0, 0, 0, 0);
+  SDL_AddTimer (0, ShowNext, NULL);
   while (SDL_WaitEvent (&event))
   {
     if (event.type == SDL_KEYDOWN)
       break;
+    else if (event.type == SDL_USEREVENT)
+      ShowPoint (screen, image, GetNextPoint ());
   }
   SDL_FreeSurface (image);
   SDL_Quit ();
+  free (points);
   return 0;
 }