AhorcaLlop - El ahorcado

Llop Site Home > JAVA > AhorcaLlop > Código java

Clase AhorcaLlop

package ahorcado;

import java.awt.*;
import java.awt.event.*;
import java.io.*;
import java.lang.*;
import java.net.*;
import javax.swing.*;
import javax.sound.sampled.*;

/** Título: AhorcaLlop
    Descripción: Prácticas capítulo 11, ejercicio 2
    Copyright: Copyright (c) 2005
    Empresa: Casa_Llop
    @author Albert_Lobo
    @version 1.0 */
public class AhorcaLlop extends JApplet implements Runnable, KeyListener, MouseListener
{
  // Estados de la partida:
  /** Constante que indica que hay una partida en curso. */
  private static final byte EN_CURSO = 0;
  /** Constante que indica que se ha adivinado la palabra secreta. */
  private static final byte VICTORIA = 1;
  /** Constante que indica que no se ha adivinado la palabra secreta. */
  private static final byte DERROTA = 2;

  /** Número de letras incorrectas para completar el dibujo del ahorcado. */
  private static final byte INTENTOS_PARTIDA = 11;
  /** Máximo de letras permitidas para la palabra oculta. */
  private static final byte MAXIMO_LETRAS_PALABRA_OCULTA = 12;

  // Array con todas las palabras secretas disponibles.
  private String lstPlbrs [];

  // Número de letras de la palabra oculta.
  private byte numLtrsPlbrOclt;
  // Tabla de caracteres en la que se almacena la palabra secreta.
  private char plbrOclt [];

  // Número de letras incorrectas que ha pulsado el jugador.
  private byte numLtrsMal;
  // Tabla que almacena las letras incorrectas que ha picado el usuario.
  private char ltrsMal [];

  // Número de letras de la palabra oculta que el jugador ha adivinado.
  private byte numLtrsBien;
  // Tabla con las letras que el jugador ha adivinado.
  private char ltrsBien [];

  // Array de imágenes que, superpuestas, dan lugar al dibujo del ahorcado.
  // Las imágenes son '.gif': este formato permite que las imagenes tengan transparencia.
  private Image clgdo [];

  // Clase que gestiona los efectos sonoros del applet.
  private Sonido son;

  // Variable que representa el estado de la partida: es una de las constantes de la clase.
  private byte rsltPrtd;

  // Paneles del juego.
  // Panel para el dibujo del ahorcado.
  private PanelAhorcado pnlAhorc;
  // Panel para las letras que adivine el jugador.
  private PanelLetrasBien pnlLtrsBien;
  // Panel para las letras malas.
  private PanelLetrasMal pnlLtrsMal;
  // Panel que da instrucciones y muestra el resultado de las partidas.
  private PanelResultado pnlRslt;

  // Hilo que refrescará la pantalla constantemente.
  private Thread hilo;

  /** Inicializa el applet. */
  public void init ()
  {
    try
    {
      SwingUtilities.invokeAndWait (new Runnable ()
      {
        public void run ()
        {
          iniLstPlbrs ();
          iniVar ();
          iniCmp ();
          jugar ();
          if (!hilo.isAlive ())
            hilo.start ();
        }
      });
    } catch (Exception excepcion) {
      System.err.println ("Error al intentar arrancar el juego.");
    }
  }

  /** Iniciliza las variables. */
  private void iniVar ()
  {
    // Consigue los dibujos del ahorcado.
    clgdo = new Image [INTENTOS_PARTIDA];
    for (byte i = 0; i < INTENTOS_PARTIDA; i++)
      clgdo [i] = getImagen ("ahorc" + i + ".gif");

    // La palabra secreta.
    numLtrsPlbrOclt = 0;
    plbrOclt = new char [MAXIMO_LETRAS_PALABRA_OCULTA];

    // Las letras equivocadas.
    numLtrsMal = 0;
    ltrsMal = new char [INTENTOS_PARTIDA];

    // Las letras acertadas.
    numLtrsBien = 0;
    ltrsBien = new char [MAXIMO_LETRAS_PALABRA_OCULTA];

    // El estado de la partida, y el hilo.
    rsltPrtd = EN_CURSO;
    hilo = new Thread (this);
  }

  /** Iniciliza los componentes. */
  private void iniCmp ()
  {
    // El tamaño, el color, y el gestor del diseño del applet.
    getContentPane ().setSize (560, 355);
    getContentPane ().setBackground (Color.white);
    getContentPane ().setLayout (null);

    // Añadimos el panel para el dibujo del ahorcado.
    pnlAhorc = new PanelAhorcado ();
    getContentPane ().add (pnlAhorc);
    pnlAhorc.setLocation (20, 20);
    pnlAhorc.setSize (220, 235);
    // Añadimos el panel para las letras bien.
    pnlLtrsBien = new PanelLetrasBien ();
    getContentPane ().add (pnlLtrsBien);
    pnlLtrsBien.setLocation (20, 265);
    pnlLtrsBien.setSize (320, 65);
    // Añadimos el panel para las letras mal.
    pnlLtrsMal = new PanelLetrasMal ();
    getContentPane ().add (pnlLtrsMal);
    pnlLtrsMal.setLocation (250, 20);
    pnlLtrsMal.setSize (90, 235);
    // Añadimos el panel para el resultado de la partida.
    pnlRslt = new PanelResultado ();
    getContentPane ().add (pnlRslt);
    pnlRslt.setLocation (350, 20);
    pnlRslt.setSize (190, 310);
    // Inicializamos el sonido, y añadimos los oyentes de teclado y ratón.
    son = new Sonido ();
    addMouseListener (this);
    addKeyListener (this);
  }

  /** 'paint ()' se sobrecarga para personalizar un poco la interfaz.
      @param grfcs Graphics  : Contexto 'Graphics' sobre el que pintamos. */
  public void paint (Graphics grfcs)
  {
    super.paint (grfcs);
    // Pone un borde redondeado color azul sobre el fondo blanco.
    grfcs.setColor (Color.blue);
    grfcs.drawRoundRect(10, 10, getSize ().width - 20, getSize ().height - 20, 20, 20);
  }

  /** Se encarga de refrescar la pantalla constantemente, como una una tele.
      Esto permite ver bien los 'gifs animados'. */
  public void run ()
  {
    while (true)
    {
      repaint ();
      // Ponemos unos 20 fotogramas por segundo.
      try
      {
        Thread.sleep (50);
      } catch (InterruptedException e) {}
    }
  }

  /** Este método hace el trabajo de detectar qué tecla ha pulsado el jugador, y gestionarla
      correctamente: ¿es una letra de la palabra secreta?, ¿no lo es?, ¿está repetida?...
      @param evt KeyEvent  : Evento que dispara este método. */
  public void keyTyped (KeyEvent evt)
  {
    // Sólo interesa tratar con letras mayúsculas.
    // Esta variable representa la tecla que ha pulsado el jugador.
    char tcl = Character.toUpperCase (evt.getKeyChar ());

    // Si la partida ha terminado, el jugador debe pulsar 'Enter' para empezar una nueva.
    // Si no, no puede hacer nada con el juego.
    if (rsltPrtd != EN_CURSO)
    {
      if (tcl == '\n')
        jugar ();
      return;
    }

    // Ahora se comprueba si la tecla pulsada es una letra.
    if (!Character.isLetter (tcl))
    {
      // Si no lo es, un ruidito indica el error.
      son.repe ();
      return;
    }

    byte i;

    // Comprobamos si la letra está repetida: habrá que mirar en las tablas con las letras
    // acertadas, y las equivocadas.
    // Un ruidito notifica el error.
    for (i = 0; i < numLtrsPlbrOclt; i++)
      if (tcl == ltrsBien [i])
      {
        son.repe ();
        return;
      }
    for (i = 0; i < INTENTOS_PARTIDA; i++)
      if (tcl == ltrsMal [i])
      {
        son.repe ();
        return;
      }

    // Ahora se mira si la letra está en la palabra secreta.
    // De ser así, la variable 'bool' lo hará constar.
    boolean bool = false;
    for (i = 0; i < numLtrsPlbrOclt; i++) 
    {
      if (tcl == plbrOclt [i])
      {
        // Si el jugador ha adivinado una/s letra/s, la/s ponemos en la tabla de teras adivinadas.
        // También se suma uno a la cuenta.
        ltrsBien [i] = tcl;
        numLtrsBien++;
        bool = true;
      }
    }

    // Si el jugador ha acertado, suena un ruidito para notificarlo.
    // También se mira si con esta letra ha acertado la palabra entera.
    if (bool)
    {
      son.bien ();
      if (numLtrsBien == numLtrsPlbrOclt)
      {
        // Cuando el jugador adivina la palabra, hay que ajustar la variable con el
        // 'estado de la partida', y activar un ruidito.
        rsltPrtd = VICTORIA;
        son.victoria ();
      }
      return;
    }

    // Llegado este punto, el jugador se ha equivocado de letra.
    // Se suma uno a la cuenta de letras malas, se añade la letra a la tabla,
    // y suena un ruidito desagradable.
    numLtrsMal++;
    ltrsMal [numLtrsMal - 1] = tcl;
    son.mal ();

    // Puede que con este error se complete el dibujo del ahorcado.
    if (numLtrsMal == INTENTOS_PARTIDA)
    {
      // Se desvela la palabra secreta añadiendo a la tabla de letras bien las que le faltaban.
      // Se ajusta el 'estado de la partida', y suena un abucheo.
      for (i = 0; i < numLtrsPlbrOclt; i++)
        if (ltrsBien [i] == ' ')
          ltrsBien [i] = plbrOclt [i];
      rsltPrtd = DERROTA;
      son.derrota ();
    }
  }
  /** No hace nada; es necesaria para implementar correctamente la interfaz KeyListener.
      @param evt KeyEvent  : Evento asociado a la tecla pulsada. */
  public void keyPressed (KeyEvent evt) {}
  /** No hace nada; es necesaria para implementar correctamente la interfaz KeyListener.
      @param evt KeyEvent  : Evento asociado a la tecla pulsada. */
  public void keyReleased (KeyEvent evt) {}

  /** Pulsar el ratón sobre el panel de juego le da el foco al applet.
      @param evt MouseEvent  : Evento del ratón que ha disparado el método. */
  public void mouseClicked (MouseEvent e)
  {
    requestFocus ();
  }
  /** No hace nada; es necesaria para implementar correctamente la interfaz MouseListener.
      @param evt MouseEvent  : Evento del ratón que ha disparado el método. */
  public void mouseEntered (MouseEvent e) {}
  /** No hace nada; es necesaria para implementar correctamente la interfaz MouseListener.
      @param evt MouseEvent  : Evento del ratón que ha disparado el método. */
  public void mouseExited (MouseEvent e) {}
  /** No hace nada; es necesaria para implementar correctamente la interfaz MouseListener.
      @param evt MouseEvent  : Evento del ratón que ha disparado el método. */
  public void mousePressed (MouseEvent e) {}
  /** No hace nada; es necesaria para implementar correctamente la interfaz MouseListener.
      @param evt MouseEvent  : Evento del ratón que ha disparado el método. */
  public void mouseReleased (MouseEvent e) {}

  /** Método que inicia una partida nueva. */
  public void jugar ()
  {
    // Variable índice.
    byte i;

    // Escoge al azar una de las palabras de la lista, y la mete en el array para la palabra secreta.
    String plbr = lstPlbrs [(int) (Math.random () * lstPlbrs.length)];
    numLtrsPlbrOclt = (byte) plbr.length ();
    for (i = 0; i < numLtrsPlbrOclt; i++)
      plbrOclt [i] = plbr.charAt (i);

    // Se limpia la tabla de letras correctas,
    // y se añade una de las letras de la palabra secreta como pista.
    for (i = 0; i < MAXIMO_LETRAS_PALABRA_OCULTA; i++)
      ltrsBien [i] = ' ';
    numLtrsBien = 0;
    byte j = (byte) (Math.random () * plbrOclt.length);
    for (i = 0; i < MAXIMO_LETRAS_PALABRA_OCULTA; i++)
      if (plbrOclt [j] == plbrOclt [i])
      {
        ltrsBien [i] = plbrOclt [i];
        numLtrsBien++;
      }

    // También se limpia la tabla con las letras erróneas.
    for (i = 0; i < INTENTOS_PARTIDA; i++)
      ltrsMal [i] = ' ';
    numLtrsMal = 0;

    // Se ajusta el 'estado de la partida'.
    rsltPrtd = EN_CURSO;
  }

  /** Arranca el applet dándole el foco. */
  public void start()
  {
    requestFocus();
    // Prepara una partida nueva si la anterior ya ha terminado.
    if (rsltPrtd != EN_CURSO)
      jugar ();
  }

  /** Detener el applet. Ahorca al pavo -el jugador pierde. */
  public void stop ()
  {
    // Se ajusta el número de letras mal para completar el dibujo del ahorcado.
    // Se desvela la palabra secreta añadiendo a la tabla de letras bien las que le faltaban.
    // Se ajusta el 'estado de la partida', y suena un abucheo.
    numLtrsMal = INTENTOS_PARTIDA;
    for (byte i = 0; i < numLtrsPlbrOclt; i++)
      if (ltrsBien [i] == ' ')
        ltrsBien [i] = plbrOclt [i];
    rsltPrtd = DERROTA;
    son.derrota ();
  }

  /** Información del applet.
      @return String  : Nombre del autor. */
  public String getAppletInfo ()
  {
    return "Autor: Albert Lobo";
  }

  /** Método estático que devuelve la imagen en el fichero de recursos cuyo nombre corresponde con el
      del primero de los argumentos.
      @param imagen String       : Nombre del archivo de la imagen.
      @return Image              : La imagen apropiada del fichero de recursos. */
  public static Image getImagen (String imagen)
  {
    URL uRL = AhorcaLlop.class.getResource ("rcsAhorc/" + imagen);
    return new ImageIcon (uRL).getImage ();
  }

  /** Método que devuelve un flujo de entrada para datos de audio desde el clip cuyo nombre
      se especifica en el argumento.
      @param clip String        : Nombre del clip.
      @return AudioInputStream  : Flujo de datos de retorno. */
  public static AudioInputStream getClip (String clip)
  {
    AudioInputStream retorno = null;
    URL uRL = AhorcaLlop.class.getResource ("rcsAhorc/" + clip);
    try
    {
      retorno = AudioSystem.getAudioInputStream (uRL);
    } catch (IOException ex) {
      System.err.println (clip + " no encontrado.");
    } catch (UnsupportedAudioFileException ex) {
      System.err.println (clip + " no puede sonar.");
    }
    return retorno;
  }

  /** Inicializa la tabla con las palabras secretas. */
  private void iniLstPlbrs ()
  {
    lstPlbrs = new String [] {"ABALANZARSE",  "ABERRANTE",    "ABYECTO",      "ACAUDILLADO",
                              "ACOBARDADO",   "ACRITUD",      "ADHERIDO",     "AFGANISTAN",
                              "AGNOSTICO",    "AGUAFIESTAS",  "AGUILEÑO",     "ALBUMEN",
                              "ALCAYATA",     "ALIMENTACION", "ALMIRANTAZGO", "AMAESTRADO",
                              "AMNESIA",      "ANALFABETO",   "ANHELANTE",    "ANTEOJO",
                              "ANTROPOLOGIA", "APARIENCIA",   "APLIQUE",      "APROXIMADO",
                              "ARBITRAJE",    "ARISTOCRATA",  "ARCHIPIELAGO", "ARMATOSTE",
                              "ARREPENTIDO",  "ARSENICO",     "ASEMEJARSE",   "ASFIXIAR",
                              "ASQUEAR",      "ATIBORRADO",   "AUSPICIOS",    "AVENTURADO",
                              "AZABACHE",     "BALBUCIR",     "BAÑADOR",      "BARBECHO",
                              "BAYONETA",     "BESUQUEAR",    "BICARBONATO",  "BOLCHEVIQUE",
                              "BOQUIABIERTO", "BRICOLAJE",    "BUENAVENTURA", "BUSCAPLEITOS",
                              "CABALLERESCA", "CALABOZO",     "CALDERILLA",   "CALVICIE",
                              "CANIJO",       "CAÑAMON",      "CARAMBANO",    "CARNIVORO",
                              "CASTAÑUELAS",  "CATOLICISMO",  "CEDAZO",       "CERVECERIA",
                              "CIGARRILLO",   "CLEPTOMANO",   "CLIMATIZADO",  "COFRADIA",
                              "COLIFLOR",     "COMODIN",      "COMPARSA",     "CONCEJAL",
                              "CONCURRENCIA", "CONFITURA",    "CONMUTADOR",   "CONSTRICCION",
                              "CONTAGIOSO",   "CONTROVERSIA", "CORAJE",       "CORTAUÑAS",
                              "COSTILLAMEN",  "CRUCIFIJO",    "CUADRUPLE",    "CUCHITRIL",
                              "CUTICULA",     "CHANCHULLO",   "CHUBASQUERO",  "DAMNIFICADO",
                              "DECADENCIA",   "DEFICITARIO",  "DELIRIO",      "DENIGRANTE",
                              "DESABROCHAR",  "DESAJUSTE",    "DESASOSIEGO",  "DESBARATAR",
                              "DESCOMUNAL",   "DESCUARTIZAR", "DESENGAÑAR",   "DESGREÑADO",
                              "DESMAYO",      "DESPELLEJAR",  "DESQUITE",     "DEVALUACION",
                              "DIARREA",      "DIGNATARIO",   "DISFRAZ",      "DISQUETE",
                              "DOMICILIO",    "DONAIRE",      "DROGUERIA",    "EDICTO",
                              "ECUESTRE",     "ENSAMBLAJE",   "EMBRIONARIO",  "EMPERATRIZ",
                              "ENARBOLAR",    "ENCLENQUE",    "ENDOMINGARSE", "ENGATUSAR",
                              "ENMOHECIDO",   "ENSAYISTA",    "ENTRESIJO",    "ENVAINADO",
                              "EPILOGO",      "ESCARAMUZA",   "ESCURREPLATO", "ESPAGUETIS",
                              "ESPELUZNANTE", "ESQUIVO",      "ESTAÑO",       "ESTRATIFICAR",
                              "EUFEMISMO",    "EXCOMULGAR",   "EXPIATORIO",   "EXQUISITEZ",
                              "EXTRARRADIO",  "FASCISTA",     "FELPUDO",      "FILANTROPO",
                              "FLAGRANCIA",   "FORMATEADO",   "FRANQUEZA",    "FULGOR",
                              "GAMUZA",       "GAZPACHO",     "GIMNASIO",     "GRAMATICA",
                              "GROSELLA",     "GUIRALDA",     "HABICHUELA",   "HALTEROFILIA",
                              "HAZMERREIR",   "HIPOCRESIA",   "HOLGAZAN",     "HORQUILLA",
                              "HOSTIGAR",     "HURTADILLAS",  "ILUSORIO",     "IMPREVISTO",
                              "INCENTIVO",    "INCOLUMNE",    "INDEMNIZADO",  "INEFABLE",
                              "INFAUSTO",     "INHERENTE",    "INSONDABLE",   "INSURRECCION",
                              "INTERRUPCION", "INYECCION",    "ITINERARIO",   "JACTARSE",
                              "JAQUECA",      "JURISDICCION", "JUBILEO",      "KIOSCO",
                              "LABRADOR",     "LAPICERO",     "LEGUMBRES",    "LIBELO",
                              "LEXICO",       "LISONJEAR",    "LONGANIZA",    "LOMBRIZ",
                              "LUCIERNAGA",   "MACEDONIA",    "MADREPERLA",   "MALEDICENCIA",
                              "MALHUMORADO",  "MANCHEGO",     "MANUTENCION",  "MAQUIAVELICO",
                              "MARXISMO",     "MAXILAR",      "MECANOGRAFIA", "MEDUSA",
                              "MENOPAUSIA",   "MIGRATORIA",   "MISERABLE",    "MODIFICAR",
                              "MONTARAZ",     "MOTOSIERRA",   "MURCIELAGO",   "NARIGUDO",
                              "NEPOTISMO",    "NISPERO",      "NOCHEVIEJA",   "NOVIAZGO",
                              "NUPCIAS",      "ÑOÑERIAS",     "OBCECADO",     "OBSTETRICIA",
                              "OFTALMOLOGO",  "OMNIVORO",     "OPULENCIA",    "ORTODOXIA",
                              "OPULENCIA",    "OXIGENO",      "PABELLON",     "PADRASTRO",
                              "PALADIN",      "PALIDECER",    "PANTUFLA",     "PARACHOQUES",
                              "PARANGON",     "PARAPLEJICO",  "PARROQUIA",    "PASAMONTAÑAS",
                              "PASTEURIZADO", "PEDICURO",     "PELUCHE",      "PELOTARI",
                              "PEÑASCO",      "PERJURAR",     "PERSPICACIA",  "PERTURBADOR",
                              "PESQUISA",     "PIJAMA",       "PIQUETE",      "PLAÑIDERO",
                              "PLUTOCRACIA",  "POLIVALENCIA", "PONTIFICADO",  "PORTAMALETAS",
                              "POSTERGAR",    "PRECONCEBIDO", "PREMONICION",  "PRERROGATIVA",
                              "PRIMOGENITO",  "PRODIGAR",     "PROLETARIADO", "PROTAGONISTA",
                              "PSIQUICO",     "PUNICION",     "PUTRIDO",      "QUEMARROPA",
                              "QUIMERA",      "QUINCALLA",    "QUITANIEVES",  "RAMIFICADO",
                              "RASGUÑAR",     "RECALCITRAR",  "RECIPROCO",    "RECTANGULO",
                              "REEMBOLSAR",   "REGAÑINA",     "REHUSAR",      "REMACHE",
                              "RENACUAJO",    "REPLEGARSE",   "REQUESON",     "RESIGNACION",
                              "RESQUEBRAJAR", "RETRIBUCION",  "REVENTON",     "RIMBOMBANTE",
                              "ROMPEHUELGAS", "RUBRICA",      "SABAÑON",      "SAGACIDAD",
                              "SALTIMBANQUI", "SARAMPION",    "SAZONADO",     "SECUESTRO",
                              "SEMINARIO",    "SEPTIEMBRE",   "PSEUDONIMO",   "SINFONIA",
                              "SOBRASADA",    "SOFISTICADO",  "SOLVENTAR",    "SOPORIFERO",
                              "SUBYUGADO",    "SUFRAGIO",     "SUPERFLUO",    "SUSODICHO",
                              "TACITURNO",    "TALLARINES",   "TARDANZA",     "TARANTULA",
                              "TAUROMAQUIA",  "TEMPLARIO",    "TERGIVERSADO", "TIFIODEA",
                              "TIRACHINAS",   "TOCAYO",       "TORNIQUETE",   "TRABALENGUAS",
                              "TRANSEUNTE",   "TRAPICHEO",    "TRAVESAÑO",    "TRIQUIÑUELA",
                              "TROTAMUNDOS",  "TRONCHAR",     "TUETANO",      "ULTRAMARINO",
                              "URGENCIA",     "UTENSILIO",    "UTOPIA",       "VACUO",
                              "VAGAMENTE",    "VAGABUNDO",    "VANAGLORIAR",  "VEHEMENCIA",
                              "VENDIMIA",     "VENGANZA",     "VERTIGINOSO",  "VICISITUD",
                              "VIRTUALMENTE", "VITUPERIO",    "VORAGINE",     "VORTICE",
                              "WATERPOLO",    "XENOFOBIA",    "XILOFONO",     "YACIMIENTO",
                              "YUGULAR",      "YUXTAPONER",   "ZAHORI",       "ZANGANO",
                              "ZARANDEAR",    "ZUMBIDO"};
  }




Clase PanelAhorcado

  /** Clase interna que es el panel en el que se muestra el dibujo del ahorcado. */
  class PanelAhorcado extends PanelAhorcaLlop
  {
    public PanelAhorcado ()
    {
      super ();
    }

    /** Se sobrecarga la función que pinta el componente para pintar todo, parte, o nada del
        dibujo del ahorcado, según los fallos del jugador.
        Si la partida ha terminado, también se muestra un mensaje con instrucciones para
        iniciar una partida nueva.
        @param grfcs Graphics  : Contexto 'Graphics' sobre el que se pinta. */
    public void paint (Graphics grfcs)
    {
      super.paint (grfcs);

      for (byte i = 0; i < numLtrsMal; i++)
        grfcs.drawImage (clgdo [i], 15, 25, null);

      if (rsltPrtd != EN_CURSO)
      {
        grfcs.setColor (Color.red);
        grfcs.setFont (new Font ("Verdana", Font.BOLD, 16));
        grfcs.drawString ("Pulse 'Enter'", 10, 20);
        grfcs.drawString ("para jugar otra partida.", 10, 35);
      }
    }
  }




Clase PanelLetrasBien

  /** Clase interna que es el panel en el que se muestran las letras acertadas. */
  class PanelLetrasBien extends PanelAhorcaLlop
  {
    public PanelLetrasBien ()
    {
      super ();
    }

    /** Se sobrecarga la función que pinta el componente para:
          1 - Mostar tantos guiones como letras tenga la palabra secreta.
          2 - Mostrar las letras que ha acertado el jugador, ubicadas en su sitio.
        @param grfcs Graphics  : Contexto 'Graphics' sobre el que se pinta. */
    public void paint (Graphics grfcs)
    {
      super.paint (grfcs);

      if (numLtrsPlbrOclt > 0)
      {
        grfcs.setColor (Color.green.darker ());
        int coordX;
        byte anchLtr = 23;
        for (byte i = 0; i < numLtrsPlbrOclt; i++)
        {
          coordX = anchLtr * (i + 1);
          if (ltrsBien [i] != ' ')
            grfcs.drawChars (ltrsBien, i, 1, coordX, 30);
          grfcs.drawRect (coordX, 40, anchLtr - 5, 1);
        }
      }
    }
  }




Clase PanelLetrasMal

  /** Clase interna, que es el panel en el que se muestra las letras que el jugador ha picado,
      y no están en la palabra secreta. */
  class PanelLetrasMal extends PanelAhorcaLlop
  {
    public PanelLetrasMal ()
    {
      super ();
    }

    /** Se sobrecarga la función que pinta el componente para mostrar las letra que el
        jugador ha equivocado.
        @param grfcs Graphics  : Contexto 'Graphics' sobre el que se pinta. */
    public void paint (Graphics grfcs)
    {
      super.paint (grfcs);

      if (numLtrsMal > 0)
      {
        grfcs.setColor (Color.red);
        byte coordX = 0;
        short coordY = 0;
        for (byte i = 0; i < numLtrsMal; i++)
        {
          if (i % 2 == 0)
          {
            coordX = 0;
            coordY += 35;
          }
          coordX += 25;
          grfcs.drawChars (ltrsMal, i, 1, coordX, coordY);
        }
      }
    }
  }




Clase PanelResultado

  /** Clase interna que es el panel en el que se muestra un mensaje según el 'estado de la partida'. */
  class PanelResultado extends PanelAhorcaLlop
  {
    // Estas dos imágenes son 'gifs animados': uno por si el jugador adivina la palabra,
    // y otro por si no lo hace.
    private Image animVict = getImagen ("vict.gif");
    private Image animDerr = getImagen ("derr.gif");

    public PanelResultado ()
    {
      super ();
    }

    /** Se sobrecarga la función que pinta el componente para:
          * Mostrar el nombre del juego: "El Ahorcado".
          * 1 - Si el jugador ha acertado la palabra, sale un mensaje y la animación con la
                cara sonriente.
            2 - Si el jugador ha perdido, sale un mensaje y la animación con la cara triste.
            3 - Si la partida aún no ha terminado, sale un texto con instrucciones.
        @param grfcs Graphics  : Contexto 'Graphics' sobre el que se pinta. */
    public void paint (Graphics grfcs)
    {
      super.paint (grfcs);

      grfcs.setColor (Color.red);
      grfcs.drawString ("El Ahorcado", 20, 40);
      grfcs.setFont (new Font ("Verdana", Font.BOLD, 18));
      switch (rsltPrtd)
      {
        case VICTORIA:
          grfcs.drawString ("¡Felicidades!", 20, 70);
          grfcs.drawString ("Ha salvado", 20, 90);
          grfcs.drawString ("la vida de", 20, 110);
          grfcs.drawString ("un inocente.", 20, 130);
          grfcs.drawImage (animVict, 24, 145, null);
          break;
        case DERROTA:
          grfcs.drawString ("!Qué lástima!", 20, 70);
          grfcs.drawString ("El condenado", 20, 90);
          grfcs.drawString ("no ha podido", 20, 110);
          grfcs.drawString ("ser salvado.", 20, 130);
          grfcs.drawImage (animDerr, 24, 145, null);
          break;
        default:
          grfcs.drawString ("Intente", 20, 100);
          grfcs.drawString ("adivinar", 20, 120);
          grfcs.drawString ("la palabra", 20, 140);
          grfcs.drawString ("secreta.", 20, 160);
          grfcs.drawString ("Pruebe con", 20, 200);
          grfcs.drawString ("diferentes", 20, 220);
          grfcs.drawString ("letras.", 20, 240);
      }
    }
  }





Clase Sonido

  /** Esta clase guarda los efectos sonoros, y proporciona métodos para reproducirlos.
      Si el sonido se carga antes que los hilos, no se les concederá espacio en memoria a todos. */
  class Sonido
  {
    /** Constante entera con el total de clips de la clase. */
    public static final byte NUMERO_CLIPS = 5;

    /** Constante correspondiente al efecto sonoro de rotación de la pieza. */
    public static final byte REPE = 0;
    /** Constante correspondiente al efecto sonoro de completar líneas. */
    public static final byte BIEN = 1;
    /** Constante correspondiente al efecto sonoro de subir nivel. */
    public static final byte MAL = 2;
    /** Constante correspondiente al efecto sonoro de empezar partida. */
    public static final byte VICTORIA = 3;
    /** Constante correspondiente al efecto sonoro de game over. */
    public static final byte DERROTA = 4;

    // Variables de clase. Una representa la tabla de 'Clip's donde
    // se guardan todas las músicas y efectos sonoros para el juego; y la cadena contiene la ruta a la
    // carpeta con las diferentes musiquitas.
    private Clip clip [];

    /** Constructor. Define el clip designado como música de fondo durante la partida, recibe la
        ubicación de los archivos de sonido. */
    public Sonido ()
    {
      /** Las diferentes músicas y efectos sonoros tienen un nombre estandarizado: 'clip0.wav', 'clip1.wav',
        'clip2.wav', etc... Por eso, con el siguiente bucle se pueden meter todos los clips en la tabla. */
      clip = new Clip [NUMERO_CLIPS];
      for (byte indice = 0; indice < NUMERO_CLIPS; indice++)
        try
        {
          AudioInputStream flujo = AhorcaLlop.getClip ("clip" + String.valueOf (indice) + ".wav");
          AudioFormat formato = flujo.getFormat ();
          DataLine.Info informacion = new DataLine.Info (Clip.class, flujo.getFormat (),
                                                         (int) (flujo.getFrameLength () * formato.getFrameSize ()));
          clip [indice] = (Clip) AudioSystem.getLine (informacion);
          clip [indice].open (flujo);
        } catch (IOException ex) {
          System.err.println ("Error al intentar leer el archivo de audio " + indice + ".");
        } catch (LineUnavailableException ex) {
          System.err.println ("Archivo de audio " + indice + " no disponible.\n"
                              + "Puede que otro programa lo esté utilizando.");
        }
    }

    /** Método que hace sonar el efecto sonoro de 'tecla repetida o no válida'. */
    public void repe ()
    {
      efectoSonoro (this.REPE);
    }

    /** Método que hace sonar el efecto sonoro de 'letra acertada'. */
    public void bien ()
    {
      efectoSonoro (this.BIEN);
    }

    /** Método que hace sonar el efecto sonoro de 'letra incorrecta'. */
    public void mal ()
    {
      efectoSonoro (this.MAL);
    }

    /** Método que hace sonar el efecto sonoro de 'palabra secreta adivinada'. */
    public void victoria ()
    {
      efectoSonoro (this.VICTORIA);
    }

    /** Método que hace sonar el efecto sonoro de 'tío ahorcado'. */
    public void derrota ()
    {
      efectoSonoro (this.DERROTA);
    }

    /** Método que hace sonar uno de los clips desde el principio.
      @param efecto byte  : Variable que corresponde a la posición del clip de marras en la tabla. */
    public void efectoSonoro (byte efecto)
    {
      clip [efecto].setFramePosition (0);
      clip [efecto].start ();
    }
  }
}




Clase PanelAhorcaLlop

package ahorcado;

import java.awt.*;
import javax.swing.*;

/** Clase que extiende de 'JPanel', y personaliza un poco su interfaz. */
public class PanelAhorcaLlop extends JPanel
{
  /** Constructor. Pone el fondo blanco, y las letras de fuente 'Verdana', en negrita y de tamaño 22. */
  public PanelAhorcaLlop ()
  {
    super ();
    setBackground (Color.white);
    setFont (new Font ("Verdana", Font.BOLD, 22));
  }

  /** Se sobrecarga la función que pinta el componente; tendrá un par de bordes azules y
      redondeados.
      @param grfcs Graphics  : Contexto 'Graphics' sobre el que se pinta. */
  public void paint (Graphics grfcs)
  {
    super.paint (grfcs);
    grfcs.setColor (Color.blue);
    grfcs.drawRoundRect(10, 10, getSize ().width - 20, getSize ().height - 20, 20, 20);
    grfcs.drawRoundRect(20, 20, getSize ().width - 40, getSize ().height - 40, 10, 10);
  }
}


¿Comentarios, sugerencias?: llopsite.at.yahoo.es | © 2005-07 Albert Lobo

Última actualización: 18-Feb-2007

Hosted by www.Geocities.ws

1