//
//  $Log: ui-MUI.c,v $
//  Revision 1.18  1994/03/24  09:58:19  hakan
//  MUI_Request-text verbessert
//
//  Revision 1.17  1994/02/22  23:46:10  hakan
//  Sollte soweit umgebaut sein.  Als nächstes bauen wir das Shell-interface
//
//  Revision 1.16  1994/02/05  21:51:15  hakan
//  Vor dem großen umbau
//
//  Revision 1.15  1993/11/01  21:52:13  hakan
//  Anzeige des aktuellen Hosts läuft über MUI_Messages die an den
//  lv-objekten hängen
//
//  Revision 1.14  1993/10/04  21:43:59  hakan
//  Keyboard Chains added
//
//  Revision 1.13  1993/10/04  21:27:37  hakan
//  Noch mehr defaultwerte
//
//  Revision 1.12  1993/10/04  21:25:46  hakan
//  Sinnvollerer Defaultwert für Save Path
//
//  Revision 1.11  1993/10/03  17:28:18  hakan
//  DiskObject and .guide-file added
//
//  Revision 1.10  1993/09/25  12:06:33  hakan
//  Preferences landen jetzt in ENV:Envoy statt ENV:Mui
//
//  Revision 1.9  1993/09/04  21:02:25  hakan
//  GUI sollte (fast) vollständig sein
//
//  Revision 1.8  1993/08/29  09:11:00  hakan
//  Onkel Peter hat mir geholfen, jetzt wird das UI de-windofized
//
//  Revision 1.7  1993/08/22  23:59:25  hakan
//  Zwischensave bevor ich struktur umbaue
//
//  Revision 1.6  1993/08/19  00:49:26  hakan
//  General-ci
//
//



#include <config.h>
#include <protoypes.h>

#include <ui-MUI.h>



static void Add (APTR list, char* string);
static VOID fail(APTR app,char *str);
static VOID create_app (VOID);
static void DecodeHost (Host* foo);
static void BuildNPConfiguration (void);
static void HandleCheckBox (APTR CheckBox, APTR StringGadget);


struct Library*     MUIMasterBase;
struct DiskObject	*dobj;
APTR MuiObjects [muiMax];

static struct NewMenu mnNetProbe[] =
{
    { NM_TITLE, "Project",          0,  0,  0,  0,},
    {  NM_ITEM, "About",           "?", 0,  0,  (void*) ID_ABOUT,},
    {  NM_ITEM, NM_BARLABEL,        0,  0,  0,  0,},
    {  NM_ITEM, "Save List",       "W", 0,  0,  (void*) ID_SAVE,},
    {  NM_ITEM, "Preferences...",  "P", 0,  0,  (void*) ID_PREFS,},
    {  NM_ITEM, NM_BARLABEL,        0,  0,  0,  0,},
    {  NM_ITEM, "Quit",            "Q", 0,  0,  (void*) ID_QUIT,},

    {   NM_END, 0,                  0,  0,  0,  0,},
};




void SetupUI (int argc, char* argv[])
{
    if (!(MUIMasterBase = OpenLibrary("muimaster.library", 3)))
        fail(NULL,"Failed to open muimaster.library.");

    create_app ();
}



void ShutDownUI (void)
{
    fail (MuiObjects[app],NULL);
}



static VOID fail(APTR app,char *str)
{
    if (dobj)
        FreeDiskObject (dobj);

    if (app)
        MUI_DisposeObject(app);

    if (MUIMasterBase)
        CloseLibrary(MUIMasterBase);

    if (str)
    {
        puts(str);
        exit(20);
    }

    exit(0);
}



static VOID create_app (VOID)
{
    char*   foo;
    long    exportid = 1;


    MuiObjects[winMain] = WindowObject,
        MUIA_Window_Title,  (getWindowVersionString()),
        MUIA_Window_ID   ,  MAKE_ID('M','A','I','N'),

        WindowContents, VGroup,
            //
            //  Obere Reihe der drei Gadgets
            //
            Child, HGroup,
                MUIA_Group_SameSize,    TRUE,

                Child, MuiObjects[btScanRealms]     = KeyButton ("Scan Realms", 'r'),
                Child, MuiObjects[btScanHosts]      = KeyButton ("Scan Hosts", 'h'),
                Child, MuiObjects[btScanAllHosts]   = KeyButton ("Scan All", 'a'),
                Child, MuiObjects[btQuit]           = KeyButton ("Quit", 'q'),

                End,


            //
            //  Mittlere Reihe der ListViews
            //
            Child, HGroup,
                Child, ColGroup (2),
                    MUIA_Group_SameSize, TRUE,

                    Child, HGroup,
                        Child, VGroup,

                            //
                            //  Realms
                            //
                            Child, MuiObjects[lvRealms] = ListviewObject,
                                MUIA_Weight, 50,
                                MUIA_Listview_List, ListObject,
                                    InputListFrame,
                                    End,
                                End,


                            //
                            //  Hosts
                            //
                            Child, MuiObjects[lvHosts] = ListviewObject,
                                MUIA_Weight, 200,
                                MUIA_Listview_List, ListObject,
                                    InputListFrame,
                                    End,
                                End,

                            End,
                        End,

                    Child, HGroup,
                        Child, VGroup,
                            ListViewWithKey(MuiObjects[cbServices],MuiObjects[lvServices],exportid++,'s',"Services"),
                            ListViewWithKey(MuiObjects[cbEntities],MuiObjects[lvEntities],exportid++,'e',"Entities"),
                            End,
                        End,
                    End,
                End,

                //  Child, RectangleObject, MUIA_Rectangle_HBar, TRUE, MUIA_FixHeight, 8, End,

                //
                //  Untere Reihe der Real-Important-Information-Gadgets
                //
                Child, ColGroup (3),

                    GadgetLine (MuiObjects[cbOwner],    MuiObjects[stOwner],    exportid++,'o', "Owner:"),
                    GadgetLine (MuiObjects[cbIPAddr],   MuiObjects[stIPAddr],   exportid++,'i', "IP-Addr"),
                    GadgetLine (MuiObjects[cbKickStart],MuiObjects[stKickStart],exportid++,'k', "Kickstart:"),
                    GadgetLine (MuiObjects[cbWorkbench],MuiObjects[stWorkbench],exportid++,'w', "Workbench:"),
                    GadgetLine (MuiObjects[cbNIPC],     MuiObjects[stNIPC],     exportid++,'n', "NIPC:"),
                    GadgetLine (MuiObjects[cbFastMem],  MuiObjects[stFastMem],  exportid++,'f', "Fast Memory:"),
                    GadgetLine (MuiObjects[cbChipMem],  MuiObjects[stChipMem],  exportid++,'y', "Chip Memory:"),
                    GadgetLine (MuiObjects[cbProcessor],MuiObjects[stProcessor],exportid++,'p', "Processor:"),
                    GadgetLine (MuiObjects[cbChips],    MuiObjects[stChips],    exportid++,'c', "Custom Chips:"),

                End,

            End,    //  WindowContents
        End;    //  WindowObject



    if (!MuiObjects[winMain])
        fail(MuiObjects[winMain], "Failed to create Main Window.");



    //
    //  We create our Preferences Window,  too
    //

    MuiObjects [winPrefs] = WindowObject,
        MUIA_Window_Title,  "NetProbe Preferences",
        MUIA_Window_ID,     MAKE_ID('P','R','F','S'),
        MUIA_Window_Menu,   MUIV_Window_Menu_NoMenu,

        WindowContents, VGroup,
            Child, ColGroup (2),
                Child, Label2 ("Max. Scan Time: "),
                Child, MuiObjects[stScanTime] = StringObject, StringFrame,
                    MUIA_String_MaxLen,     5,
                    MUIA_String_Format,     MUIV_String_Format_Left,
                    MUIA_String_Accept,     "0123456789",
                    MUIA_ExportID,          exportid++,
                End,

                Child, Label2 ("Max. Packets: "),
                Child, MuiObjects[stScanPackets] = StringObject, StringFrame,
                    MUIA_String_MaxLen,     5,
                    MUIA_String_Format,     MUIV_String_Format_Left,
                    MUIA_String_Accept,     "0123456789",
                    MUIA_ExportID,          exportid++,
                End,

                Child, Label1 ("Save file Path: "),
                Child, HGroup,
                    Child, MuiObjects[stSavePath] = StringObject, StringFrame,
                        MUIA_ExportID,          exportid++,
                    End,
                    Child, MuiObjects[btSavePath] = ImageObject, ImageButtonFrame,
                        MUIA_Image_Spec,            MUII_PopFile,
                        MUIA_Image_FontMatchWidth,  TRUE,
                        MUIA_Image_FreeVert,        TRUE,
                        MUIA_InputMode,             MUIV_InputMode_RelVerify,
                        MUIA_Background,            MUII_BACKGROUND,
                    End,
                End,

                Child, Label1 ("40.2-Kludge: "),
                Child, HGroup,
                    Child, MuiObjects[bt402Kludge] = KeyCheckmark (TRUE, 'k', exportid++),
                    Child, HSpace (0),
                End,

            End,

            Child, VSpace (0),

            Child, HGroup,
                MUIA_Group_SameSize, TRUE,

                Child, MuiObjects[btPrefsSave]      = KeyButton ("Save", 's'),
                Child, MuiObjects[btPrefsUse]       = KeyButton ("Use", 'u'),
                Child, MuiObjects[btPrefsCancel]    = KeyButton ("Cancel", 'c'),
            End,

        End,
    End;


    if (!MuiObjects[winPrefs])
        fail(MuiObjects[winPrefs], "Failed to create Preferences Window.");


    //
    //  We create our Preferences Window,  too
    //

    MuiObjects [winScan] = WindowObject,
        MUIA_Window_Title,  "NetProbe Scanning",
        MUIA_Window_ID,     MAKE_ID('S','C','A','N'),
        MUIA_Window_Menu,   MUIV_Window_Menu_NoMenu,

        WindowContents, VGroup,
            Child,
                ColGroup (3),
                    Child, HSpace (0),
                    Child, Label1 ("Scanning"),
                    Child, HSpace (0),
                End,

            Child, MuiObjects[fgScanTime] = GaugeObject,
                GaugeFrame,
                MUIA_Gauge_Horiz,   TRUE,
            End,

            Child, VSpace (0),

            Child, MuiObjects[btStopScan] = KeyButton ("Stop", 's'),
        End,
    End;


    if (!MuiObjects[winScan])
        fail(MuiObjects[winScan], "Failed to create Scan Window.");


    //
    //  Here goes the Application
    //

    MuiObjects[app] = ApplicationObject,
        MUIA_Application_Title,         "NetProbe",
        MUIA_Application_Version,       getVersTag (),
        MUIA_Application_Copyright,     "©1993,1994, Hakan Tandogan",
        MUIA_Application_Author,        "Hakan Tandogan",
        MUIA_Application_Description,   "Scans an Envoy Network",
        MUIA_Application_Base,          "NETPROBE",
        MUIA_Application_Menu,          mnNetProbe,
        MUIA_Application_DiskObject,    dobj = GetDiskObject ("PROGDIR:NetProbe"),
        MUIA_HelpFile,                  "NetProbe.guide",

        SubWindow, MuiObjects[winMain],
        SubWindow, MuiObjects[winPrefs],
        SubWindow, MuiObjects[winScan],

    End;


    if (!MuiObjects[app])
        fail(MuiObjects[app],"Failed to create Application.");


    //
    //  Keyboard chain to keep folks happy
    //

    DoMethod (MuiObjects[winMain], MUIM_Window_SetCycleChain,
        MuiObjects[btScanRealms],
        MuiObjects[btScanHosts],
        MuiObjects[btScanAllHosts],
        MuiObjects[btQuit],
        MuiObjects[lvRealms],
        MuiObjects[lvHosts],
        NULL );

    DoMethod (MuiObjects[winPrefs], MUIM_Window_SetCycleChain,
        MuiObjects[stScanTime],
        MuiObjects[stScanPackets],
        MuiObjects[stSavePath],
        MuiObjects[btSavePath],
        MuiObjects[btPrefsSave],
        MuiObjects[btPrefsUse],
        MuiObjects[btPrefsCancel],
        NULL );

    DoMethod (MuiObjects[winScan], MUIM_Window_SetCycleChain,
        MuiObjects[btStopScan],
        NULL );
        

    //        
    //  Diz be me active object
    //
    
    set (MuiObjects[winMain], MUIA_Window_ActiveObject, MuiObjects[lvHosts]);


    //
    //  Install notification events...
    //

    DoMethod(MuiObjects[winMain], MUIM_Notify, MUIA_Window_CloseRequest, TRUE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_QUIT);

    DoMethod(MuiObjects[btScanRealms], MUIM_Notify, MUIA_Pressed, FALSE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_SCAN_REALMS);

    DoMethod(MuiObjects[btScanHosts], MUIM_Notify, MUIA_Pressed, FALSE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_SCAN_HOSTS);

    DoMethod(MuiObjects[btScanAllHosts], MUIM_Notify, MUIA_Pressed, FALSE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_SCAN_ALL_HOSTS);

    DoMethod(MuiObjects[btQuit], MUIM_Notify, MUIA_Pressed, FALSE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_QUIT);

    DoMethod(MuiObjects[winPrefs], MUIM_Notify, MUIA_Window_CloseRequest, TRUE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_PREFS_QUIT);

    DoMethod(MuiObjects[btPrefsSave], MUIM_Notify, MUIA_Pressed, TRUE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_PREFS_SAVE);

    DoMethod(MuiObjects[btPrefsUse], MUIM_Notify, MUIA_Pressed, TRUE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_PREFS_USE);

    DoMethod(MuiObjects[btPrefsCancel], MUIM_Notify, MUIA_Pressed, TRUE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_PREFS_QUIT);

    DoMethod(MuiObjects[btSavePath], MUIM_Notify, MUIA_Pressed, TRUE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_PREFS_ASLREQ);

    DoMethod(MuiObjects[btStopScan], MUIM_Notify, MUIA_Pressed, TRUE,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_STOP_SCAN);

    DoMethod(MuiObjects[lvHosts], MUIM_Notify, MUIA_List_Active, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_LV_HOSTS_CHANGED);

    DoMethod(MuiObjects[lvRealms], MUIM_Notify, MUIA_List_Active, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_LV_REALMS_CHANGED);

    DoMethod(MuiObjects[lvRealms], MUIM_Notify, MUIA_Listview_DoubleClick, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_SCAN_HOSTS);

    DoMethod(MuiObjects[cbServices], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_SERVICES);

    DoMethod(MuiObjects[cbEntities], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_ENTITIES);

    DoMethod(MuiObjects[cbOwner], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_OWNER);

    DoMethod(MuiObjects[cbIPAddr], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_IPADDR);

    DoMethod(MuiObjects[cbKickStart], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_KICKSTART);

    DoMethod(MuiObjects[cbWorkbench], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_WORKBENCH);

    DoMethod(MuiObjects[cbNIPC], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_NIPC);

    DoMethod(MuiObjects[cbFastMem], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_FASTMEM);

    DoMethod(MuiObjects[cbChipMem], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_CHIPMEM);

    DoMethod(MuiObjects[cbProcessor], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_PROCESSOR);

    DoMethod(MuiObjects[cbChips], MUIM_Notify, MUIA_Selected, MUIV_EveryTime,
        MuiObjects[app], 2, MUIM_Application_ReturnID, ID_BT_CHIPS);


    //  The application is set up, now load
    //  a previously saved configuration from env:
    //

    DoMethod(MuiObjects[app], MUIM_Application_Load, "ENV:" PATH_PREFS);

    get (MuiObjects[stScanTime], MUIA_String_Contents, &foo);
    if ((*foo == 0) || (atol (foo) == 0))
    {
        set (MuiObjects[stScanTime], MUIA_String_Contents, "1");
    }

    get (MuiObjects[stScanPackets], MUIA_String_Contents, &foo);
    if ((*foo == 0) || (atol (foo) == 0))
    {
        set (MuiObjects[stScanPackets], MUIA_String_Contents, "10");
    }

    get (MuiObjects[stSavePath], MUIA_String_Contents, &foo);
    if (*foo == 0)
    {
        set (MuiObjects[stSavePath], MUIA_String_Contents, "PROGDIR:NetProbe.List");
    }
}



void EventLoop (void)
{
    ULONG   signals = 0;
    BOOL    running = TRUE;


    if (!(getRealmServerRunning ()))
    {
        set (MuiObjects[btScanRealms],      MUIA_Disabled, TRUE);
        set (MuiObjects[btScanAllHosts],    MUIA_Disabled, TRUE);
        set (MuiObjects[lvRealms],          MUIA_Disabled, TRUE);
    }


    set (MuiObjects[winMain],   MUIA_Window_Open, TRUE);

    while (running)
    {
        switch (DoMethod(MuiObjects[app], MUIM_Application_Input, &signals))
        {
            case MUIV_Application_ReturnID_Quit:
            case ID_QUIT:
                running = FALSE;
                break;


            case ID_ABOUT:
                MUI_Request (MuiObjects[app], MuiObjects[winMain], 0, NULL, "*Excellent",
                    "\33c%s\n"
                    "\33c\n"
                    "\33c© 1993,1994 Hakan Tandogan\n"
                    "\33cFreely  distributable\n"
                    "\33c\n"
                    "\33cThis is a MUI-Application.\n"
                    "\33cMUI is copyrighted by Stefan Stuntz.",
                    getAboutVersionString ());
                break;


            case ID_SAVE:
                {
                    char* pathname;

                    get (MuiObjects[stSavePath], MUIA_String_Contents, &pathname);
                    SaveList (pathname);
                }
                break;


            case ID_SCAN_REALMS:
                {
                    struct Node* realm;
                    char*        foo;

                    DoMethod (MuiObjects[lvRealms], MUIM_List_Clear);

                    BuildNPConfiguration ();

                    get (MuiObjects[stScanTime], MUIA_String_Contents, &foo);
                    NP_ScanTime    = atol (foo);

                    get (MuiObjects[stScanPackets], MUIA_String_Contents, &foo);
                    NP_ScanPackets = atol (foo);

                    ScanRealms ();

                    for (realm = getRealmList()->lh_Head; realm->ln_Succ; realm = realm->ln_Succ)
                    {
                        DoMethod (MuiObjects[lvRealms], MUIM_List_Insert, &(realm->ln_Name), 1, MUIV_List_Insert_Sorted);
                    }
                }
                break;


            case ID_SCAN_HOSTS:
                {
                    struct Node* host;
                    ULONG        selected;
                    APTR         realmname;
                    char*        foo;


                    get (MuiObjects[lvRealms], MUIA_List_Entries, &selected);

                    if (selected > 0)
                    {
                        get (MuiObjects[lvRealms], MUIA_List_Active, &selected);

                        if (selected != MUIV_List_Active_Off)
                        {
                            DoMethod (MuiObjects[lvRealms], MUIM_List_GetEntry, selected, &realmname);
                        }
                        else
                        {
                            realmname = NULL;
                        }
                    }
                    else
                    {
                        realmname = NULL;
                    }

                    DoMethod (MuiObjects[lvHosts],          MUIM_List_Clear);
                    DoMethod (MuiObjects[lvServices],       MUIM_List_Clear);
                    DoMethod (MuiObjects[lvEntities],       MUIM_List_Clear);

                    set (MuiObjects[stOwner],       MUIA_Text_Contents, NULL);
                    set (MuiObjects[stIPAddr],      MUIA_Text_Contents, NULL);
                    set (MuiObjects[stKickStart],   MUIA_Text_Contents, NULL);
                    set (MuiObjects[stWorkbench],   MUIA_Text_Contents, NULL);
                    set (MuiObjects[stNIPC],        MUIA_Text_Contents, NULL);
                    set (MuiObjects[stFastMem],     MUIA_Text_Contents, NULL);
                    set (MuiObjects[stChipMem],     MUIA_Text_Contents, NULL);
                    set (MuiObjects[stProcessor],   MUIA_Text_Contents, NULL);
                    set (MuiObjects[stChips],       MUIA_Text_Contents, NULL);

                    BuildNPConfiguration ();

                    get (MuiObjects[stScanTime], MUIA_String_Contents, &foo);
                    NP_ScanTime    = atol (foo);

                    get (MuiObjects[stScanPackets], MUIA_String_Contents, &foo);
                    NP_ScanPackets = atol (foo);

                    ScanHosts ((char*) realmname);

                    for (host = getHostList()->lh_Head; host->ln_Succ; host = host->ln_Succ)
                    {
                        DoMethod (MuiObjects[lvHosts], MUIM_List_Insert, &(host->ln_Name), 1, MUIV_List_Insert_Sorted);
                    }

                    if (getHostCount())
                    {
                        set (MuiObjects[lvHosts], MUIA_List_Active, 0);
                    }
                }
                break;


            case ID_SCAN_ALL_HOSTS:
                {
                    struct Node* host;
                    struct Node* realm;
                    char*        foo;

                    DoMethod (MuiObjects[lvRealms],         MUIM_List_Clear);
                    DoMethod (MuiObjects[lvHosts],          MUIM_List_Clear);
                    DoMethod (MuiObjects[lvServices],       MUIM_List_Clear);
                    DoMethod (MuiObjects[lvEntities],       MUIM_List_Clear);

                    BuildNPConfiguration ();

                    get (MuiObjects[stScanTime], MUIA_String_Contents, &foo);
                    NP_ScanTime    = atol (foo);

                    get (MuiObjects[stScanPackets], MUIA_String_Contents, &foo);
                    NP_ScanPackets = atol (foo);

                    ScanAllHosts ();

                    for (realm = getRealmList()->lh_Head; realm->ln_Succ; realm = realm->ln_Succ)
                    {
                        DoMethod (MuiObjects[lvRealms], MUIM_List_Insert, &(realm->ln_Name), 1, MUIV_List_Insert_Sorted);
                    }

                    for (host = getHostList()->lh_Head; host->ln_Succ; host = host->ln_Succ)
                    {
                        DoMethod (MuiObjects[lvHosts], MUIM_List_Insert, &(host->ln_Name), 1, MUIV_List_Insert_Sorted);
                    }

                    if (getHostCount())
                    {
                        set (MuiObjects[lvHosts], MUIA_List_Active, 0);
                    }
                }
                break;


            case ID_PREFS:
                set (MuiObjects[winPrefs], MUIA_Window_Open,  TRUE);
                break;


            case ID_PREFS_ASLREQ:
                {
                    LONG leftedge;
                    LONG topedge;
                    char pathbuf [1024];
                    struct FileRequester*   FileRequester;
                    struct Window*          parent;


                    get (MuiObjects[winPrefs], MUIA_Window_Window,      &parent);
                    get (MuiObjects[winPrefs], MUIA_Window_LeftEdge,    &leftedge);
                    get (MuiObjects[winPrefs], MUIA_Window_TopEdge,     &topedge);

                    if (FileRequester = MUI_AllocAslRequestTags (ASL_FileRequest,
                                                                 ASLFR_Window,          parent,
                                                                 ASLFR_InitialLeftEdge, leftedge,
                                                                 ASLFR_InitialTopEdge,  topedge,
                                                                 ASLFR_TitleText,       "Select Save File",
                                                                 TAG_DONE))
                    {
                        set (MuiObjects[winPrefs], MUIA_Window_Sleep, TRUE);

                        if (MUI_AslRequestTags ((APTR) FileRequester, TAG_DONE))
                        {
                            stccpy (pathbuf, FileRequester->fr_Drawer, sizeof (pathbuf));

                            AddPart (pathbuf, FileRequester->fr_File, sizeof (pathbuf));

                            set (MuiObjects[stSavePath], MUIA_String_Contents, pathbuf);
                        }

                        set (MuiObjects[winPrefs], MUIA_Window_Sleep, FALSE);

                        MUI_FreeAslRequest (FileRequester);
                    }
                }
                break;


            case ID_PREFS_SAVE:
                DoMethod(MuiObjects[app], MUIM_Application_Save, "ENVARC:" PATH_PREFS);
                //  fall through


            case ID_PREFS_USE:
                DoMethod(MuiObjects[app], MUIM_Application_Save, "ENV:" PATH_PREFS);
                //  fall through


            case ID_PREFS_QUIT:
                set (MuiObjects[winPrefs], MUIA_Window_Open,  FALSE);
                break;


            case ID_LV_HOSTS_CHANGED:
                {
                    long selected;
                    APTR hostname;

                    get (MuiObjects[lvHosts], MUIA_List_Active, &selected);
                    DoMethod (MuiObjects[lvHosts], MUIM_List_GetEntry, selected, &hostname);

                    DecodeHost (getHost ((char*) hostname));
                }
                break;


            case ID_LV_REALMS_CHANGED:
                break;


            case ID_BT_ENTITIES:
                HandleCheckBox (MuiObjects[cbEntities],     MuiObjects[lvEntities]);
                break;

            case ID_BT_SERVICES:
                HandleCheckBox (MuiObjects[cbServices],     MuiObjects[lvServices]);
                break;

            case ID_BT_OWNER:
                HandleCheckBox (MuiObjects[cbOwner],        MuiObjects[stOwner]);
                break;

            case ID_BT_IPADDR:
                HandleCheckBox (MuiObjects[cbIPAddr],       MuiObjects[stIPAddr]);
                break;

            case ID_BT_KICKSTART:
                HandleCheckBox (MuiObjects[cbKickStart],    MuiObjects[stKickStart]);
                break;

            case ID_BT_WORKBENCH:
                HandleCheckBox (MuiObjects[cbWorkbench],    MuiObjects[stWorkbench]);
                break;

            case ID_BT_NIPC:
                HandleCheckBox (MuiObjects[cbNIPC],         MuiObjects[stNIPC]);
                break;

            case ID_BT_FASTMEM:
                HandleCheckBox (MuiObjects[cbFastMem],      MuiObjects[stFastMem]);
                break;

            case ID_BT_CHIPMEM:
                HandleCheckBox (MuiObjects[cbChipMem],      MuiObjects[stChipMem]);
                break;

            case ID_BT_PROCESSOR:
                HandleCheckBox (MuiObjects[cbProcessor],    MuiObjects[stProcessor]);
                break;

            case ID_BT_CHIPS:
                HandleCheckBox (MuiObjects[cbChips],        MuiObjects[stChips]);
                break;

            default:
                break;
        }

        if (running && signals) Wait(signals);
    }


    set (MuiObjects[winScan],  MUIA_Window_Open, FALSE);
    set (MuiObjects[winPrefs], MUIA_Window_Open, FALSE);
    set (MuiObjects[winMain],  MUIA_Window_Open, FALSE);
}


static void HandleCheckBox (APTR CheckBox, APTR StringGadget)
{
    long selected;

    get (CheckBox, MUIA_Selected, &selected);
    if (selected)
    {
        set (StringGadget, MUIA_Disabled, FALSE);
    }
    else
    {
        set (StringGadget, MUIA_Disabled, TRUE);
    }

}



static void BuildNPConfiguration (void)
{                                
    long selected   = TRUE;


    NP_Configuration = NP_HostName;

    get (MuiObjects[cbIPAddr], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_IPAddr;
    }


    get (MuiObjects[cbOwner], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_Owner;
    }

    get (MuiObjects[cbKickStart], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_KickVersion;
    }


    get (MuiObjects[cbWorkbench], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_WBVersion;
    }


    get (MuiObjects[cbNIPC], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_NIPCVersion;
    }


    get (MuiObjects[cbFastMem], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_MaxFastMem;
        NP_Configuration |= NP_AvailFastMem;
    }


    get (MuiObjects[cbChipMem], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_MaxChipMem;
        NP_Configuration |= NP_AvailChipMem;
    }


    get (MuiObjects[cbProcessor], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_ATTNFlags;
    }


    get (MuiObjects[cbChips], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_ChipRevBits;
    }


    get (MuiObjects[cbServices], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_Services;
    }


    get (MuiObjects[cbEntities], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_Entities;
    }


    get (MuiObjects[bt402Kludge], MUIA_Selected, &selected);
    if (selected)
    {
        NP_Configuration |= NP_402_Kludge;
    }
}



static void Add (APTR list, char* string)
{
    DoMethod (list, MUIM_List_Insert, &string, 1, MUIV_List_Insert_Sorted);
}



static void DecodeHost (Host* foo)
{
    char string [1024];



    set (MuiObjects[stOwner], MUIA_Text_Contents, foo->Owner);



    if (NP_Configuration & NP_IPAddr)
    {
        sprintf (string, "%ld.%ld.%ld.%ld", ((foo->IPAddr >> 24) & 0xff), ((foo->IPAddr >> 16) & 0xff), ((foo->IPAddr >> 8) & 0xff), (foo->IPAddr & 0xff));
    }
    else
    {
        string [0] = 0;
    }

    set (MuiObjects[stIPAddr], MUIA_Text_Contents, &(string));



    if (NP_Configuration & NP_KickVersion)
    {
        sprintf (string, "%ld.%ld", ((foo->KickVersion >> 16) & 0xffff), (foo->KickVersion & 0xffff));
    }
    else
    {
        string [0] = 0;
    }

    set (MuiObjects[stKickStart], MUIA_Text_Contents, &(string));



    if (NP_Configuration & NP_WBVersion)
    {
        sprintf (string, "%ld.%ld", ((foo->WBVersion >> 16) & 0xffff), (foo->WBVersion & 0xffff));
    }
    else
    {
        string [0] = 0;
    }

    set (MuiObjects[stWorkbench], MUIA_Text_Contents, &(string));



    if (NP_Configuration & NP_NIPCVersion)
    {
        sprintf (string, "%ld.%ld", ((foo->NIPCVersion >> 16) & 0xff), (foo->NIPCVersion & 0xff));
    }
    else
    {
        string [0] = 0;
    }

    set (MuiObjects[stNIPC],   MUIA_Text_Contents, &(string));



    if (NP_Configuration & NP_MaxChipMem)
    {
        sprintf (string, "%ld K", (foo->MaxChipMem) / 1024);
    }
    else
    {
        string [0] = 0;
    }

    set (MuiObjects[stChipMem], MUIA_Text_Contents, &(string));



    if (NP_Configuration & NP_MaxFastMem)
    {
        sprintf  (string, "%ld K", (foo->MaxFastMem) / 1024);
    }
    else
    {
        string [0] = 0;
    }

    set (MuiObjects[stFastMem], MUIA_Text_Contents, &(string));



    if (NP_Configuration & NP_ATTNFlags)
    {
        sprintf (string, "%s", DecodeATTNFlags (foo->ATTNFlags));
    }
    else
    {
        string [0] = 0;
    }

    set (MuiObjects[stProcessor],   MUIA_Text_Contents, &(string));



    if (NP_Configuration & NP_ChipRevBits)
    {
        sprintf (string, "%s", DecodeChipRevBits (foo->ChipRevBits));
    }
    else
    {
        string [0] = 0;
    }

    set (MuiObjects[stChips],   MUIA_Text_Contents, &(string));



    DoMethod (MuiObjects[lvServices], MUIM_List_Clear);

    if (NP_Configuration & NP_Services)
    {
        if (!(IsListEmpty (&(foo->Services))))
        {
            struct Node* work;

            for (work = foo->Services.lh_Head; work->ln_Succ; work = work->ln_Succ)
            {
                Add (MuiObjects[lvServices], work->ln_Name);
            }
        }
    }



    DoMethod (MuiObjects[lvEntities], MUIM_List_Clear);

    if (NP_Configuration & NP_Entities)
    {
        if (!(IsListEmpty (&(foo->Entities))))
        {
            struct Node* work;

            for (work = foo->Entities.lh_Head; work->ln_Succ; work = work->ln_Succ)
            {
                Add (MuiObjects[lvEntities], work->ln_Name);
            }
        }
    }
}



void SetupFuelGauge (long current, long max)
{
    set (MuiObjects[fgScanTime], MUIA_Gauge_Max, max * 5);

    set (MuiObjects[fgScanTime], MUIA_Gauge_Current, current);

    set (MuiObjects[winScan], MUIA_Window_Open, TRUE);
}



void ShutDownFuelGauge (void)
{
    set (MuiObjects[winScan], MUIA_Window_Open, FALSE);
}


void ShowScan (void)
{
    long MuiSignals;
    long ReceivedSignals;
    long running    = TRUE;
    long ticks      = 0;
    long now        = 0;
    long base       = 0;
    struct timerequest* TimeReq  = GetTimeReq ();
    struct MsgPort*     TimePort = GetTimePort ();



    //
    //  What MUI signals do we listen to?
    //

    DoMethod (MuiObjects[app], MUIM_Application_Input, &MuiSignals);


    //
    //  Remove the 'pushed'-status on the stop-button
    //

    set (MuiObjects[btStopScan], MUIA_Pressed, FALSE);


    //
    //  Let's rock...
    //

    get (MuiObjects[fgScanTime], MUIA_Gauge_Current, &base);
    base *= 5;

    TimeReq->tr_time.tv_secs    = 0L;
    TimeReq->tr_time.tv_micro   = TIME_INTERVAL;
    SendIO ((struct IORequest*) TimeReq);

    while (running)
    {
        ReceivedSignals = Wait (MuiSignals | 1L << TimePort->mp_SigBit);

        switch (DoMethod (MuiObjects[app], MUIM_Application_Input, &MuiSignals))
        {
            case ID_STOP_SCAN:
                running = FALSE;
                break;

            default:
                break;
        }

        if (ReceivedSignals & (1L << TimePort->mp_SigBit))
        {
            if (ticks ++ == NP_ScanTime * 5)
            {
                running = FALSE;
            }

            while (GetMsg (TimePort))
                ;

            TimeReq->tr_time.tv_secs    = 0L;
            TimeReq->tr_time.tv_micro   = TIME_INTERVAL;
            SendIO ((struct IORequest*) TimeReq);

            set (MuiObjects[fgScanTime], MUIA_Gauge_Current, base + now++);
        }
    }

    AbortIO ((struct IORequest*) TimeReq);
}
