/* ** helpreader context sensitive help manager * */

#include "win.h"
#include "wimp.h"
#include "werr.h"
#include "kernel.h"
#include "swis.h"

#include <string.h>
#include <stdio.h>

/* ********************************************** */

#define MSG_HERE  0xC3A80
#define MSG_WHERE 0xC3A81
#define MSG_CLOSE 0xC3A82
#define MSG_MOVE  0xC3A83
#define MSG_FRONT 0xC3A84

#define MSG_TASKCLOSEDOWN 0x400c3

#define HANDLE 0
#define MAGIC  1
#define NAME   8
#define MOVETO 0 

#define MOVETO_DATA_SIZE 12

/* ********************************************** */

static char _helpreader_listenfor[36];
static int  _helpreader_initialised = FALSE;
static int  _helpreader_handle = -1;
static int  _helpreader_magicn;

/* ********************************************** */

void helpreader_helptext_to_front(void)
{
  wimp_msgstr msg;

  if(_helpreader_initialised == FALSE)
    werr(1, "HelpReader context sensitive help: Not initialised");

  if(_helpreader_handle == -1)
    return;

  msg.hdr.size = sizeof(wimp_msghdr) + MOVETO_DATA_SIZE;
  msg.hdr.action = MSG_FRONT;
  msg.data.words[MAGIC] = _helpreader_magicn;
  wimp_sendmessage(wimp_ESEND, &msg, _helpreader_handle);
}

void helpreader_load(char *taskname)
{
  char command[256];
  _kernel_swi_regs r;

  if(_helpreader_initialised == FALSE)
    werr(1, "HelpReader context sensitive help: Not initialised");

  if(_helpreader_handle == -1) {  /* then load the help file */
    sprintf(command, "Run <%s$Dir>.!Help", taskname);
    r.r[0] = (int)command;
    _kernel_swi(Wimp_StartTask, &r, &r);
  } else {   /* bring the helptext to the front of the window stack */
    helpreader_helptext_to_front();
  }
}

static void _helpreader_ask_whereis(void)
{
  wimp_msgstr msg;

  msg.hdr.size = sizeof(wimp_msghdr);
  msg.hdr.action = MSG_WHERE;
  wimp_sendmessage(wimp_ESEND, &msg, 0 /* broadcast */);
}

void helpreader_move(int to)
{
  wimp_msgstr msg;

  if(_helpreader_initialised == FALSE)
    werr(1, "HelpReader context sensitive help: Not initialised");
  if(_helpreader_handle == -1)
    return;

  msg.hdr.size = sizeof(wimp_msghdr) + MOVETO_DATA_SIZE;
  msg.hdr.action = MSG_MOVE;
  msg.data.words[MOVETO] = to;
  msg.data.words[MAGIC] = _helpreader_magicn;
  wimp_sendmessage(wimp_ESEND, &msg, _helpreader_handle);
}

static BOOL _helpreader_event_pro(wimp_eventstr *e, void *handle)
{
  handle = handle;

  if((e->e == wimp_ESEND || e->e == wimp_ESENDWANTACK)) {
    switch(e->data.msg.hdr.action) {
      case MSG_HERE:
        if(strcmp(&e->data.msg.data.chars[NAME], _helpreader_listenfor)==0) {
          _helpreader_handle = e->data.msg.data.words[HANDLE];
          _helpreader_magicn = e->data.msg.data.words[MAGIC];
        }
        return TRUE;
        break;

      case MSG_CLOSE:
        if(strcmp(&e->data.msg.data.chars[NAME], _helpreader_listenfor)==0) {
          _helpreader_handle = -1;
          _helpreader_ask_whereis();
        }
        return TRUE;
        break;

      case MSG_TASKCLOSEDOWN:
        if(e->data.msg.hdr.task == _helpreader_handle) {
          _helpreader_handle = -1;
          _helpreader_ask_whereis();
        }
        return FALSE;  /* someone else (in this program) might be interested
        break;            in this message...  */

      default:
        return FALSE;
        break; /* ? */
    }
  }

  return FALSE;
}

BOOL helpreader_init(char *listenfor)
{
  strcpy(_helpreader_listenfor, listenfor);

  win_add_unknown_event_processor(_helpreader_event_pro, 0);

  _helpreader_initialised = TRUE;

  _helpreader_ask_whereis();

  return TRUE;
}
