/* 'central' file for !polysaw.  initiallisation and event handlers */


#include "wimp.h"
#include "wimpt.h"
#include "win.h"
#include "event.h"
#include "baricon.h"
#include "res.h"
#include "resspr.h"
#include "menu.h"
#include "template.h"
#include "dbox.h"
#include "werr.h"
#include "bbc.h" 
#include "coords.h" 
#include "saveas.h"
#include "os.h"
#include "xferrecv.h"
#include "colourtran.h"

#include <stdlib.h>
#include <string.h>

#include "PolySaw.h"

/******************************* CONSTANTS *****************************/


/* Menu items */
#define baricon_menu_info     1
#define baricon_menu_quit     2
static const char * baricon_menu_entries = ">Info,Quit";
#define SAVE 1
#define SHOWTOOLS 2
static const char *  board_menu_entries = ">Save,Show Tools";

/* Info box field for the version string */
#define version_info_field    4

/* modes of operation in 'board' = icon number in 'tools' */
#define PLAY 0
#define SQUARES 1
#define HOLES 2
#define PIECES 3
#define FRESHSTART 4

/************************* STATIC *******************************/

static char    version_string[40] = "1.10";
static menu    baricon_menu;
static menu    board_menu;
static BOOL    board_open = FALSE;


/********************* EXTERN GLOBALS ****************************/

wimp_w           tools_wh;
wimp_w           board_wh;
wimp_wind *      board_windefn;           /* for getting work extent for
                                         updates via template_syshandle */
int              nofpieces=0; 
Polymo           piece[MAX_PIECES];   
char             grid[MAX_BOARD][MAX_BOARD];
int              pe_mode=0;               /* play/edit mode */
char             filepath[256];
int              boardfiletype;

/*****************************  FUNCTIONS *********************/
static BOOL create_win(wimp_w *handle, char *name);
static void deal_with_but(wimp_mousestr m);
static void baricon_click(wimp_i icon);
static void display_prog_info(void);
static void baricon_menuproc(void *handle, char *hit);
static void board_menuproc(void *handle, char *hit);
static void tools_event_handler(wimp_eventstr *e, void *handle);
static void board_event_handler(wimp_eventstr *e, void *handle);
static BOOL initialise(void);





BOOL create_win(wimp_w *handle, char *name)
{
wimp_wind *w;
w = template_syshandle(name);
if (w == 0) return FALSE;

return (wimpt_complain(wimp_create_wind(w, handle)) == 0);
}



/************************* EVENT HANDLERS ******************************/

/* Select and Adjust on main 'board' window */
/* calls functions. in dragging or edit files according to pe_mode */
void deal_with_but(wimp_mousestr m)
{
wimp_bbits      mse_b;
wimp_wstate     result;
coords_pointstr mse;
coords_pointstr wrk;

mse_b = m.bbits;
mse.x  = m.x;
mse.y  = m.y;
wimp_get_wind_state(m.w, &result);
wrk = mse;
coords_point_toworkarea(&wrk, (coords_cvtstr *)&result.o.box);

switch (pe_mode)
  {
  case PLAY:
  deal_with_play_but(wrk, mse, mse_b, result.o.box);
  break;

  case SQUARES:
  deal_with_squares_but(wrk, mse_b);
  break;

  case HOLES:
  deal_with_holes_but(wrk, mse_b);
  break;

  case PIECES:
  deal_with_jnsplt_but(wrk, mse_b);
  break;

  default:
  break;
  }
}



void baricon_click(wimp_i icon)
{
icon = icon; 
if (!board_open)
  {
    wimp_wstate  state;

    if (wimpt_complain(wimp_get_wind_state(board_wh, &state)) == 0)
    {
      state.o.behind = -1;       /* Make sure window is opened in front */
      wimpt_noerr(wimp_open_wind(&state.o));
      board_open = TRUE;
    }
  }

}



void display_prog_info(void)
{
dbox  d;  
if (d = dbox_new("ProgInfo"), d != NULL)
  {
  dbox_setfield(d, version_info_field, version_string);
  dbox_show(d);
  dbox_fillin(d);
  dbox_dispose(&d);
  }
}




void baricon_menuproc(void *handle, char *hit)
{
handle = handle; 

switch (hit[0])
  {
  case baricon_menu_info:
    display_prog_info();
    break;

  case baricon_menu_quit:

    exit(0);
  }
}



void board_menuproc(void *handle, char *hit)
{
wimp_wstate  state;

handle = handle; 
switch (hit[0])
  {
  case SAVE:
  saveas(0x4bd, filepath, 2000, save_poly_board, 0, 0, 0);
  break;

  case SHOWTOOLS:
  if (wimpt_complain(wimp_get_wind_state(tools_wh, &state)) == 0)
    {
    state.o.behind = -1;          /* Make sure window is opened in front */
    wimpt_noerr(wimp_open_wind(&state.o));
    }
  }
}
 

void tools_event_handler(wimp_eventstr *e, void *handle)
{
int icon;
int row, col;
handle = handle;


switch (e->e)
  {
  case wimp_EREDRAW:
  break;

  case wimp_EOPEN:
  wimpt_noerr(wimp_open_wind(&e->data.o));
  break;

  case wimp_ECLOSE: 
  wimpt_noerr(wimp_close_wind(e->data.o.w));
  break;

  case wimp_EBUT:
  
  icon = e->data.but.m.i;  /* NB adjust does deselection, seem to
                                 be stuck with that for icons, so
                                 it would be better to call which_icon() */
  if (icon <= PIECES)
    pe_mode = icon;

  if (icon == FRESHSTART)  
    {
    wimp_redrawstr r;

    nofpieces = 0;
    for (row=0; row<MAX_BOARD; row++)
      {
      for (col=0; col<MAX_BOARD; col++)
        {
        grid[row][col] = 0;
        }
      }
    r.w = board_wh;
    r.box = board_windefn->ex;
    wimpt_noerr(wimp_force_redraw(&r));

    }
  break;

  default:
  break;
  }
}




 

void board_event_handler(wimp_eventstr *e, void *handle)
{

handle = handle;

switch (e->e)
  {
  case wimp_ENULL:
  update_drag();
  break;

  case wimp_EREDRAW:
  redraw_board(e->data.o.w);
  break;

  case wimp_EOPEN:
  wimpt_noerr(wimp_open_wind(&e->data.o));
  break;

  case wimp_ECLOSE: 
  wimpt_noerr(wimp_close_wind(e->data.o.w));
  board_open = FALSE;
  break;

  case wimp_EBUT:
  deal_with_but(e->data.but.m);
  break;

  case wimp_ESEND:
  case wimp_ESENDWANTACK:
  switch (e->data.msg.hdr.action)
    {
    case wimp_MDATALOAD:
    case wimp_MDATAOPEN:
    load_file();
    break;
    }
  break;

  default:   
  break;
  }
}

/****************************** INITIALISATION ******************************/


BOOL initialise(void)
{
char filetypevarname[16];
char buffer[16];
char *endp = buffer;
 
/* RISC_OSlib initialisation */
wimpt_init("PolySaw"); 
res_init("PolySaw"); 
resspr_init();   
template_init();  
dbox_init();      

strcpy(filepath, "board");       /* suggested file name */
sprintf(version_string +strlen(version_string), " (%s)", __DATE__);

sprintf(filetypevarname, "%s$FT", "PolySaw");
os_read_var_val(filetypevarname, buffer, 16);
boardfiletype = (int)strtol(buffer, &endp, 16);
if (endp != buffer+3 || boardfiletype<0 || boardfiletype>0x3ff)
  werr(TRUE, "Bad filetype number, must be &000 to &3FF");
board_windefn = template_syshandle("board");

/* Create the main window, and declare its event handler */
if (!create_win(&board_wh, "board"))
  return FALSE; /* Window creation failed */

/* claim idle events for drag */

win_claim_idle_events(board_wh);
win_register_event_handler(board_wh, board_event_handler, 0);

/* create tools window */
if (!create_win(&tools_wh, "tools"))
  return FALSE; /* Window creation failed */
win_register_event_handler(tools_wh, tools_event_handler, 0);

/* Create the bar icon menu tree */
if (baricon_menu = menu_new("PolySaw", (char *)baricon_menu_entries), baricon_menu == NULL)
  return FALSE; /* Menu create failed */

/* Create the board menu tree */
if (board_menu = menu_new("Options", (char *)board_menu_entries), board_menu == NULL)
  return FALSE; /* Menu create failed */
/* attach to window */
if (!event_attachmenu(board_wh, board_menu, board_menuproc, 0))
  return FALSE; /* Unable to attach menu */

/* Set up the icon on the icon bar, and declare its event handlers */
baricon("!PolySaw", (int)resspr_area(), baricon_click);
if (!event_attachmenu(win_ICONBAR, baricon_menu, baricon_menuproc, 0))
  return FALSE; /* Unable to attach menu */

/* All went ok */
return TRUE;
}

/******************************* MAIN PROGRAM ********************************/

int main(void)
{
if (initialise())
  {
  while (TRUE)
    event_process();
  }
return 0;
}








