Logo Search packages:      
Sourcecode: vertex version File versions

vmainstall.c

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <gtk/gtk.h>
#include <gdk/gdkkeysyms.h>
#include <gdk/gdkx.h>

#include "../include/string.h"
#include "../include/disk.h"

#include "guiutils.h"
#include "cdialog.h"

#include "vmacfg.h"
#include "vmacfglist.h"
#include "vmainstall.h"
#include "vmainstallop.h"
#include "vma.h"
#include "vmautils.h"
#include "config.h"

#ifdef MEMWATCH
# include "memwatch.h"
#endif

#include "vertex.xpm"


/* Installer GTK+ structure. */
typedef struct {

      gchar *name;            /* Name of this page. */

      GtkWidget   *heading_parent,
                  *main_parent;

      GtkWidget **widget;     /* List of widgets on this page. */
      gint total_widgets;

} vma_installer_page_struct;

typedef struct {

      gbool initialized;
      gbool map_state;

      GtkAccelGroup     *accelgrp;

      GtkRcStyle  *rcstyle_main,
                  *rcstyle_heading,
                  *rcstyle_text_editable;

      GtkWidget   *toplevel,
                  *heading_eb,
                  *heading_vbox,
                  *main_eb,
                  *main_vbox,
                  *buttons_eb;

      GtkWidget   *next_btn, *next_btn_label,
                  *prev_btn, *prev_btn_label;

      /* Current page and total number of pages. */
      gint current_page, total_pages;

      /* Page data structures, size indicated total_pages. */
      vma_installer_page_struct *page;

      /* Page change callback. */
        void (*page_change_cb)(
                gpointer, gint, gint, gpointer
        );

} vma_installer_struct;


static gint vma_gtk_main_level;
static gint vma_install_end_code;   /* 0 = cancel, 1 = success. */


/* Installer GTK+ builders and callbacks. */
static void VMAInstallerUpdatePageWidgets(
        vma_installer_struct *inst, gint prev_page, gint new_page
);
static GtkWidget *VMAInstallerGetPageParentHeading(
        vma_installer_struct *inst, gint page_num
);
static GtkWidget *VMAInstallerGetPageParentMain(
        vma_installer_struct *inst, gint page_num
);
static void VMAInstallerNextPageCB(GtkWidget *widget, gpointer data);
static void VMAInstallerPrevPageCB(GtkWidget *widget, gpointer data);
static gint VMAInstallerCloseCB(
      GtkWidget *widget, GdkEvent *event, gpointer data
);
static vma_installer_struct *VMAInstallerNew(
      const gchar *title, gint total_pages,
      void (*page_change_cb)(
            gpointer, gint, gint, gpointer
      )
);
static int VMAInstallerAddWidget(
        vma_installer_struct *inst, gint page_num, GtkWidget *w
);
/*
static GtkWidget *VMAInstallerGetWidget(
        vma_installer_struct *inst, gint page_num, gint i
);
 */
static void VMAInstallerDelete(vma_installer_struct *inst);


/* Install/upgrade page change callbacks. */
static void VMAInstallUpgradePageChangeCB(
        gpointer i, gint prev_page, gint new_page,
        gpointer data
);
static void VMAInstallPageChangeCB(
        gpointer i, gint prev_page, gint new_page,
        gpointer data
);

/* Install/upgrade front ends. */
int VMADoInstallUpgrade(
        int *argc, char ***argv,
        const char *preferences, vma_cfg_item_struct *parm_list
);
int VMADoInstall(
        int *argc, char ***argv,
      const char *preferences, vma_cfg_item_struct *parm_list
);


#define RADTODEG(r)     ((r) * 180 / PI)
#define DEGTORAD(d)     ((d) * PI / 180)

#define MAX(a,b)        (((a) > (b)) ? (a) : (b))
#define MIN(a,b)        (((a) < (b)) ? (a) : (b))
#define CLIP(a,l,h)     (MIN(MAX((a),(l)),(h)))


#define VMA_INSTALLER_TITLE         (PROG_NAME)
#define VMA_INSTALLER_WIDTH         500
#define VMA_INSTALLER_HEIGHT        400
#define VMA_INSTALLER_BANNER_HEIGHT 60    /* For header and footer. */


/*
 *    Installer GTK+ page change procedure.
 *
 *    Unmaps widgets on the old page and remaps the widgets on
 *    the new page.
 */
static void VMAInstallerUpdatePageWidgets(
      vma_installer_struct *inst, gint prev_page, gint new_page
)
{
      GtkWidget *w;
      vma_installer_page_struct *page;

      if(inst == NULL)
          return;
      if(inst->total_pages <= 0)
          return;
      /* Sanitize previous page number. */
      if(prev_page >= inst->total_pages)
           prev_page = inst->total_pages - 1;
      if(prev_page < 0)
          prev_page = 0;
      /* Sanitize new page number. */
        if(new_page >= inst->total_pages)
            new_page = inst->total_pages - 1;
        if(new_page < 0)
            new_page = 0;

      /* Unmap parent widgets on previous page. */
      page = &inst->page[prev_page];
      if(new_page != prev_page)
      {
          w = page->heading_parent;
          if(w != NULL)
            gtk_widget_hide(w);
          w = page->main_parent;
          if(w != NULL)
            gtk_widget_hide(w);
      }

      /* Map parent widgets on new page. */
      page = &inst->page[new_page];
        w = page->heading_parent;
        if(w != NULL)
            gtk_widget_show(w);
        w = page->main_parent;
        if(w != NULL)
            gtk_widget_show(w);

      return;
}

/*
 *      Returns pointer to a vbox that is the given page parent for the
 *    heading widgets.
 */
static GtkWidget *VMAInstallerGetPageParentHeading(
        vma_installer_struct *inst, gint page_num
)
{
        vma_installer_page_struct *page;

        if(inst == NULL)
            return(NULL); 

        if((page_num < 0) || (page_num >= inst->total_pages))
            return(NULL);

        page = &inst->page[page_num];
        return(page->heading_parent);
} 

/*
 *      Returns pointer to a vbox that is the given page parent for the
 *      heading widgets.
 */
static GtkWidget *VMAInstallerGetPageParentMain(
        vma_installer_struct *inst, gint page_num
)
{
      vma_installer_page_struct *page;

      if(inst == NULL)
          return(NULL);

      if((page_num < 0) || (page_num >= inst->total_pages))
          return(NULL);

      page = &inst->page[page_num];
      return(page->main_parent);
}

/*
 *    Installer GTK+ next page callback.
 */
static void VMAInstallerNextPageCB(GtkWidget *widget, gpointer data)
{
      gint prev_page;
      GtkWidget *w;
        vma_installer_struct *inst = (vma_installer_struct *)data;
        if(inst == NULL)
            return;

        prev_page = inst->current_page;
        inst->current_page++;

        /* Update button labels. */ 
        w = inst->next_btn_label;
        if(w != NULL)
        {
            const gchar *cstrptr = ((inst->current_page >= (inst->total_pages - 1)) ?
                "Finish" : "Next >>"
            );
            gtk_label_set_text(GTK_LABEL(w), cstrptr);
        }
        w = inst->prev_btn_label;
        if(w != NULL)
        {     
            const gchar *cstrptr = ((inst->current_page <= 0) ?
                "Cancel" : "<< Back"
            );
            gtk_label_set_text(GTK_LABEL(w), cstrptr);
        }

      VMAInstallerUpdatePageWidgets(inst, prev_page, inst->current_page);


      /* Call page change callback. */
      if(inst->page_change_cb != NULL)
          inst->page_change_cb(
            (gpointer)inst,
            prev_page, inst->current_page,
            NULL
          );

      /* Going past last page? */
        if(inst->current_page >= inst->total_pages)
        {
            inst->current_page = inst->total_pages - 1;

            /* Update install end code to indicate user finished. */
            vma_install_end_code = 1;

            /* Break out of the GTK+ main loop. */
            if(vma_gtk_main_level > 0)
            {
                vma_gtk_main_level--;
                gtk_main_quit();
            }
        }

      return;
}

/*
 *      Installer GTK+ previous page callback.
 */
static void VMAInstallerPrevPageCB(GtkWidget *widget, gpointer data)
{
      gint prev_page;
      GtkWidget *w;
      vma_installer_struct *inst = (vma_installer_struct *)data;
      if(inst == NULL)
          return;

        prev_page = inst->current_page;
        inst->current_page--;

        /* Update button labels. */
        w = inst->next_btn_label;
        if(w != NULL)
        {
            const gchar *cstrptr = ((inst->current_page >= (inst->total_pages - 1)) ?
            "Finish" : "Next >>"
          );
          gtk_label_set_text(GTK_LABEL(w), cstrptr);
        }
        w = inst->prev_btn_label;
        if(w != NULL)
        {
            const gchar *cstrptr = ((inst->current_page <= 0) ?
                "Cancel" : "<< Back"
            );
            gtk_label_set_text(GTK_LABEL(w), cstrptr);
        }

        VMAInstallerUpdatePageWidgets(inst, prev_page, inst->current_page);


        /* Call page change callback. */
        if(inst->page_change_cb != NULL)
            inst->page_change_cb(
                (gpointer)inst,
                prev_page, inst->current_page,
                NULL
            );

        /* Going past first page? */
        if(inst->current_page < 0)
        {
            inst->current_page = 0;

          /* Update install end code to indicate user canceled. */
          vma_install_end_code = 0;

            /* Break out of the GTK+ main loop. */
          if(vma_gtk_main_level > 0)
          {
            vma_gtk_main_level--;
            gtk_main_quit();
          }
        }

      return;
}

/*
 *    Installer GTK+ close event callback.
 */
static gint VMAInstallerCloseCB(
        GtkWidget *widget, GdkEvent *event, gpointer data
)
{
        vma_installer_struct *inst = (vma_installer_struct *)data;
        if(inst == NULL)
            return(FALSE);

        /* Call page change callback. */
        if(inst->page_change_cb != NULL)
            inst->page_change_cb(
                (gpointer)inst,
                inst->current_page, /* Use current page as prev page. */
            -1,               /* New page is -1, to indicate cancel. */
                NULL
            );

        /* Update install end code to indicate user canceled. */
        vma_install_end_code = 0;

        /* Break out of the GTK+ main loop. */
        if(vma_gtk_main_level > 0)
        {
            vma_gtk_main_level--;
            gtk_main_quit();
        }

        return(TRUE);
}       

/*
 *    Allocates and builds a new installer and maps it
 */
static vma_installer_struct *VMAInstallerNew(
      const gchar *title, gint total_pages,
      void (*page_change_cb)(
            gpointer, gint, gint, gpointer
      )
)
{
      gint  bw = (80 + (2 * 3)),
            bh = (30 + (2 * 3));
      gint  border_major = 5,
            border_minor = 2;
      GdkColor *c;
      GtkRcStyle *rcstyle;
      GtkAccelGroup *accelgrp;
      GdkWindow *window, *root;
      GtkWidget *w, *parent, *parent2, *parent3;
      vma_installer_struct *inst = (vma_installer_struct *)calloc(
          1, sizeof(vma_installer_struct)
      );
      if(inst == NULL)
          return(NULL);


      /* Reset values. */
      inst->initialized = TRUE;
      inst->map_state = FALSE;
      inst->current_page = 0;
      inst->total_pages = total_pages;
      inst->page_change_cb = page_change_cb;


      /* Create RcStyles. */

      /* Heading style. */
      rcstyle = gtk_rc_style_new();
      /* Color flags. */
      rcstyle->color_flags[GTK_STATE_NORMAL] = GTK_RC_FG;
        rcstyle->color_flags[GTK_STATE_ACTIVE] = GTK_RC_FG;
        rcstyle->color_flags[GTK_STATE_PRELIGHT] = GTK_RC_FG;
        rcstyle->color_flags[GTK_STATE_SELECTED] = GTK_RC_FG | GTK_RC_BG;
        rcstyle->color_flags[GTK_STATE_INSENSITIVE] = GTK_RC_FG;
      /* Color values. */
      c = &rcstyle->fg[GTK_STATE_NORMAL];
      c->red = 1.0 * (guint16)-1;
      c->green = 1.0 * (guint16)-1;
        c->blue = 1.0 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_ACTIVE];
        c->red = 1.0 * (guint16)-1;
        c->green = 1.0 * (guint16)-1;
        c->blue = 1.0 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_PRELIGHT];
        c->red = 1.0 * (guint16)-1;
        c->green = 1.0 * (guint16)-1;
        c->blue = 1.0 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_SELECTED];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 0.0 * (guint16)-1;
        c = &rcstyle->bg[GTK_STATE_SELECTED];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 1.0 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_INSENSITIVE];
        c->red = 0.84 * (guint16)-1;
        c->green = 0.84 * (guint16)-1;
        c->blue = 0.84 * (guint16)-1;
      inst->rcstyle_heading = rcstyle;

      /* Main style. */
        rcstyle = gtk_rc_style_new();
      /* Color flags. */
        rcstyle->color_flags[GTK_STATE_NORMAL] = GTK_RC_FG;
        rcstyle->color_flags[GTK_STATE_ACTIVE] = GTK_RC_FG;
        rcstyle->color_flags[GTK_STATE_PRELIGHT] = GTK_RC_FG;
        rcstyle->color_flags[GTK_STATE_SELECTED] = GTK_RC_FG | GTK_RC_BG;
        rcstyle->color_flags[GTK_STATE_INSENSITIVE] = GTK_RC_FG;
      /* Color values. */
        c = &rcstyle->fg[GTK_STATE_NORMAL];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 0.0 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_ACTIVE];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 0.0 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_PRELIGHT];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 0.0 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_SELECTED];
        c->red = 1.0 * (guint16)-1;
        c->green = 1.0 * (guint16)-1;
        c->blue = 1.0 * (guint16)-1;
        c = &rcstyle->bg[GTK_STATE_SELECTED];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 0.5 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_INSENSITIVE];
        c->red = 0.84 * (guint16)-1;
        c->green = 0.84 * (guint16)-1;
        c->blue = 0.84 * (guint16)-1;
      inst->rcstyle_main = rcstyle;

      /* Editable text style. */
        rcstyle = gtk_rc_style_new();
      /* Font name. */
      g_free(rcstyle->font_name);
      rcstyle->font_name = g_strdup(VMA_GTK_FONT_NAME_TEXT_LICENSE);
      /* Colors. */
        rcstyle->color_flags[GTK_STATE_NORMAL] = GTK_RC_FG;
        rcstyle->color_flags[GTK_STATE_ACTIVE] = GTK_RC_FG;
        rcstyle->color_flags[GTK_STATE_PRELIGHT] = GTK_RC_FG;
        rcstyle->color_flags[GTK_STATE_SELECTED] = GTK_RC_FG | GTK_RC_BG;
        rcstyle->color_flags[GTK_STATE_INSENSITIVE] = GTK_RC_FG | GTK_RC_BG;
      /* Color values. */
        c = &rcstyle->fg[GTK_STATE_NORMAL];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 0.0 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_ACTIVE];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 0.0 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_PRELIGHT];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 0.0 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_SELECTED];
        c->red = 1.0 * (guint16)-1;
        c->green = 1.0 * (guint16)-1;
        c->blue = 1.0 * (guint16)-1;
        c = &rcstyle->bg[GTK_STATE_SELECTED];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 0.5 * (guint16)-1;
        c = &rcstyle->fg[GTK_STATE_INSENSITIVE];
        c->red = 0.0 * (guint16)-1;
        c->green = 0.0 * (guint16)-1;
        c->blue = 0.0 * (guint16)-1;
        c = &rcstyle->bg[GTK_STATE_INSENSITIVE];
        c->red = 0.5 * (guint16)-1;
        c->green = 0.5 * (guint16)-1;
        c->blue = 0.5 * (guint16)-1;
        inst->rcstyle_text_editable = rcstyle;

      rcstyle = NULL;


      /* Keyboard accelerator group. */
      inst->accelgrp = accelgrp = gtk_accel_group_new();

        /* Toplevel. */
        inst->toplevel = w = gtk_window_new(GTK_WINDOW_DIALOG);
      gtk_widget_set_usize(w, VMA_INSTALLER_WIDTH, VMA_INSTALLER_HEIGHT);
        gtk_widget_realize(w);
      if(title != NULL)
          gtk_window_set_title(GTK_WINDOW(w), title);
        window = w->window;
      root = GDK_ROOT_PARENT();
        if(window != NULL)
        {
            gdk_window_set_decorations(
                window,
                GDK_DECOR_TITLE | GDK_DECOR_MENU | GDK_DECOR_MINIMIZE
            );
            gdk_window_set_functions(
                window,
                GDK_FUNC_MOVE | GDK_FUNC_MINIMIZE | GDK_FUNC_CLOSE
            );
          GUISetWMIcon(window, (u_int8_t **)vertex_xpm);
          if(root != NULL)
          {
                gint rx, ry, rw, rh, rd;

                gdk_window_get_geometry(
                    root, &rx, &ry, &rw, &rh, &rd
                );
                gtk_widget_set_uposition(
                    w,
                    (rw / 2) - (w->allocation.width / 2),
                    (rh / 2) - (w->allocation.height / 2)
                );
          }
        }
        gtk_signal_connect(
            GTK_OBJECT(w), "delete_event",
            GTK_SIGNAL_FUNC(VMAInstallerCloseCB),
            (gpointer)inst
        );
      gtk_accel_group_attach(accelgrp, GTK_OBJECT(w));
        gtk_container_border_width(GTK_CONTAINER(w), 0);
      parent = w;


        /* Main vbox. */
        w = gtk_vbox_new(FALSE, 0);
        gtk_container_add(GTK_CONTAINER(parent), w);
        gtk_widget_realize(w);
        gtk_widget_show(w);
        parent = w;

      /* Heading event box. */
      inst->heading_eb = w = gtk_event_box_new();
        gtk_widget_set_usize(w, -1, VMA_INSTALLER_BANNER_HEIGHT);
        gtk_box_pack_start(GTK_BOX(parent), w, FALSE, FALSE, 0);
/*    gtk_widget_realize(w); */
      gtk_widget_show(w);
      parent2 = w;
      /* RC style for heading event box. */
        rcstyle = gtk_rc_style_new();
        if(rcstyle != NULL)
        {
          const gchar *cstrptr = (const gchar *)PrefixPaths(
            VMADefaultDataGlobalDir(), VMA_DEF_INSTALLER_IMAGE_BG_HEADING
          );
          if(cstrptr != NULL)
          {
            g_free(rcstyle->bg_pixmap_name[GTK_STATE_NORMAL]);
            rcstyle->bg_pixmap_name[GTK_STATE_NORMAL] = g_strdup(cstrptr);
          }
          gtk_widget_modify_style(w, rcstyle);
          GUIRCStyleDeallocUnref(rcstyle);
            rcstyle = NULL;
      }
      /* Heading vbox. */
      inst->heading_vbox = w = gtk_vbox_new(FALSE, 0);
      gtk_container_add(GTK_CONTAINER(parent2), w);
      gtk_widget_show(w);


        /* Main event box. */
        inst->main_eb = w = gtk_event_box_new();
        gtk_box_pack_start(GTK_BOX(parent), w, TRUE, TRUE, 0);
/*    gtk_widget_realize(w); */
        gtk_widget_show(w);
      parent2 = w;
        /* RC style for heading event box. */
        rcstyle = gtk_rc_style_new();
        if(rcstyle != NULL)  
        {
            const gchar *cstrptr = (const gchar *)PrefixPaths(
                VMADefaultDataGlobalDir(), VMA_DEF_INSTALLER_IMAGE_BG_MAIN
            );
            if(cstrptr != NULL)
            { 
                g_free(rcstyle->bg_pixmap_name[GTK_STATE_NORMAL]);
                rcstyle->bg_pixmap_name[GTK_STATE_NORMAL] = g_strdup(cstrptr);
            }
            gtk_widget_modify_style(w, rcstyle);
            GUIRCStyleDeallocUnref(rcstyle);
            rcstyle = NULL;
        }
        /* Main vbox. */
        inst->main_vbox = w = gtk_vbox_new(FALSE, 0);
        gtk_container_add(GTK_CONTAINER(parent2), w);
        gtk_widget_show(w);


      /* Buttons event box. */
        inst->buttons_eb = w = gtk_event_box_new();
        gtk_widget_set_usize(w, -1, VMA_INSTALLER_BANNER_HEIGHT);
        gtk_box_pack_start(GTK_BOX(parent), w, FALSE, FALSE, 0);
/*    gtk_widget_realize(w); */
        gtk_widget_show(w);
        parent2 = w;
        /* RC style for heading event box. */
        rcstyle = gtk_rc_style_new();
        if(rcstyle != NULL)
        { 
            const gchar *cstrptr = (const gchar *)PrefixPaths(
                VMADefaultDataGlobalDir(), VMA_DEF_INSTALLER_IMAGE_BG_FOOTER
            );
            if(cstrptr != NULL)
            {
                g_free(rcstyle->bg_pixmap_name[GTK_STATE_NORMAL]);
                rcstyle->bg_pixmap_name[GTK_STATE_NORMAL] = g_strdup(cstrptr);
            }
            gtk_widget_modify_style(w, rcstyle);
            GUIRCStyleDeallocUnref(rcstyle);
            rcstyle = NULL;
        }

      w = gtk_alignment_new(1.0, 0.5, 0.0, 0.0);
        gtk_container_add(GTK_CONTAINER(parent2), w);
      gtk_widget_show(w);
        parent2 = w;

        w = gtk_hbox_new(TRUE, border_minor);
        gtk_container_add(GTK_CONTAINER(parent2), w);
      gtk_container_border_width(GTK_CONTAINER(w), border_major);
        gtk_widget_show(w);
        parent2 = w;

      /* Previous button. */
      inst->prev_btn = w = gtk_button_new();
      gtk_box_pack_start(GTK_BOX(parent2), w, TRUE, FALSE, 0);
      gtk_widget_set_usize(w, bw, bh);
        GTK_WIDGET_SET_FLAGS(w, GTK_CAN_DEFAULT);
        gtk_signal_connect(
            GTK_OBJECT(w), "clicked",          
            GTK_SIGNAL_FUNC(VMAInstallerPrevPageCB),
            (gpointer)inst
        );
        gtk_accel_group_add(
            accelgrp, GDK_Escape, 0, GTK_ACCEL_VISIBLE,
            GTK_OBJECT(w), "clicked"
        );
      gtk_widget_show(w);
      parent3 = w;

      inst->prev_btn_label = w = gtk_label_new(
            (inst->current_page > 0) ?  "<< Back" : "Cancel"
      );
      gtk_container_add(GTK_CONTAINER(parent3), w);
      gtk_widget_show(w);


        /* Next button. */
        inst->next_btn = w = gtk_button_new();
        gtk_box_pack_start(GTK_BOX(parent2), w, TRUE, FALSE, 0);
        gtk_widget_set_usize(w, bw, bh);
        GTK_WIDGET_SET_FLAGS(w, GTK_CAN_DEFAULT);
        gtk_signal_connect(
            GTK_OBJECT(w), "clicked",
            GTK_SIGNAL_FUNC(VMAInstallerNextPageCB),
            (gpointer)inst
        );
        gtk_accel_group_add(
            accelgrp, GDK_Return, 0, GTK_ACCEL_VISIBLE,
            GTK_OBJECT(w), "clicked"
        );
        gtk_accel_group_add(
            accelgrp, GDK_3270_Enter, 0, GTK_ACCEL_VISIBLE,
            GTK_OBJECT(w), "clicked"
        );
        gtk_accel_group_add(
            accelgrp, GDK_KP_Enter, 0, GTK_ACCEL_VISIBLE,
            GTK_OBJECT(w), "clicked"
        );
        gtk_accel_group_add(
            accelgrp, GDK_ISO_Enter, 0, GTK_ACCEL_VISIBLE,
            GTK_OBJECT(w), "clicked"
        );
        gtk_widget_show(w);
        parent3 = w;

        inst->next_btn_label = w = gtk_label_new(
          (inst->current_page < (inst->total_pages - 1)) ?  "Next >>" : "Finish"
      );
        gtk_container_add(GTK_CONTAINER(parent3), w);
        gtk_widget_show(w);


      /* Allocate and set up pages. */
      parent = inst->heading_vbox;
      parent2 = inst->main_vbox;
      if((inst->total_pages > 0) && (parent != NULL) && (parent2 != NULL))
      {
          gint page_num;
          vma_installer_page_struct *page;

          inst->page = (vma_installer_page_struct *)calloc(
            inst->total_pages,
            sizeof(vma_installer_page_struct)
          );
          if(inst->page == NULL)
          {
            inst->total_pages = 0;
          }
          /* Itterate through each new page, creating parents for
           * each page.
           */
          for(page_num = 0; page_num < inst->total_pages; page_num++)
          {
            page = &inst->page[page_num];

                w = gtk_vbox_new(TRUE, 0);
            gtk_box_pack_start(GTK_BOX(parent), w, TRUE, TRUE, 0);
            gtk_container_border_width(GTK_CONTAINER(w), border_major);
                page->heading_parent = w;

            w = gtk_vbox_new(FALSE, 0);
                gtk_box_pack_start(GTK_BOX(parent2), w, TRUE, TRUE, 0);
            gtk_container_border_width(GTK_CONTAINER(w), border_major);
            page->main_parent = w;
          }
      }
      else
      {
          inst->total_pages = 0;
      }



      /* Set next button as default. */
      w = inst->next_btn;
      if(w != NULL)
      {
          gtk_widget_grab_focus(w);
          gtk_widget_grab_default(w);
      }

      /* Map toplevel. */
      w = inst->toplevel;
      if(w != NULL)
      {
          gtk_widget_show(w);
          inst->map_state = TRUE;
      }

      return(inst);
}

/*
 *    Adds widget w to the installer's page specified by page_num.
 */
static int VMAInstallerAddWidget(
      vma_installer_struct *inst, gint page_num, GtkWidget *w
)
{
      gint n;
      vma_installer_page_struct *page;

      if((inst == NULL) || (w == NULL))
          return(-1);

      if((page_num < 0) || (page_num >= inst->total_pages))
          return(-1);

      page = &inst->page[page_num];
      if(page->total_widgets < 0)
          page->total_widgets = 0;
      n = page->total_widgets;
      page->total_widgets = n + 1;
      page->widget = (GtkWidget **)realloc(
          page->widget,
          page->total_widgets * sizeof(GtkWidget *)
      );
      if(page->widget == NULL)
      {
          page->total_widgets = 0;
          return(-1);
      }

      page->widget[n] = w;

      return(n);
}

/*
 *    Returns widget pointer to widget i, recorded on the given page.
 */
/*
static GtkWidget *VMAInstallerGetWidget(
        vma_installer_struct *inst, gint page_num, gint i
)
{
        vma_installer_page_struct *page;
 
        if(inst == NULL)
            return(NULL);

        if((page_num < 0) || (page_num >= inst->total_pages))
            return(NULL);

        page = &inst->page[page_num];
      if((i < 0) || (i >= page->total_widgets))
          return(NULL);

      return(page->widget[i]);
}
*/

/*
 *    Destroys all resources on the given installer inst and deallocates
 *    the given inst structure itself.
 */
static void VMAInstallerDelete(vma_installer_struct *inst)
{
      gint i;
      GtkWidget **w;
      GtkRcStyle **rcstyle;
      vma_installer_page_struct *page;


      if(inst == NULL)
          return;

#define DO_DESTROY_WIDGET     \
{ \
 if((*w) != NULL) \
 { \
  GtkWidget *tmp_w = (*w); \
  (*w) = NULL; \
  gtk_widget_destroy(tmp_w); \
 } \
}

#define DO_UNREF_RCSTYLE      \
{ \
 if((*rcstyle) != NULL) \
 { \
  GtkRcStyle *ts = (*rcstyle); \
  (*rcstyle) = NULL; \
  GUIRCStyleDeallocUnref(ts); \
 } \
}

      /* Destroy all widgets on each page. */
      for(i = 0; i < inst->total_pages; i++)
      {
          page = &inst->page[i];

          g_free(page->name);
          page->name = NULL;

          g_free(page->widget);
          page->widget = NULL;
          page->total_widgets = 0;

          w = &page->heading_parent;
          DO_DESTROY_WIDGET
            w = &page->main_parent;
            DO_DESTROY_WIDGET
      }
      g_free(inst->page);
      inst->page = NULL;
      inst->total_pages = 0;

        w = &inst->heading_vbox; 
        DO_DESTROY_WIDGET
      w = &inst->heading_eb;
      DO_DESTROY_WIDGET

        w = &inst->main_vbox; 
        DO_DESTROY_WIDGET
        w = &inst->main_eb;
        DO_DESTROY_WIDGET

        w = &inst->next_btn;
        inst->next_btn_label = NULL;
        DO_DESTROY_WIDGET

        w = &inst->prev_btn;
        inst->prev_btn_label = NULL;
        DO_DESTROY_WIDGET

        w = &inst->buttons_eb;
        DO_DESTROY_WIDGET

        w = &inst->toplevel;
        DO_DESTROY_WIDGET

      if(inst->accelgrp != NULL)
      {
            gtk_accel_group_unref(inst->accelgrp);
          inst->accelgrp = NULL;
      }

      rcstyle = &inst->rcstyle_heading;
      DO_UNREF_RCSTYLE
      rcstyle = &inst->rcstyle_main;
      DO_UNREF_RCSTYLE
      rcstyle = &inst->rcstyle_text_editable;
      DO_UNREF_RCSTYLE

#undef DO_DESTROY_WIDGET
#undef DO_UNREF_RCSTYLE

      /* Deallocate structure itself. */
      g_free(inst);
}



/*
 *    Upgrade procedure page change callback for the GTK+ installer.
 */
static void VMAInstallUpgradePageChangeCB(
      gpointer i, gint prev_page, gint new_page,
      gpointer data
)
{
      vma_installer_struct *inst = (vma_installer_struct *)i;
      if(inst == NULL)
          return;

      /* Handle by new page number. */
      switch(new_page)
      {
        case 0:

          break;

        case 1:

          break;

        case 2:
          if(prev_page < new_page)
          {
            /* Do upgrade scan. */





          }
          break;

        case -1:  /* Canceled. */
          CDialogSetTransientFor(inst->toplevel);
          CDialogGetResponse(
"Incomplete upgrade",
"Upgrade not complete, you will not be able\n\
to run this application.",
            NULL,
                CDIALOG_ICON_WARNING,
            CDIALOG_BTNFLAG_OK,
            CDIALOG_BTNFLAG_OK
          );
          CDialogSetTransientFor(NULL);
          break;

        case 3:   /* Finished. */

          break;
      }

      return;
}

/*
 *    Install procedure page change callback for the GTK+ installer.
 */
static void VMAInstallPageChangeCB(
      gpointer i, gint prev_page, gint new_page,
        gpointer data
)
{
        vma_installer_struct *inst = (vma_installer_struct *)i;
        if(inst == NULL)
            return;

        /* Handle by new page number. */
        switch(new_page)
        {
          case 0:
 
            break;

        case 1:

          break;

          case 2:
            if(prev_page < new_page)
            {
  
          
          
          
            } 
            break;

        case -1:  /* Canceled. */
            CDialogSetTransientFor(inst->toplevel);
            CDialogGetResponse(
"Incomplete installation",
"Installation not complete, you will not be able\n\
to run this application.",
                NULL,
                CDIALOG_ICON_WARNING,
                CDIALOG_BTNFLAG_OK,
                CDIALOG_BTNFLAG_OK
            );
            CDialogSetTransientFor(NULL);
            break;

          case 3:       /* Finished. */

            break;
        }

        return;
}



/*
 *    Upgrade main routine, may go into a GTK loop bug will
 *    shut down GTK resources that it allocates. Global initialized_gtk
 *    will be checked and updated accordingly.
 *
 *      -1      General error.
 *      -2      Missing data.
 *      -3      System error.
 *      -4      User aborted.
 */
int VMADoInstallUpgrade(
        int *argc, char ***argv,
        const char *preferences, vma_cfg_item_struct *parm_list
)
{
      gint page_num;
      const gchar *cstrptr;
      GtkWidget *w, *parent;
      vma_installer_struct *inst;
        gchar local_data_dir[PATH_MAX];  
      struct stat stat_buf;


        if(preferences == NULL)
            return(-1);
        if(parm_list == NULL)
            return(-1);

        if(!ISPATHABSOLUTE(preferences))
            return(-1);

        /* Need to initialize GTK+? */
        if(!initialized_gtk)
        {
            if(!gtk_init_check(argc, argv))
            {
                fprintf(
                    stderr,
 "This program requires X.\n"
                );
                return(-1);
            }
            initialized_gtk = TRUE;
        }

        /* Initialize gui resources, they should have not been
         * already initialized prior to calling this function.
         */
        CDialogInit();

      /* Initialize installer GTK+ resources. */
      vma_install_end_code = 0;
      inst = VMAInstallerNew(
          PROG_NAME " Version " PROG_VERSION " Upgrade",
          3,
          VMAInstallUpgradePageChangeCB
      );
      if(inst == NULL)
          return(-1);

/* Macro to shut down GUI resources that we allocated. */
#define DO_SHUTDOWN     \
{ \
 VMAInstallerDelete(inst); \
 CDialogShutdown(); \
}

        /* Check if global data directory exists. */
        cstrptr = (const gchar *)VMADefaultDataGlobalDir();
        if(stat(cstrptr, &stat_buf))
        {   
            /* Cannot install without global data directory. */
            gint len;  
            gchar *buf;
            
            len = (80 * 13) + strlen(cstrptr);
            buf = (gchar *)g_malloc((len + 1) * sizeof(gchar));
            if(buf != NULL)
                sprintf(buf,
"Cannot find the global data directory:\n\
\n\
    %s\n\
\n\
Make sure that you have installed the application\n\
properly. If you have installed the global data files\n\
to an alternate directory then you should set the\n\
environment variable:\n\
\n\
    %s\n\
\n\
to reffer to the alternate global data directory.",
                    cstrptr,
                    VMA_ENVNAME_DATA_GLOBAL_DIR
                );

            CDialogGetResponse(
"Cannot find directory!",
                buf,
                NULL,
                CDIALOG_ICON_ERROR,
                CDIALOG_BTNFLAG_OK | CDIALOG_BTNFLAG_HELP,
                CDIALOG_BTNFLAG_OK
            );

            g_free(buf);
            buf = NULL;

            DO_SHUTDOWN
            return(-1);
        }





        /* Get local data directory as the parent of the given preferences
         * file path.
         */
        cstrptr = (const gchar *)GetParentDir(preferences);
        if((cstrptr == NULL) ? 1 : ((*cstrptr) == '\0'))
        {
            /* Cannot install without local data directory. */
            CDialogGetResponse(
"Invalid Path!",
"Specified local configuration file path is\n\
invalid, unable to parse parent directory from\n\
it. Please make sure that the path is specified\n\
correctly.",
"The specified local configuration file path is\n\
not specified properly, its parent directory\n\
could not be determined. The parent directored\n\
is needed to know the installation location for\n\
local data files. Please make sure that the local\n\
configuration file path is specified correctly.",
                CDIALOG_ICON_WARNING,
                CDIALOG_BTNFLAG_OK | CDIALOG_BTNFLAG_HELP,
                CDIALOG_BTNFLAG_OK
            );

            DO_SHUTDOWN
            return(-1);
        }
        strncpy(local_data_dir, cstrptr, PATH_MAX); 
        local_data_dir[PATH_MAX - 1] = '\0';



      /* Create widgets for page 0 - license. */
        page_num = 0;
        parent = VMAInstallerGetPageParentHeading(inst, page_num);
        if(parent != NULL)
        {
            GtkWidget *parent2;

          w = gtk_hbox_new(FALSE, 0);
            gtk_box_pack_start(GTK_BOX(parent), w, TRUE, FALSE, 0);
            gtk_widget_show(w);
            parent2 = w;

            w = gtk_label_new(PROG_NAME " License Agreement");
            gtk_label_set_justify(GTK_LABEL(w), GTK_JUSTIFY_LEFT);
            gtk_widget_modify_style(w, inst->rcstyle_heading);
          gtk_box_pack_start(GTK_BOX(parent2), w, FALSE, FALSE, 85);
          gtk_widget_show(w);
        }
        parent = VMAInstallerGetPageParentMain(inst, page_num);
        if(parent != NULL)
        {     
            GtkWidget *parent2;
            GtkCList *clist;
            gchar *heading[1];
            gchar tmp_path[PATH_MAX + NAME_MAX];


            w = gtk_hbox_new(FALSE, 0);
            gtk_box_pack_start(GTK_BOX(parent), w, FALSE, FALSE, 0);
          gtk_widget_show(w);
            parent2 = w;

          /* Alignment to align to license clist to right side. */
          w = gtk_alignment_new(1.0, 0.5, 0.85, 1.0);
          gtk_box_pack_start(GTK_BOX(parent2), w, TRUE, TRUE, 0);
            gtk_widget_show(w);
            parent2 = w;

            w = gtk_scrolled_window_new(NULL, NULL);
            gtk_scrolled_window_set_policy(
                GTK_SCROLLED_WINDOW(w),
                GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC
            );
          gtk_container_add(GTK_CONTAINER(parent2), w);
          gtk_widget_show(w);
            parent2 = w;

            heading[0] = g_strdup("None");
            w = gtk_clist_new_with_titles(1, heading);
            clist = GTK_CLIST(w);
            g_free(heading[0]);  
            gtk_clist_column_titles_passive(clist);
            gtk_clist_column_titles_hide(clist);   
            gtk_clist_set_shadow_type(clist, GTK_SHADOW_IN);
            gtk_clist_set_selection_mode(clist, GTK_SELECTION_BROWSE);
            gtk_clist_set_column_width(clist, 0, 640);
            gtk_widget_set_usize(w, -1, 170);
          gtk_widget_modify_style(w, inst->rcstyle_text_editable);
            gtk_container_add(GTK_CONTAINER(parent2), w);
            VMAInstallerAddWidget(inst, page_num, w);   /* #0 */
          gtk_widget_show(w);
            /* Load license file to clist. */
            cstrptr = (const gchar *)PrefixPaths(
                VMADefaultDataGlobalDir(), VMA_DEF_FILE_LICENSE
            );
            if(cstrptr != NULL)
            {
                strncpy(tmp_path, cstrptr, PATH_MAX + NAME_MAX);
                tmp_path[PATH_MAX + NAME_MAX - 1] = '\0';
                
                gtk_clist_freeze(clist);
                VMATextFileToCList(
                    clist, tmp_path, NULL
                );
                gtk_clist_thaw(clist);
            }


            w = gtk_hbox_new(FALSE, 0);
            gtk_box_pack_start(GTK_BOX(parent), w, FALSE, FALSE, 0);
          gtk_widget_show(w);
            parent2 = w;

            w = gtk_label_new("\
BY CLICKING THE `NEXT' BUTTON OR INSTALLING OR USING\n\
VERTEX (THE \"PRODUCT\"), THE INDIVIDUAL OR ENTITY\n\
LICENSING THE PRODUCT (\"LICENSEE\") IS CONSENTING TO\n\
BE BOUND BY THE ABOVE AGREEMENT. OTHERWISE THE `BACK'\n\
OR `CANCEL' BUTTON MUST BE SELECTED."
            );
            gtk_label_set_justify(GTK_LABEL(w), GTK_JUSTIFY_LEFT);
            gtk_widget_modify_style(w, inst->rcstyle_main);
            gtk_box_pack_start(GTK_BOX(parent2), w, FALSE, FALSE, 85);
          gtk_widget_show(w);
        }

        /* Create widgets for page 1 - upgrade welcome. */
      page_num = 1;
      parent = VMAInstallerGetPageParentHeading(inst, page_num);
      if(parent != NULL)
        {
            GtkWidget *parent2;

            w = gtk_hbox_new(FALSE, 0);
            gtk_box_pack_start(GTK_BOX(parent), w, TRUE, FALSE, 0);
            gtk_widget_show(w);
            parent2 = w;

            w = gtk_label_new("\
Upgrade " PROG_NAME " Local Installation"
            );
            gtk_label_set_justify(GTK_LABEL(w), GTK_JUSTIFY_LEFT);
            gtk_widget_modify_style(w, inst->rcstyle_heading);
            gtk_box_pack_start(GTK_BOX(parent2), w, FALSE, FALSE, 85);
            gtk_widget_show(w);
      }
      parent = VMAInstallerGetPageParentMain(inst, page_num);
      if(parent != NULL)
      {
          gint old_version_major, old_version_minor;
          gchar *buf;
          int len;

            old_version_major = VMACFGItemListGetValueI(
                parm_list, VMA_CFG_PARM_VERSION_MAJOR
            );  
            old_version_minor = VMACFGItemListGetValueI(
                parm_list, VMA_CFG_PARM_VERSION_MINOR
            );

          len = (80 * 16) + strlen(preferences);
          buf = (char *)g_malloc((len + 1) * sizeof(char));
          if(buf != NULL)
          {
            sprintf(
                buf,
"Previous version specified by file:\n\
\n\
    %s\n\
\n\
Identifies the previous version of this application to be\n\
%i.%i.<r> where <r> is any release number. The new\n\
version of this application is %s.\n\
\n\
Your local data files for this application will be reviewed\n\
and then automatically updated (as needed) to suit the new\n\
version. To begin the upgrade process, click on the `Next'\n\
button.\n\
\n\
If you do not wish to upgrade your local data files, then click\n\
on the `Back' or `Cancel' button.",
                preferences, old_version_major, old_version_minor,
                PROG_VERSION
            );

            w = gtk_label_new(buf);
                gtk_widget_modify_style(w, inst->rcstyle_main);
            gtk_box_pack_start(GTK_BOX(parent), w, FALSE, FALSE, 0);
            gtk_label_set_justify(GTK_LABEL(w), GTK_JUSTIFY_LEFT);
                gtk_widget_show(w);

            g_free(buf);
            buf = NULL;
          }
      }


        /* Create widgets for page 2 - finish. */
        page_num = 2;
        parent = VMAInstallerGetPageParentHeading(inst, page_num);
        if(parent != NULL)
        {

        }
        parent = VMAInstallerGetPageParentMain(inst, page_num);
        if(parent != NULL)
        {
          gchar *buf;
          gint len;

            len = (80 * 7);
            buf = (char *)g_malloc((len + 1) * sizeof(char));
            if(buf != NULL)
            {
            sprintf(
                buf,
"Check complete, there are no additional local data files\n\
that need to be installed. Your configuration file will be\n\
updated to identify with the new version of %s.\n\
\n\
To proceed with the upgrade and start %s click on the\n\
`Finish' button.",
                PROG_NAME, PROG_NAME
            );

                w = gtk_label_new(buf);
                gtk_widget_modify_style(w, inst->rcstyle_main);
                gtk_box_pack_start(GTK_BOX(parent), w, FALSE, FALSE, 0);
                gtk_label_set_justify(GTK_LABEL(w), GTK_JUSTIFY_LEFT);
                gtk_widget_show(w);

                g_free(buf);
                buf = NULL;
            }
      }

      /* Done creating pages, now change to first page. */
      inst->current_page = 0;
      VMAInstallerUpdatePageWidgets(inst, -1, inst->current_page);

      /* Reset vma_gtk_main_level and enter GTK+ main loop. */
      vma_gtk_main_level = 1;
      gtk_main();

        /* Flush GTK+ events. */
        while(gtk_events_pending() > 0)
            gtk_main_iteration();

        /* Shutdown GTK+ resources. */
      DO_SHUTDOWN
#undef DO_SHUTDOWN

      /* Return by install end code. */
      if(vma_install_end_code)
          return(0);
      else
          return(-4);
}

/*
 *    Installation main routine, may go into a GTK loop but will
 *    shut down GTK resources that it allocates. Global initialized_gtk
 *    will be checked and updated accordingly.
 *
 *    The given preferences file must be a full path, its parent
 *    directory will be taken as the local data path and will be
 *    created if it does not exist.
 *
 *    The given configuration options list will be set up to default
 *    values.
 *
 *    Returns 0 on success or non-zero on error, possible error codes
 *    are as follows:
 *
 *    -1    General error.
 *    -2    Missing data.
 *    -3    System error.
 *    -4    User aborted.
 */
int VMADoInstall(
      int *argc, char ***argv,
      const char *preferences, vma_cfg_item_struct *parm_list
)
{
      gint page_num;
      GtkWidget *w, *parent;
      const gchar *cstrptr;
      vma_installer_struct *inst;
      gchar local_data_dir[PATH_MAX];
      struct stat stat_buf;


      if(preferences == NULL)
          return(-1);
      if(parm_list == NULL)
          return(-1);

      if(!ISPATHABSOLUTE(preferences))
          return(-1);

      /* Need to initialize GTK? */
      if(!initialized_gtk)
      {
          if(!gtk_init_check(argc, argv))
          {
            fprintf(
                stderr,
 "This program requires X.\n"
            );
            return(-1);
          }
          initialized_gtk = TRUE;
      }

      /* Initialize gui resources, they should have not been
       * already initialized prior to calling this function.
       */
      CDialogInit();

        /* Initialize installer GTK+ resources. */
        vma_install_end_code = 0;
        inst = VMAInstallerNew(
            PROG_NAME " Version " PROG_VERSION " Local Installation",
            3,
            VMAInstallPageChangeCB
        );
        if(inst == NULL)
            return(-1);

/* Macro to shut down GUI resources that we allocated. */
#define DO_SHUTDOWN     \
{ \
 VMAInstallerDelete(inst); \
 CDialogShutdown(); \
}

      /* Check if global data directory exists. */
      cstrptr = (const gchar *)VMADefaultDataGlobalDir();
      if(stat(cstrptr, &stat_buf))
      {
            /* Cannot install without global data directory. */
          gint len;
          gchar *buf;

          len = (80 * 13) + strlen(cstrptr);
          buf = (gchar *)g_malloc((len + 1) * sizeof(gchar));
          if(buf != NULL)
            sprintf(buf,
"Cannot find the global data directory:\n\
\n\
    %s\n\
\n\
Make sure that you have installed the application\n\
properly. If you have installed the global data files\n\
to an alternate directory then you should set the\n\
environment variable:\n\
\n\
    %s\n\
\n\
to reffer to the alternate global data directory.",
                cstrptr,
                VMA_ENVNAME_DATA_GLOBAL_DIR
            );

            CDialogGetResponse(
"Cannot find directory!",
            buf,
            NULL,
                CDIALOG_ICON_ERROR,
                CDIALOG_BTNFLAG_OK | CDIALOG_BTNFLAG_HELP,
                CDIALOG_BTNFLAG_OK
            );

          g_free(buf);
          buf = NULL;

            DO_SHUTDOWN
            return(-1);
      }

      /* Get local data directory as the parent of the given preferences
       * file path.
       */
      cstrptr = (const gchar *)GetParentDir(preferences);
      if((cstrptr == NULL) ? 1 : ((*cstrptr) == '\0'))
      {
          /* Cannot install without local data directory. */
          CDialogGetResponse(
"Invalid Path!",
"Specified local configuration file path is\n\
invalid, unable to parse parent directory from\n\
it. Please make sure that the path is specified\n\
correctly.",
"The specified local configuration file path is\n\
not specified properly, its parent directory\n\
could not be determined. The parent directored\n\
is needed to know the installation location for\n\
local data files. Please make sure that the local\n\
configuration file path is specified correctly.",
                CDIALOG_ICON_WARNING,
                CDIALOG_BTNFLAG_OK | CDIALOG_BTNFLAG_HELP,
            CDIALOG_BTNFLAG_OK
            );

          DO_SHUTDOWN
          return(-1);
      }
      strncpy(local_data_dir, cstrptr, PATH_MAX);
      local_data_dir[PATH_MAX - 1] = '\0';


        /* Create widgets for page 0 - license. */
        page_num = 0;
        parent = VMAInstallerGetPageParentHeading(inst, page_num);
        if(parent != NULL)
        {       
            GtkWidget *parent2;

            w = gtk_hbox_new(FALSE, 0);
            gtk_box_pack_start(GTK_BOX(parent), w, TRUE, FALSE, 0);
            gtk_widget_show(w);
            parent2 = w;

            w = gtk_label_new(PROG_NAME " License Agreement");
            gtk_label_set_justify(GTK_LABEL(w), GTK_JUSTIFY_LEFT);
            gtk_widget_modify_style(w, inst->rcstyle_heading);
            gtk_box_pack_start(GTK_BOX(parent2), w, FALSE, FALSE, 85);
            gtk_widget_show(w);
        }
        parent = VMAInstallerGetPageParentMain(inst, page_num);
        if(parent != NULL)
        {
            GtkWidget *parent2;
            GtkCList *clist;
            gchar *heading[1];
            gchar tmp_path[PATH_MAX + NAME_MAX];


            w = gtk_hbox_new(FALSE, 0);
            gtk_box_pack_start(GTK_BOX(parent), w, FALSE, FALSE, 0);
            gtk_widget_show(w);
            parent2 = w;  

            /* Alignment to align to license clist to right side. */
            w = gtk_alignment_new(1.0, 0.5, 0.85, 1.0);
            gtk_box_pack_start(GTK_BOX(parent2), w, TRUE, TRUE, 0);
            gtk_widget_show(w);
            parent2 = w;

            w = gtk_scrolled_window_new(NULL, NULL);
            gtk_scrolled_window_set_policy(
                GTK_SCROLLED_WINDOW(w),
                GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC
            );
          gtk_container_add(GTK_CONTAINER(parent2), w);
            gtk_widget_show(w);
            parent2 = w;

            heading[0] = g_strdup("None");
            w = gtk_clist_new_with_titles(1, heading);
            clist = GTK_CLIST(w);
            g_free(heading[0]);
            gtk_clist_column_titles_passive(clist);
            gtk_clist_column_titles_hide(clist);
            gtk_clist_set_shadow_type(clist, GTK_SHADOW_IN); 
            gtk_clist_set_selection_mode(clist, GTK_SELECTION_BROWSE);
            gtk_clist_set_column_width(clist, 0, 640);
            gtk_widget_set_usize(w, -1, 170);
          gtk_widget_modify_style(w, inst->rcstyle_text_editable);
            gtk_container_add(GTK_CONTAINER(parent2), w);
            VMAInstallerAddWidget(inst, page_num, w);   /* #0 */
            gtk_widget_show(w);
            /* Load license file to clist. */
            cstrptr = (const gchar *)PrefixPaths(
                VMADefaultDataGlobalDir(), VMA_DEF_FILE_LICENSE
            );
            if(cstrptr != NULL)
            {
                strncpy(tmp_path, cstrptr, PATH_MAX + NAME_MAX);
                tmp_path[PATH_MAX + NAME_MAX - 1] = '\0';

                gtk_clist_freeze(clist);
                VMATextFileToCList(
                    clist, tmp_path, NULL
                );
                gtk_clist_thaw(clist); 
            }


            w = gtk_hbox_new(FALSE, 0);
            gtk_box_pack_start(GTK_BOX(parent), w, FALSE, FALSE, 0);
            gtk_widget_show(w);
            parent2 = w;

            w = gtk_label_new("\
BY CLICKING THE `NEXT' BUTTON OR INSTALLING OR USING\n\
VERTEX (THE \"PRODUCT\"), THE INDIVIDUAL OR ENTITY\n\
LICENSING THE PRODUCT (\"LICENSEE\") IS CONSENTING TO\n\
BE BOUND BY THE ABOVE AGREEMENT. OTHERWISE THE `BACK'\n\
OR `CANCEL' BUTTON MUST BE SELECTED."
            );
            gtk_label_set_justify(GTK_LABEL(w), GTK_JUSTIFY_LEFT);
            gtk_widget_modify_style(w, inst->rcstyle_main);
            gtk_box_pack_start(GTK_BOX(parent2), w, FALSE, FALSE, 85);
            gtk_widget_show(w);
        }

        /* Create widgets for page 1 - welcome. */
        page_num = 1;
        parent = VMAInstallerGetPageParentHeading(inst, page_num);
        if(parent != NULL)
        {
          GtkWidget *parent2;

            w = gtk_hbox_new(FALSE, 0);
            gtk_box_pack_start(GTK_BOX(parent), w, TRUE, FALSE, 0);
            gtk_widget_show(w);
            parent2 = w;

          w = gtk_label_new("\
Welcome to " PROG_NAME " version " PROG_VERSION "!"
          );
          gtk_label_set_justify(GTK_LABEL(w), GTK_JUSTIFY_LEFT);
          gtk_widget_modify_style(w, inst->rcstyle_heading);
          gtk_box_pack_start(GTK_BOX(parent2), w, FALSE, FALSE, 85);
            gtk_widget_show(w);
        }
        parent = VMAInstallerGetPageParentMain(inst, page_num);
        if(parent != NULL)
        {
            gchar *buf;
            int len;

            len = (80 * 12) + strlen(local_data_dir);
            buf = (char *)g_malloc((len + 1) * sizeof(char));
            if(buf != NULL)
          {
            sprintf(
                buf,
"Local data files will be installed in:\n\
\n\
    %s\n\
\n\
To proceed with the installation, click on the `Next' button.\n\
To abort installation, click on the `Back' button a few times.\n\
\n\
To install in an alternate location, abort installation and\n\
run this program again with the alternate location of the\n\
configuration file specified by the -f <configuration_file>\n\
argument from the command line. Example:\n\
\n\
vertex -f /home/someone/alternate_vertex/altvertex.ini",
                local_data_dir
            );

                w = gtk_label_new(buf);
                gtk_label_set_justify(GTK_LABEL(w), GTK_JUSTIFY_LEFT);
                gtk_widget_modify_style(w, inst->rcstyle_main);
                gtk_box_pack_start(GTK_BOX(parent), w, FALSE, FALSE, 0);
                gtk_widget_show(w);

                g_free(buf);
                buf = NULL;
            }
        }

        /* Create widgets for page 2 - preferences. */
        page_num = 2;
        parent = VMAInstallerGetPageParentHeading(inst, page_num);
        if(parent != NULL)
        {

        }
        parent = VMAInstallerGetPageParentMain(inst, page_num);
        if(parent != NULL)
        {
            w = gtk_label_new("\
There is now enough information to begin the local installation\n\
process.\n\
\n\
Afterwards you should take a moment to review the preferences\n\
by going to Edit->Preferences.\n\
\n\
To begin the installation process, click on the `Finish' button."
          );
          gtk_label_set_justify(GTK_LABEL(w), GTK_JUSTIFY_LEFT);
            gtk_widget_modify_style(w, inst->rcstyle_main);
          gtk_box_pack_start(GTK_BOX(parent), w, FALSE, FALSE, 0);
          gtk_widget_show(w);
      }


        /* Done creating pages, now change to first page. */
        inst->current_page = 0;
        VMAInstallerUpdatePageWidgets(inst, -1, inst->current_page);
 
        /* Reset vma_gtk_main_level and enter GTK+ main loop. */
        vma_gtk_main_level = 1;
        gtk_main();

        /* Flush GTK+ events. */
        while(gtk_events_pending() > 0)
            gtk_main_iteration();

      /* Proceed with actual installation if the installation end
       * code is a success.
       */
      if(vma_install_end_code)
      {


          /* Create local data directories, if this is successful then
           * the dname structure will be properly set after this call.
           */
          if(VMAInstallDefaultLocalDataDirs(local_data_dir))
          {
            /* Installation of directories failed. */
            DO_SHUTDOWN
            return(-2);
          }

          /* Reset given configuration options list to default
           * values.
           */
          VMAInstallDefaultPreferences(parm_list);
      }

        /* Shutdown GTK+ resources. */
        DO_SHUTDOWN
#undef DO_SHUTDOWN

        /* Return by install end code. */
        if(vma_install_end_code)
            return(0);
        else
            return(-4);
}

Generated by  Doxygen 1.6.0   Back to index