# include <kapa_internal.h>

int KiiCenter (int fd, double x, double y, int zoom) {

  KiiSendCommand (fd, 4, "CENT");
  KiiSendMessage (fd, "%8.3f %8.3f %8d ", x, y, zoom);
  KiiWaitAnswer (fd, "DONE");
  
  return (TRUE);
}

int KiiResize (int fd, int Nx, int Ny) {

  KiiSendCommand (fd, 4, "RSIZ");
  KiiSendMessage (fd, "%d %d", Nx, Ny); 
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaBox (int fd, Graphdata *graphdata) {

  KiiSendCommand (fd, 4, "DBOX");
  KiiSendMessage (fd, "%12.6g %12.6g %12.6g %12.6g", 
		    graphdata[0].xmin, graphdata[0].xmax, graphdata[0].ymin, graphdata[0].ymax);

  KiiSendMessage (fd, "%lf %d", graphdata[0].lweight, graphdata[0].color);

  KiiSendMessage (fd, "%s %s %s", graphdata[0].axis, graphdata[0].labels, graphdata[0].ticks);
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaClearCurrentPlot (int fd) {
  
  KiiSendCommand (fd, 4, "ERSC");
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaClearPlots (int fd) {
  
  KiiSendCommand (fd, 4, "ERSP");
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaClearSections (int fd) {
  
  KiiSendCommand (fd, 4, "ERSS");
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaClearImage (int fd) {
  
  KiiSendCommand (fd, 4, "ERSI");
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaSetToolbox (int fd, int location) {
  
  KiiSendCommand (fd, 4, "TOOL");
  KiiSendMessage (fd, "%d", location); 
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaInitGraph (Graphdata *graphdata) {

  graphdata[0].xmin = graphdata[0].ymin = 0.0;
  graphdata[0].xmax = graphdata[0].ymax = 1.0;
  graphdata[0].style = graphdata[0].ptype = 0;
  graphdata[0].ltype = graphdata[0].color = 0;
  graphdata[0].etype = graphdata[0].ebar = 0;
  graphdata[0].lweight = graphdata[0].size = 1.0;
    
  graphdata[0].coords.pc1_1 = graphdata[0].coords.pc2_2 = 1.0;
  graphdata[0].coords.pc1_2 = graphdata[0].coords.pc2_1 = 0.0;
  strcpy (graphdata[0].coords.ctype, "RA---LIN");
  graphdata[0].coords.crval1 = 0.0;
  graphdata[0].coords.crval2 = 0.0;
  graphdata[0].coords.crpix1 = 0.0;
  graphdata[0].coords.crpix2 = 0.0;
  graphdata[0].coords.cdelt1 = graphdata[0].coords.cdelt2 = 1.0;
  graphdata[0].flipeast = TRUE;
  graphdata[0].flipnorth = FALSE;
  strcpy (graphdata[0].axis, "2222");
  strcpy (graphdata[0].ticks, "2222");
  strcpy (graphdata[0].labels, "2222");

  return (TRUE);
}

int KapaPrepPlot (int fd, int Npts, Graphdata *data) {

  /* tell kapa to look for the incoming image */
  KiiSendCommand (fd, 4, "PLOT"); 
  
  /* send kapa the plot details */
  KiiSendMessage (fd, "%8d %8d %d %d %d %d %d %f %f", 
		  Npts, data[0].style, 
		  data[0].ptype, data[0].ltype, 
		  data[0].etype, data[0].ebar, data[0].color, 
		  data[0].lweight, data[0].size);
  KiiSendMessage (fd, "%g %g %g %g", 
		  data[0].xmin, data[0].xmax, 
		  data[0].ymin, data[0].ymax);
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaSetGraphData (int fd, Graphdata *data) {

  /* tell kapa to look for the incoming image */
  KiiSendCommand (fd, 4, "SSTY"); 
  
  /* send kapa the plot details */
  KiiSendMessage (fd, "%8d %d %d %d %d %d %f %f", 
		  data[0].style, 
		  data[0].ptype, data[0].ltype, 
		  data[0].etype, data[0].ebar, data[0].color, 
		  data[0].lweight, data[0].size);

  KiiSendMessage (fd, "%g %g %g %g", 
		  data[0].xmin, data[0].xmax, 
		  data[0].ymin, data[0].ymax);

  KiiSendMessage (fd, "%g %g %g %g", 
		  data[0].coords.pc1_1, data[0].coords.pc2_2,
		  data[0].coords.pc1_2, data[0].coords.pc2_1);

  KiiSendMessage (fd, "%d %d %s", 
		  data[0].flipeast, data[0].flipnorth,
		  data[0].coords.ctype);

  KiiSendMessage (fd, "%g %g %g %g %g %g", 
		  data[0].coords.crval1,
		  data[0].coords.crval2,
		  data[0].coords.crpix1,
		  data[0].coords.crpix2,
		  data[0].coords.cdelt1,
		  data[0].coords.cdelt2);

  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaGetGraphData (int fd, Graphdata *data) {

  /* tell kapa to look for the incoming image */
  KiiSendCommand (fd, 4, "GSTY"); 
  
  /* send kapa the plot details */
  KiiScanMessage (fd, "%d %d %d %d %d %d %lf %lf", 
		  &data[0].style, 
		  &data[0].ptype, &data[0].ltype, 
		  &data[0].etype, &data[0].ebar, &data[0].color, 
		  &data[0].lweight, &data[0].size);

  KiiScanMessage (fd, "%lf %lf %lf %lf", 
		  &data[0].xmin, &data[0].xmax, 
		  &data[0].ymin, &data[0].ymax);

  KiiScanMessage (fd, "%f %f %f %f", 
		  &data[0].coords.pc1_1, &data[0].coords.pc2_2,
		  &data[0].coords.pc1_2, &data[0].coords.pc2_1);

  KiiScanMessage (fd, "%d %d %s", 
		  &data[0].flipeast, &data[0].flipnorth,
		  data[0].coords.ctype);

  KiiScanMessage (fd, "%lf %lf %f %f %f %f", 
		  &data[0].coords.crval1,
		  &data[0].coords.crval2,
		  &data[0].coords.crpix1,
		  &data[0].coords.crpix2,
		  &data[0].coords.cdelt1,
		  &data[0].coords.cdelt2);

  // XXX at some point, we need to add polynomials and 2-level mosaic
  // astrometry here.

  data[0].coords.Npolyterms = 0;

  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaSetImageData (int fd, KapaImageData *data) {

  /* tell kapa to look for the incoming image */
  KiiSendCommand (fd, 4, "SIMD"); 
  
  /* send kapa the plot details */
  KiiSendMessage (fd, "%g %g %s %s", 
		  data[0].zero, data[0].range, data[0].name, data[0].file);

  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaGetImageData (int fd, KapaImageData *data) {

  /* tell kapa to look for the incoming image */
  KiiSendCommand (fd, 4, "GIMD"); 
  
  KiiScanMessage (fd, "%lf %lf %s %s", 
		  &data[0].zero, &data[0].range, data[0].name, data[0].file);

  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaPlotVector (int fd, int Npts, float *values, char *type) {

  int Nbytes;
  int swap;

# ifdef BYTE_SWAP
  swap = 1;
# else
  swap = 0;
# endif

  Nbytes = Npts * sizeof (float);

  if (!strcmp(type, "x")) goto valid;
  if (!strcmp(type, "y")) goto valid;
  if (!strcmp(type, "z")) goto valid;
  if (!strcmp(type, "dym")) goto valid;
  if (!strcmp(type, "dyp")) goto valid;
  if (!strcmp(type, "dxm")) goto valid;
  if (!strcmp(type, "dxp")) goto valid;
  return (FALSE);

valid:
  KiiSendCommand (fd, 4, "PLOB"); 
  KiiSendMessage (fd, "%s %d %d %d", type, Npts, Nbytes, swap); 

  write (fd, values, Nbytes);
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaSetFont (int fd, char *name, int size) {

  KiiSendCommand (fd, 4, "FONT");
  KiiSendCommand (fd, 16, "%s", name);
  KiiSendCommand (fd, 16, "%d", size);
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaSendLabel (int fd, char *string, int mode) {

  KiiSendCommand (fd, 4, "LABL");
  KiiSendMessage (fd, "%6d", mode);
  KiiSendData (fd, string, strlen(string));
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaSendTextline (int fd, char *string, float x, float y, float angle) {
  
  KiiSendCommand (fd, 4, "PTXT");
  KiiSendMessage (fd, "%f %f %f", x, y, angle);
  KiiSendData (fd, string, strlen(string));
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaSetLimits (int fd, Graphdata *data) {

  KiiSendCommand (fd, 4, "SLIM");
  KiiSendMessage (fd, "%g %g %g %g ", data[0].xmin, data[0].xmax, data[0].ymin, data[0].ymax);
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

// for now, this just gets the dimensions
int KapaGetLimits (int fd, float *dx, float *dy) {

  KiiSendCommand (fd, 4, "GLIM"); 
  KiiScanMessage (fd, "%f %f", dx, dy); 
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaSetSection (int fd, KapaSection *section) {

  KiiSendCommand (fd, 4, "DSEC");
  KiiSendMessage (fd, "%s %6.3f %6.3f %6.3f %6.3f", 
		  section[0].name, 
		  section[0].x,
		  section[0].y,
		  section[0].dx,
		  section[0].dy);
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaMoveSection (int fd, char *name, char *direction) {

  if (!strcasecmp(direction, "up")) goto valid;
  if (!strcasecmp(direction, "down")) goto valid;
  if (!strcasecmp(direction, "top")) goto valid;
  if (!strcasecmp(direction, "bottom")) goto valid;
  
  fprintf (stderr, "unexpected direction %s\n", direction); 
  return (FALSE);

valid:
  KiiSendCommand (fd, 4, "MSEC");
  KiiSendMessage (fd, "%s %s", name, direction);
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaSelectSection (int fd, char *name) {

  KiiSendCommand (fd, 4, "SSEC");
  KiiSendMessage (fd, "%s", name);
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}

int KapaGetSection (int fd, char *name) {

  KiiSendCommand (fd, 4, "LSEC");
  KiiSendMessage (fd, "%s", name);
  KiiWaitAnswer (fd, "DONE");
  return (TRUE);
}
