/*
 * MandelVroom 2.0
 *
 * (c) Copyright 1987,1989  Kevin L. Clague, San Jose, CA
 *
 * All rights reserved.
 *
 * Permission is hereby granted to distribute this program's source
 * executable, and documentation for non-comercial purposes, so long as the
 * copyright notices are not removed from the sources, executable or
 * documentation.  This program may not be distributed for a profit without
 * the express written consent of the author Kevin L. Clague.
 *
 * This program is not in the public domain.
 *
 * Fred Fish is expressly granted permission to distribute this program's
 * source and executable as part of the "Fred Fish freely redistributable
 * Amiga software library."
 *
 * Permission is expressly granted for this program and it's source to be
 * distributed as part of the Amicus Amiga software disks, and the
 * First Amiga User Group's Hot Mix disks.
 *
 * contents: this file contains functions to decode Intuition Menu messages.
 */

#include "mandp.h"

extern struct NewScreen NewScreen;

extern int Num_vp_Colors;

char File[80] = "", Path[80] = "Mandelbrot:PROJECTS";

HandleMenuPick( Msg )
  register struct IntuiMessage *Msg;
{
  register struct MenuItem *Item;
  register USHORT code = Msg->Code;

  if (code == MENUNULL) {
    return;
  }

  if (State == HELPSTATE) {
    HelpMenuCmd(Msg);
    State = IDLESTATE;
    return;
  } else {
    State = IDLESTATE;
  }

  while (code != MENUNULL) {

    switch ( MENUNUM( code ) ) {

      case PROJECTMENU:
           ProjectMenu( Msg, code );
           break;

      case DISPLAYMENU:
           DisplayMenu( Msg, code );
           break;

      case CALCULATEMENU:
           CalculateMenu( Msg, code );
           break;

      case SPECIALMENU:
           SpecialMenu( Msg, code );
           break;
    }
    Item = ItemAddress( (struct Menu *) &Menu[0], (long) code);
    code = Item->NextSelect;
  }
  MaybeNewScreen();
}

/*
 * Decide what to do for Project menu's Items
 */
ProjectMenu(Msg,code)
  struct IntuiMessage *Msg;
  USHORT code;
{
  char Name[160];
  char *p;

  register struct Picture *Pict = CurPict;
  register struct Picture *LoadPict;
  register struct Window  *Window;
  register SHORT  Type;

  struct Picture *NewPict();

  if (Pict) {
    Window = Pict->Window;
  } else {
    Window = BackWind;
  }

  switch (ITEMNUM(code)) {

    case NEWITEM:

         switch( SUBNUM(code) ) {

           case 0:
                Type = MANDPICT;
                break;

           case 1:
                Type = JULIAPICT;
                break;
         }

         if ( Pict )
           ClonePict( Pict, Type );
         else
           NewPreset( -1, Type );
         break;

    case CURITEM:
         MakeCurProj( (struct Picture *) Msg->IDCMPWindow->UserData );
         break;

    case CLOSEPROJ:
         CloseWinds( CurPict->Window );
         break;

    case HELPITEM:
         SetWithPointer();
         State = HELPSTATE;
         break;

    case SAVEPROJ:
         strcpy( File, Pict->Title+2 );

    case LOADITEM:
    case SAVEILBM:

         switch( ITEMNUM(code) ) {
           case  LOADITEM: p = "Load Project"; break;
           case  SAVEPROJ: p = "Save Project"; break;
           case  SAVEILBM: p = "Save ILBM";    break;
         }

         if (get_fname(BackWind, screen, p, File, Path)) {

           SetSleepyPointer();

           strcpy(Name,Path);
           if (Name[0] != '\0' && Name[strlen(Name)-1] != ':') {
             strcat(Name,"/");
           }
           strcat(Name,File);

           switch( ITEMNUM(code) ) {

             case  LOADITEM:
                   (void) LoadPicture( Name );
                   RefreshContours();

                   RefreshContours();
                   CalcHist(CurPict);
                   ShowStats(CurPict);
                   SetDirGadget(CurPict);
                   ModifySpeedPot();
                   break;

             case  SAVEPROJ:

                   PauseChild( Pict );

                   strncpy( Pict->Title+2, File, sizeof(Pict->Title)-3);
                   (void) SaveCounts(Name,Pict);

                   AwakenChild( Pict );
                   break;

             case  SAVEILBM:
                   SaveILBM(Name, Pict->Crngs, 4);
                   break;
           }
           SetNormPointer();
         }

    case CANCELITEM:
         State = IDLESTATE;
         break;

    case QUITITEM:
         if (DispErrMsg("Really quit?",1)) {

           QuitScreen = TRUE;
         }
    }
} /* ProjectMenu */

/*
 * Decide what to do for Display menu's Items
 */
DisplayMenu(Msg,code)
  struct IntuiMessage *Msg;
  USHORT code;
{
  double gapy,gapx;
  extern UBYTE  ScreenSizeChanged;
  extern UBYTE  StandardSize;
  extern UBYTE  NewDepth;
  extern USHORT NewViewModes;
  extern struct MenuItem ScreenSizeSubs[];
  extern struct MenuItem BorderSubs[];

  switch (ITEMNUM(code)) {

    case COLORITEM:
         OpenPalWind();
         break;

    case CYCLEITEM:
         OpenCycWind();
         break;

    case CONTOURITEM:
         OpenContWind();
         break;

    case HISTOGRAMITEM:
         OpenHistWind();
         break;

    case AUTOCNTRITEM:
         AutoContour(CurPict,SUBNUM(code));
         break;

    case DEPTHITEM:
         NewDepth = SUBNUM(code) + 1;

         if (CurPict)
           CurPict->Depth = NewDepth;
         break;

    case VIEWMODEITEM:
         EditScreenViewModes(code);

         if (CurPict) {
           CurPict->ViewModes = NewViewModes;
           if (NewViewModes & HIRES && CurPict->Depth > 4) {
             CurPict->Depth = 4;
           }
         }
         break;

    case SCREENITEM:
         StandardSize = (ScreenSizeSubs[0].Flags & CHECKED) == CHECKED;
         ScreenSizeChanged = 1;
         break;

    case BORDERITEM:
         if (CurPict) {
           int Changed;

           Changed = 0;

           if ((BorderSubs[0].Flags & CHECKED) == CHECKED) {

             /* Make it bordered */

             if (CurPict->Flags & BORDERLESS_PROJ &&
                 CurPict->CountX+LEFTMARG+RIGHTMARG <= screen->Width &&
                 CurPict->CountY+TOPMARG+BOTMARG    <= screen->Height) {

               CurPict->Flags &= ~BORDERLESS_PROJ;
               Changed = 1;
             }
           } else {

             if (!(CurPict->Flags & BORDERLESS_PROJ)) {
               CurPict->Flags |=  BORDERLESS_PROJ;
               Changed = 1;
             }
           }

           InitBorderSubs();

           if (Changed) {

             if ( CurPict->cTask ) {

               KillReColor( CurPict );
             }

             PauseChild( CurPict );

             ClosePicture(CurPict);
             OpenPicture(CurPict);

             if (CurPict->Counts)
               ReColor(CurPict);

             AwakenChild(CurPict);
           }
         }
         break;
    }
} /* DisplayMenu */

/*
 * Decide what to do for Calculate Menu's Items
 */
CalculateMenu(Msg,code)
  struct IntuiMessage *Msg;
  USHORT code;
{
  extern struct Picture *ZoomedPict;
  extern struct MenuItem LensSub[];

  double gapy,gapx;
  LONG   Temp;
  extern UBYTE  LensOn;

  switch (ITEMNUM(code)) {

    case GENERATORITEM:   /* generator type */
         if (CurPict)
           CurPict->MathMode = SUBNUM(code);
         break;

    case ZOOMITEM:
         CurPict->ZoomType = SUBNUM(code);
         DoZoom( Msg );
         break;

    case SCROLLITEM:
         ScrollPictCmd(Msg);
         break;

    case LENSITEM:
         LensOn = (LensSub[0].Flags & CHECKED) == CHECKED;
         break;

    case GENERATEITEM:
         GenerateCmd(Msg);
         break;

    case COUNTITEM:

         Temp = CurPict->MaxIteration;

         if ( GetInt( "Max Iteration", &Temp) == 1 ) {

           if (Temp > 1023) Temp = 1023;

           CurPict->MaxIteration = Temp;
         }
         break;

    case STATSITEM:

#ifndef DEVELOPMENT

         OpenStatsWind( CurPict );
#else
         { char Name[80];
           char VD0[80];

           strcpy( VD0, "ram:");

           if (get_fname(BackWind, screen, "Preset", File, VD0)) {

             strcpy(Name,VD0);

             if (Name[strlen(Name)-1] != ':') {
               strcat(Name,"/");
             }
             strcat(Name,File);

             SavePreset( Name, CurPict );
           }
         }
#endif
         break;
  }
} /* CalculateMenu */

DoZoom( Msg )
  struct IntuiMessage *Msg;
{
  register struct Picture *Pict = CurPict;

  if (Pict == NULL)
    return;

  CloseZoomBox( Pict );

  ZoomedPict = Pict;   /* Save this so we can use it later */

  switch ( SUBNUM(Msg->Code)) {

    case ZOOMIN:
         ZoomInCmd(Msg);
         break;

    case ZOOMOUT:
         ZoomOutCmd(Msg);
         break;

    case ZOOMOFF:
         ClearZoomBox( ZoomedPict );
         break;

    case ZOOMJULIA:
         SetJuliaCmd(Msg);
         break;
  }
}

USHORT NewViewModes;
UBYTE  NewDepth = 5;

/*
 * Modify the NewScreens ViewModes to match the menu
 */
EditScreenViewModes(code)
  USHORT code;
{
  switch (SUBNUM(code))
    {
    case HIRESSUB:
         NewViewModes ^= HIRES;
         break;

    case INTERLACESUB:
         NewViewModes ^= INTERLACE;
         break;

    case HALFBRITESUB:
         NewViewModes ^= EXTRA_HALFBRITE;
         break;
    }
} /* EditScreenViewMode */

/*
 * Decide what to do for Special Menu's Items
 */
SpecialMenu(Msg, code)
  struct IntuiMessage *Msg;
  USHORT code;
{
  extern SHORT MaxOrbit;

  LONG   Temp;
  int    rc;

  rc = SUCCESSFUL;

  switch (ITEMNUM(code)) {

    case ORBITITEM:
         OpenOrbitWind();
         break;

    case MAXORBITEM:
         Temp = MaxOrbit;

         if ( GetInt( "Max Iteration", &Temp) == 1 ) {

           if (Temp > 1023) Temp = 1023;

           MaxOrbit = Temp;
         }
         break;

    case ORBITMATHITEM:
         ConfOrbMode( SUBNUM(code) );
         break;

    case PRESETITEM:
         rc = SetPreset( SUBNUM( code ) );

         if (rc == UNSUCCESSFUL)
           DispErrMsg("Can't open preset. Out of RAM",0);
         else
         if (CurPict->Flags & NO_RAM_GENERATE)
           rc = UNSUCCESSFUL;

         RefreshContours();
  }
  return( rc );
} /* SpecialMenu */

LoadPicture( Name )
  char Name[];
{
  struct Picture *LoadPict;

  LoadPict = NewPict( MANDPICT );

  if ( LoadPict ) {
    if ( LoadCounts( Name, LoadPict ) == UNSUCCESSFUL ) {

      ThrowPict( LoadPict );
      GetCurPict();
      return(UNSUCCESSFUL);

    }
  } else {
    ErrNoPict();
    return(UNSUCCESSFUL);
  }
  return(SUCCESSFUL);
}

char *
ExtractName( FullPath )
  char *FullPath;
{
  char *File,*rindex(),*p;

  File = rindex( FullPath, '/' );

  if (File == NULL)

    File = rindex( FullPath, ':' );

  if (File)
    File += 1;

  /* Save a copy of it */

  strcpy( Path, FullPath );

  p = &Path[ File - FullPath - 1 ];

  if (*p == '/') *p = '\0';
  if (*p == ':') *(p+1) = '\0';

  return( File );
}

