//Menu : menu.cpp
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "menu.h"

/******************************************************/
/* Classe menu                                        */
/******************************************************/

menu::menu (menu **base,char *n) : list ((list **)base) // Costruttore della superclasse (appende alla lista)
{
  voce = new char [strlen (n) + 1]; // Alloca lo spazio per il nome del menu
  if (voce)                         // Se e' riuscito ad allocare
    strcpy (voce,n);                // Ci copia il nome del menu'
}

/* Funzione ricorsiva che stampa tutte le voci del menu',
 * precedute dal numero, che  sara' il modo per selezionera il
 * menu' stesso.
 * Il numero della vaco va passata come parametro, quindi noi
 * la invocheremo sulla prima voce del menu', con il numero 1.
 * Dopo il menu' stampa un prompt, legge l'input dell'utente,
 * lo trasforma in numero (e' la selezione) e lo ritorna */
int menu::print (int curr)
{
  printf ("%d)%s\n",curr,voce);                   // Stampa 'n) nome menu'
  if (Next ())                                    // Se non e' l'ultimo menu'
    return ((menu *)Next ()) -> print (curr + 1); // Richiema la prossima voce, per stamparla (aggiorna il numero)
  else
  {                                 // Ho stampato l'ultimo elemento, scelta:
  char str [10];                    // Posto per il numero scelto dall'utente
  int i;                            // Numero scritto dall'utente
    printf ("Fai la tua scelta: "); // Prompt
    fgets (str,9,stdin);            // Legge la risposta dell'utente
    i = strtol (str,0,0L);          // Converte in numero
    return i;                       // Ritorna il numero introdotto
  }
}

/* Funzione che individua la voce scelta e lancia l'azione per quella voce */
void menu::doaction (int n,void *par)
{
menu *m = (menu *) index (n,1); // Individua la voce usando i metodi della superclasse 'list'
  if (m)                        // Se l'elemento selezionato esiste (non ho dato un numero troppo grande)
    m -> action (par);          // Richiamo il suo metodo 'action' (virtuale)
}

menu::~menu ()
{
  if (voce)      // Se il menu' ha il nome (e' riuscito ad allocarlo)
    delete voce; // libera lo spazio del nmome
}

/******************************************************/
/* Classe menuexit                                    */
/******************************************************/

void menuexit::action (void *par)
{
#pragma argsused (par)  // serve per eliminare il warning 'parametro non utilizzato'
	exit (0);       // Azione (guarda un po'.. ;-> ) exit
}