#ifndef DATA_H
#define DATA_H

#include <time.h>
#include <gtk/gtk.h>
#include <X11/X.h>

#define ENTRYLISTCOLUMNS 2
#define MAXLINELENGTH 1024
#define MAXOBSERVATIONS 64
#define POINTER "pointer"
#define FILEDIRECTORY ".gfocustimer"
#define FILESUFFIXNAMES "names"
#define FILESUFFIXPREFS "preferences"

enum headings   { HEADINGS_HIDDEN, HEADINGS_SHOWN };
enum format     { FORMAT_HH_MM, FORMAT_HH_MM_SS, FORMAT_H_HH, FORMAT_H_HHHH };
enum totals     { TOTALS_HIDDEN, TOTALS_SHOWN };
enum unknown_do { UNKNOWN_DO_CURRENT, UNKNOWN_DO_TOP };
enum connect_do { CONNECT_DO_BEEP, CONNECT_DO_BE_SILENT };
enum save_do    { SAVE_DO_OFF, SAVE_DO_ON };
enum lock_do    { LOCK_DO_NOTHING, LOCK_DO_STOP_CHARGING, LOCK_DO_CHARGE_TOP };
enum icon_do    { ICON_DO_ME, ICON_DO_NAME, ICON_DO_TOTAL };
enum project_do { PROJECT_DO_NOTHING, PROJECT_DO_NAME };

/* preferences data */
struct pd
{
  /* front panel buttons */
  int charging;
  int watching;

  /* display format */
  enum headings headings;
  enum format format;
  enum totals totals;

  /* focus watching */
  int focus_rate;		/* milliseconds		*/
  enum unknown_do unknown_do;
  enum connect_do connect_do;
  int connect_time;		/* milliseconds		*/

  /* automatic save */
  enum save_do save_do;
  int save_rate;		/* minutes		*/

  /* check lock */
  enum lock_do lock_do;
  int lock_ignore_time;		/* minutes		*/

  /* miscellaneous */
  enum icon_do icon_do;
  enum project_do project_do;

};

/* entry data */
struct ed
{
  GList *node;	/* list node back pointer	*/
  int row;	/* which row on clist this is	*/
  char *name;	/* the entry name (heap)	*/
  time_t time;	/* the time charged to entry	*/
};

/* window focus data */
struct wd
{
  Window window;	/* XID of the window, binary tree key	*/
  struct ed *ed;	/* pointer to connected entry data	*/
  time_t connected;	/* date time that this connected done	*/
  char *name;		/* last known name for the window	*/
};

/* observation data */
struct od
{
  enum od_type
  {
    OD_MANUAL,		/* user clicked on an entry		*/
    OD_FOCUS,		/* focus changed on screen		*/
    OD_EXTERNAL		/* an external event occurred		*/
  } type;
  GList *node;		/* list node back pointer		*/
  time_t start;		/* time this interval started		*/
  time_t value;		/* number of seconds in this interval	*/
  struct ed *ed;	/* the entry interval was charged to	*/
  union {
    struct od_focus
    {
      Window window;	/* XID of the window			*/
      char *name;	/* name of window at the time (HEAP)    */
			/* why do we duplicate the name here?	*/
			/* ... because some windows change name */
      struct wd *wd;	/* OPTIONAL pointer to known window	*/
    } focus;
    struct od_external
    {
      char *name;	/* external event name (HEAP)		*/
    } external;
  } un;
};

/* main window */
struct mw
{
  GtkWidget		*widget;	/* Main dialog widget	*/
  GtkMenuItem		*preferences;	/* File - Preferences	*/
  GtkMenuItem		*edit;		/* Entry - Edit		*/
  GtkMenuItem		*delete;	/* Entry - Delete	*/
  GtkCList		*list;		/* the list of entries	*/
  gint			row;		/* current selected row	*/
  struct ed		*ed;		/* current entry	*/
  struct ed		total;		/* total entry		*/
  GtkToggleButton	*charging;	/* Charge Time button	*/
  GtkToggleButton	*focus;		/* Watch Focus button	*/
  time_t		begin;		/* current charge begin	*/
  gboolean		charge;		/* charging state	*/
};

/* preferences window */
struct pw
{
  GtkWidget		*widget;
  GtkCList		*shortcuts;
};

/* entry windows */
struct ew
{
  GtkWidget		*widget;	/* entry dialog widget	*/
  int			creating;	/* is this a new entry?	*/
  gint			row;		/* if not, the row no.	*/
  struct ed		*ed;		/* & pointer to entry	*/
  time_t		time;		/* the saved time value	*/
};
#endif
