/* LICENSE:
  =========================================================================
    CMPack'04 Source Code Release for OPEN-R SDK 1.1.5-r2 for ERS7
    Copyright (C) 2004 Multirobot Lab [Project Head: Manuela Veloso]
    School of Computer Science, Carnegie Mellon University
    All rights reserved.
  ========================================================================= */


#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "agent/Vision/colors.h"

#include "util.h"
#include "image.h"

rgb yuv2rgb(yuv c)
{
  rgb r;
  int y,u,v;

  y = c.y;
  u = c.u*2 - 255;
  v = c.v*2 - 255;

  r.red   = bound(y + u                     ,0,255);
  r.green = bound((int)(y - 0.51*u - 0.19*v),0,255);
  r.blue  = bound(y + v                     ,0,255);

  return(r);
}

void yuv2rgb(rgb *dest,yuv *src,int width,int height)
{
  int size = width*height;
  int i;

  for(i=0; i<size; i++){
    dest[i] = yuv2rgb(src[i]);
  }
}

void fix_image(SImage &img)
// Gets rid of garbage bits at the bottom of all
// dog images by copying an adjacent row over it
{
  int i;
  rgb r;

  for(i=0; i<16; i++){
    r = img.getpixel_fast(i,img.h-2);
    img.setpixel(i,img.h-1,r);
  }
}

const rgb RGB_Black = {  0,  0,  0};
const rgb YUV_Black = {  0,128,128};


int main(int argc,char **argv)
{
  SImage src,rgb_dest,yuv_dest;
  char *file;

  int width,height;
  int x,y,w,h,n;
  int a;

  if(argc < 3){
    printf("Usage: tile <width> [yuv image file(s)]\n");
    return(1);
  }

  // Read number of images and tiling dimensions
  n = argc - 2;
  w = atoi(argv[1]);
  h = (n + w-1) / w;

  // grab first image to get dimensions
  a = 2;
  src.load(argv[a]);
  width  = src.w;
  height = src.h;
  printf("Images=%d Width=%d Height=%d Tile=%dx%d\n",
         n,width,height,w,h);

  // allocate total space for destination images and clear them
  rgb_dest.allocate(w*width,h*height);
  yuv_dest.allocate(w*width,h*height);
  rgb_dest.clear(RGB_Black);
  yuv_dest.clear(YUV_Black);

  printf("Adding images");
  for(y=0; y<h; y++){
    for(x=0; x<w; x++){
      if(a < argc){
        file = argv[a];
        if(src.load(file)){
          if(width==src.w && height==src.h){
            fix_image(src);
            yuv_dest.blit(src,x*width,y*height);
            printf("."); fflush(stdout);
          }else{
            printf("\nERROR: Images are not all the same size ('%s')\n",file);
            exit(1);
          }
        }else{
          printf("\nERROR: Cannot load '%s'\n",file);
          exit(1);
        }
      }
      a++;
    }
  }
  printf("done.\n");

  printf("Converting to RGB..."); fflush(stdout);
  yuv2rgb(rgb_dest.img,(yuv*)yuv_dest.img,yuv_dest.w,yuv_dest.h);
  printf("done.\n");

  printf("Saving..."); fflush(stdout);
  yuv_dest.save("imageyuv.ppm");
  rgb_dest.save("imagergb.ppm");
  printf("done.\n");

  return(0);
}
