Fundamentos de programación y Programación Orientada a Objetos

Desarrollar programas computacionales para distintas áreas de aplicación, usando las mejores prácticas, herramientas y paradigmas

Manejo de arreglos de una dimensión

Se tienen las notas del primer parcial de los alumnos de dos materias, la materia A y la materia B, cada materia cuenta con 15 alumnos.

Este programa se encarga de mostrar la materia que obtuvo el mayor promedio. Primeramente, el programa pide al usuario ingresar las 15 calificaciones de la materia A y luego las de la materia B, las cuales son guardadas en respectivos arreglos de tipo float.

Mediante un ciclo que recorre los arreglos el programa suma las respectivas calificaciones y divide el resultado entre 15 para sacar los dos promedios.

Finalmente, mediante el uso de sentencias condicionales, determina cual de los dos promedios es mayor e imprime la respuesta.

Los arreglos de ua dimensión nos permiten guardar datos, que podemos utilizar después. La escritura de datos puede ser mediante un ciclo o al declararse el arreglo. La lectura de todos los datos de un arreglo siempre será más fácil con el ciclo for.

Act20c
import java.util.Scanner;
public class Act20c{
    public static void main (String args[]){
        System.out.print('\u000c');
        Scanner sc = new Scanner(System.in);
        int alumnos = 15;
        float sumaA = 0, sumaB=0;
        
        System.out.println("Escriba las calif. de MATERIA A: ");
        float materiaA[] = new float [alumnos];
        for (int i=0; i<alumnos; i++){
            materiaA[i] = sc.nextInt();
            sumaA = sumaA+materiaA[i];
        }
        System.out.println("Escriba las calif. de MATERIA B: ");
        float materiaB[] = new float [alumnos];
        for (int i=0; i<alumnos; i++){
            materiaB[i] = sc.nextInt();
            sumaB = sumaB+materiaB[i];
        }
        if (sumaA/alumnos > sumaB/alumnos)
        System.out.println("\nLa materia que obtuvo el mayor promedio es la materia A");
        else if (sumaA/alumnos == sumaB/alumnos)
        System.out.println("\nAmbas materias tienen el mismo promedio");
        else
        System.out.println("\nLa materia que obtuvo el mayor promedio es la materia B");
    }
}

Manejo de arreglos bidimensionales

El objetivo del programa es crear matrices de n x n (filas x columnas), donde n es un numero entero ingresado por el usuario. Estas matrices deben ser de número impar, así que si se ingresa un número par se le sumará uno para obtener un impar.

Posteriormente, se hace la escritura de la matriz donde se escriben los números de 1 hasta n x n siguiendo la regla para crear cuadros mágicos.

Finalmente se hace la lectura e impresión de la nueva matriz.

Las matrices son arreglos de dos dimensiones, donde cada indice del primer arreglo de filas contiene un arreglo de columnas. El uso correcto de lectura y escritura de las matrices facilita muchas tareas ya que podemos emplear recorridos en distintas direcciones según sea más conveniente.

MagicSquare
import java.util.Scanner;
public class MagicSquare{
    public static void main (String args []){
        System.out.print('\u000c');
        Scanner sc = new Scanner(System.in);
        System.out.print(" Ingresa un numero impar (si no te lo subire a impar):");
        int n = sc.nextInt();
        //subir a impar
        if (n%2==0){
            n++;
        }

        //Escritura de la casilla central de arriba
        int [][] arr = new int [n][n];
        int fa=0, ca=n/2;
        arr[fa][ca] = 1;
        int fn=0, cn=0;
        
        //Escritura de las demas casillas
        for(int numero=2; numero<=n*n; numero++){
            //int fn=0;
            fn = fa-1;
            if(fn<0){
                fn = n-1;
            }
            //operador terciario para fn = condicion ? verdadero : falso.
            //fn = (fa-1)<0 ? n-1 : fa-1;
            //int cn=0;
            
            cn=ca+1;
            if(cn==n){
                cn=0;
            }
            //operador terciario para cn
            //cn = (ca+1)>n ? 0 : ca+1;
            
            if(arr[fn][cn]==0){ 
                arr[fn][cn]=numero;
                fa=fn;
                ca=cn;
            } else{
                fa++;
                arr[fa][ca]=numero;
            }
        }
        
        //Lectura e impresion de la matriz
        for (int f=0; f<arr.length; f++)
        {
            for (int c=0; c<arr[f].length; c++)
            {
                if (arr[f][c]<10){
                    System.out.print(" "+arr[f][c]+" ");
                } else {
                    System.out.print(arr[f][c]+" ");
                }
            }
            System.out.println();
        }
    }
}

Manejo de Strings

Consiste en un decodificador de mensajes. Para codificar estos mensajes se hizo una matriz de n x m  (donde n son las filas y m las columnas) y que se recorría diagonalmente. Finalmente, se ordenaba esa matriz de izquierda a derecha en un String restando uno a cda letra en código ASCII .

Por lo tanto, para decodificar el mensaje es necesario acomodar nuevamente el string en un arreglo con las mismas dimensiones que el original.

Se pide al usuario que ingrese el numero de filas, el numero de columnas y el mensaje codificado. Posterormente, se escribe el mensaje en la matriz de manera diagonal. Después se lee e imprime de izquierda a derecha.

Distintos métodos nos permiten trabajar con String. Estos tambiñe son un tipo de arreglo, ya que podemos seleccionar un caracter en un índice determinado.

Desafio02
import java.util.Scanner;
/*
7 4
UH-LDD-HRC-SQRMQ@DMNNTDCCNLK
4 3
FHH-MMQ-HDD@
3 5
GMY@QDQDC@GMR-@
 */
public class Desfio02
{
    public static void main (String args[])
    {
        System.out.print('\u000c');
        Scanner sc = new Scanner(System.in);
        int rows = sc.nextInt();
        int columns = sc.nextInt();
        while (rows<2 || rows>20)
        {
            rows = sc.nextInt();
            columns = sc.nextInt();
        }
        //mensaje
        sc.nextLine();
        String message = sc.nextLine();
        //Decodificando mensaje
        int index = 0;
        char [][] matrix = new char[rows][columns];
        for(int c=columns-1; c>=0; c--)
        {
            for(int f=0; f<rows;f++)
            {
                if ((message.charAt(index)+0)==45)
                matrix[f][c] = message.charAt(index);
                else
                matrix[f][c] = (char)(message.charAt(index)+1);
                index++;
            }
        }
        //imprimir mensaje decodificado
        for(int f=0; f<matrix.length; f++)
        {
            for(int c=0; c<matrix[f].length;c++)
            {
                System.out.print(matrix[f][c]);
            }
        }
    }
}

Manejo de condicionales

Tenemos n cantidad de piezas y queremos saber:

¿Cuántas piezas tienen un peso entre 7.8 y 12.4 kg?

¿Cuántas con mas de 12.4 kg.?

¿Cuántas con menos de 7.8 kg.?

y ¿Cuál es la cantidad de piezas pesadas?

Para esto creamos cuatro variables contadores que incrementan según si hay una nueva pieza, si el peso de la pieza estña entre 7.8 y 12.4 kg, si es mayor que 12.4 o menor de 7.8 kg.

Además de if, else como sentencias condicionales, puede ser práctico utilizar switch si lo que queremos es evaluar que el valor de una variable sea uno específico.

Piezas
import java.util.Scanner;
public class Piezas
{
    public static void main (String args[])
    {
        System.out.print('\u000c');
        Scanner sc = new Scanner(System.in);
        System.out.println("Ingrese el peso en kg de las piezas (escribir un '0' para terminar el programa)-");
        int piezas = 0, evaluacion1 = 0, evaluacion2 = 0, evaluacion3 = 0;
        float peso = 1;
        while (peso!=0)
        {
            peso = sc.nextFloat();
            if (peso>7.8&&peso<12.4){
                evaluacion1++;
            }
            if (peso>12.5){
                evaluacion2++;
            }
            if (peso<7.8&&peso!=0){
                evaluacion3++;
            }
            if (peso!=0){
                piezas++;
            }
        }
        System.out.println("¿Cuántas piezas tienen un peso entre 7.8 y 12.4 kg.? "+evaluacion1);
        System.out.println("¿Cuántas con mas de 12.4 kg.? "+evaluacion2);
        System.out.println("¿Cuántas con menos de 7.8 kg.? "+evaluacion3);
        System.out.println("Cantidad total de piezas procesadas: "+piezas);
    }
}

Manejo de ciclos

For, while, do-while, son ejemplos de ciclos de iteración. Estos ciclos permiten repetir un proceeso infinidad de veces hasta que se rompa una condición.

En este ejercicio vimos el ciclo de do-while para sacar el factorial de un número. Lo interesante de este ciclo es la realización primero de las intrucciones antes de evaluar la condición.

Antes para mí parecía algo innecesario si ya existe un ciclo while, pero ahora me he dado cuenta que este ciclo tiene su uso indispensable en algunos programas.

Aunque se podría resolver un mismo problema con cualquiera de los ciclos el simple hecho de adaptarlos, cada uno nos facilita más una respectiva tarea.

Factorial
import java.util.Scanner;

public class Factorial
{
    public static void main (String args[])
    {
        System.out.print('\u000c');
        Scanner leer = new Scanner(System.in);
        long n, m, factorial;
        do
        {
            System.out.println("n factorial de un valor comprendido entre 2 y 20");
            n = leer.nextInt();
            System.out.print(n+"! = ");
            for (m = n, factorial = 1; m>=1; factorial*=m--)
            if (m!=1)
            System.out.print(m+"x");
            else
            System.out.print(m+" = ");
            System.out.println(factorial);
        }
        while(n>=2 && n<=20);
    }
}

Manejo de herencia

Tenemos que contar la menor cantidad de fuerza que utiliza un idividuo para moverse en un cuadro con centro 0 y cuatro posiciones a su alrededor.

Para esto se creó una clase individuo que nos devleve la posicion de cada uno de los pies de la persona, y asu vez nos permite cambiar la posicion de sus pies con un set cuando el movimiento sea el que mnor unidades de fuerza consume.

Para esto es necesario evaluar la posición actual de cada pie y la cantidad de unidades que se consumen al moverse en cada una de las 4 posibles posiciones. Finalmente, movemos el respectivo pie a la posición con menor fuerza consumida y agrgamos esa cantidad de fuerza a una variable que mida la cantida de fuerza.

public class Individuo {
    private int pd = 0;
    private int pi = 0;
    private int units = 0;
    public int getPd(){
        return pd;
    }
    public void setPd(int pd){
        this.pd = pd;
    }
    public int getPi(){
        return pi;
    }
    public void setPi(int pi){
        this.pi = pi;
    }
    public int getUnits(){
        return units;
    }
    public void setUnits(int units){
        this.units = units;
    }
}
import java.util.Scanner;

//1 2 2 4 0 1 2 3 4 1 2 3 3 4 2 0 0
public class Desafio05
{
    public static void main (String args[]) {
        System.out.print('\u000c');
        Scanner tec = new Scanner (System.in);
        int pos;
        String seq;
        Individuo white = new Individuo();
        do{
        white.setUnits(0);    
        seq = "";
        do {
            pos = tec.nextInt();
            seq = seq + pos;
        }while(pos!=0);
        int ud, ui;
        for (int n = 0; n<seq.length()-1; n++) {
            ud = 0;
            ui = 0;
            
            if (Math.abs(white.getPd()-seq.charAt(n))==1 || Math.abs(white.getPd()-seq.charAt(n))==3)
            ud = 3;
            if (Math.abs(white.getPd()-seq.charAt(n))==2)
            ud = 4;
            if (Math.abs(white.getPd()-seq.charAt(n))==0)
            ud = 1;
            if (Math.abs(white.getPd()-seq.charAt(n))==seq.charAt(n))
            ud = 2;
            
            if (Math.abs(white.getPi()-seq.charAt(n))==1 || Math.abs(white.getPd()-seq.charAt(n))==3)
            ui = 3;
            if (Math.abs(white.getPi()-seq.charAt(n))==2)
            ui = 4;
            if (Math.abs(white.getPi()-seq.charAt(n))==0)
            ui = 1;
            if (Math.abs(white.getPi()-seq.charAt(n))==seq.charAt(n))
            ui = 2;
            
            if (ui<ud) {
                white.setUnits(white.getUnits()+ui);
                white.setPi(seq.charAt(n));
            }else if (ud<ui) {
                white.setUnits(white.getUnits()+ud);
                white.setPd(seq.charAt(n));
            } else if (ud ==ui) {
                white.setUnits(white.getUnits()+ud);
                white.setPd(seq.charAt(n));
            }
        }
        if (white.getUnits()==0)
        break;
        System.out.println(white.getUnits());
    }while (!seq.contentEquals("00"));
    }
}

Juegos y programas hechos en clase

Realizamos como proyecto final un juego en equipo. El juego consistía ne un cubeOban donde la figura se arrastra y mueve hasta chocar con la pared más próxima. El objetivo es que cada cubo se encuentre con su punto del mismo color.

Son dos niveles y aquí se adjuntan las fotos del diseño de los mismos

Este preoyecto fue muy interesanto porque aplicamos además de lógica la interfaz que el usuario debìa usar y que fuera también atractiva.

import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JButton;
import javax.swing.JOptionPane;
import java.awt.event.MouseListener;
import java.awt.event.MouseEvent;
import java.awt.Dimension;
import java.awt.Container;
import java.awt.FlowLayout;
import java.awt.Color;

public class Nivel1Edg extends JFrame implements MouseListener{
    int botonSize=80; //tamaño de los botones 
    int xRatonAnt, yRatonAnt, xRatonAct, yRatonAct; // posiciones del raton en el panel
    int botonPressed; //1=boton 1, 2=boton 2, 0=ninguno
    int f1=1, c1=1, f2=4, c2=6; //fila y columna de los botones boton 1 y boton 2
    int fGanar1=4, cGanar1=7; // fila y columna de ganar boton 1
    int fGanar2=5, cGanar2=8; //ganar boton 2
    JButton meta1 = new RoundButton();//botones de meta
    JButton meta2 = new RoundButton();
    JButton [][]botones = new JButton[10][12]; //Matriz de botones
    public static void main(String[] args) {
        Nivel1Edg window = new Nivel1Edg();
        window.setVisible(true);
        window.setPreferredSize(new Dimension(980,870));
        window.pack();
        window.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    }
    public Nivel1Edg(){
        super("Nivel 1");
        Container contenedor = getContentPane();
        contenedor.setLayout(new FlowLayout());

        JPanel panel = new JPanel();
        panel.setLayout(null);
        panel.setPreferredSize(new Dimension(960,800));
        panel.setBackground(Color.white);
        contenedor.add(panel);
        panel.addMouseListener(this);
        
        for (int f=0; f<botones.length; f++) {
            for(int c=0; c<botones[f].length; c++) {
                //Colocar los botones de fondo del panel
                if(f==0||f==botones.length-1||c==0||c==botones[f].length-1||(f==5&&c==1)||(f==4&&c==8)){
                    botones[f][c]=new JButton();
                    botones[f][c].setBounds(c*botonSize, f*botonSize, botonSize, botonSize);
                    botones[f][c].setBackground(new Color(52,73,94));
                    panel.add(botones[f][c]);
                }
                //Colocar botones Rojos
                if((f==f1&&c==c1)||(f==f2&&c==c2)){
                    botones[f][c]=new JButton();
                    if(f==f1&&c==c1){
                        botones[f][c].setBackground(new Color(255,51,0));
                    }else if(f==f2&&c==c2){
                        botones[f][c].setBackground(new Color(0,126,229));
                    }
                    botones[f][c].setBounds(c*botonSize, f*botonSize, botonSize, botonSize);
                    panel.add(botones[f][c]);
                    botones[f][c].setBorder(null);
                    botones[f][c].addMouseListener(this);
                }
            }
        }
        meta1.setBounds(cGanar1*botonSize,fGanar1*botonSize,botonSize,botonSize);
        meta1.setBackground(new Color(255,51,0));
        panel.add(meta1);
        meta2.setBounds(cGanar2*botonSize,fGanar2*botonSize,botonSize,botonSize);
        meta2.setBackground(new Color(0,126,229));
        panel.add(meta2);
    }
    
    public void mousePressed(MouseEvent e){
        //Coordenadas del raton ANTES
        if (e.getSource()==botones[f1][c1]){//Si el boton presionado es el boton 1
            xRatonAnt=botones[f1][c1].getX()+e.getX();
            yRatonAnt=botones[f1][c1].getY()+e.getY();
            botonPressed=1;
        } else if (e.getSource()==botones[f2][c2]) { //Si el boton presionado es el boton 2
            xRatonAnt=botones[f2][c2].getX()+e.getX();
            yRatonAnt=botones[f2][c2].getY()+e.getY();
            botonPressed=2;
        } else
            botonPressed=0;
    }
    public void mouseReleased(MouseEvent e){
        //Coordenadas del raton ACTUALES
        if (e.getSource()==botones[f1][c1]) { //Si el boton presionado fue el 1
            xRatonAct=botones[f1][c1].getX()+e.getX();
            yRatonAct=botones[f1][c1].getY()+e.getY();
        } else if (e.getSource()==botones[f2][c2]) { //Si el boton presionado fue el 2
            xRatonAct=botones[f2][c2].getX()+e.getX();
            yRatonAct=botones[f2][c2].getY()+e.getY();
        }
        for (int f=0; f<botones.length; f++) {
            for (int c=0; c<botones[f].length; c++) {
                if(f==0||f==botones.length-1||c==0||c==botones[f].length-1||(f==5&&c==1)||(f==4&&c==8)
                ||(botonPressed==1&&f==f2&&c==c2)||(botonPressed==2&&f==f1&&c==c1)){ //botones prohibidos
                    if ((xRatonAct>c*botonSize&&xRatonAct<c*botonSize+botonSize)
                    &&(yRatonAct>f*botonSize&&yRatonAct<f*botonSize+botonSize)) // Raton se levanta dentro de estos botones
                    botonPressed=0; //es como si ningun boton fue presionado
                }
            }
        }
        
        //DIRECCION del raton
        int fAux=0, cAux=0;
        if (Math.abs(yRatonAct-yRatonAnt)>Math.abs(xRatonAct-xRatonAnt)&&botonPressed!=0) { //Movimiento vertical
            if (yRatonAct>yRatonAnt) {//hacia abajo
                if (botonPressed==1) {
                    fAux=f1;
                    while(botones[fAux+1][c1]==null)
                    fAux++;
                    botones[fAux][c1]=botones[f1][c1];
                    botones[f1][c1]=null;
                    f1=fAux;
                    botones[f1][c1].setLocation(c1*botonSize, f1*botonSize);
                } 
                if (botonPressed==2) {
                    fAux=f2;
                    while(botones[fAux+1][c2]==null)
                    fAux++;
                    botones[fAux][c2]=botones[f2][c2];
                    botones[f2][c2]=null;
                    f2=fAux;
                    botones[f2][c2].setLocation(c2*botonSize, f2*botonSize);
                }
            }
            else if (yRatonAct<yRatonAnt) {//hacia arriba
                if (botonPressed==1) {
                    fAux=f1;
                    while(botones[fAux-1][c1]==null)
                    fAux--;
                    botones[fAux][c1]=botones[f1][c1];
                    botones[f1][c1]=null;
                    f1=fAux;
                    botones[f1][c1].setLocation(c1*botonSize, f1*botonSize);
                }
                if (botonPressed==2) {
                    fAux=f2;
                    while(botones[fAux-1][c2]==null)
                    fAux--;
                    botones[fAux][c2]=botones[f2][c2];
                    botones[f2][c2]=null;
                    f2=fAux;
                    botones[f2][c2].setLocation(c2*botonSize, f2*botonSize);
                }
            }
        } else if (Math.abs(yRatonAct-yRatonAnt)<Math.abs(xRatonAct-xRatonAnt)&&botonPressed!=0) { //Movimiento horizontal
            if (xRatonAct>xRatonAnt) {//a la derecha
                if (botonPressed==1) {
                    cAux=c1;
                    while(botones[f1][cAux+1]==null)
                    cAux++;
                    botones[f1][cAux]=botones[f1][c1];
                    botones[f1][c1]=null;
                    c1=cAux;
                    botones[f1][c1].setLocation(c1*botonSize, f1*botonSize);
                } else if (botonPressed==2) {
                    cAux=c2;
                    while(botones[f2][cAux+1]==null)
                    cAux++;
                    botones[f2][cAux]=botones[f2][c2];
                    botones[f2][c2]=null;
                    c2=cAux;
                    botones[f2][c2].setLocation(c2*botonSize, f2*botonSize);
                }
            }
            else if (xRatonAct<xRatonAnt) {//a la izquierda
                if (botonPressed==1) {
                    cAux=c1;
                    while(botones[f1][cAux-1]==null)
                    cAux--;
                    botones[f1][cAux]=botones[f1][c1];
                    botones[f1][c1]=null;
                    c1=cAux;
                    botones[f1][c1].setLocation(c1*botonSize, f1*botonSize);
                } else if (botonPressed==2) {
                    cAux=c2;
                    while(botones[f2][cAux-1]==null)
                    cAux--;
                    botones[f2][cAux]=botones[f2][c2];
                    botones[f2][c2]=null;
                    c2=cAux;
                    botones[f2][c2].setLocation(c2*botonSize, f2*botonSize);
                }
            }
        }
        
        //Ganar
        if(c1==cGanar1 && f1==fGanar1 && c2==cGanar2 && f2==fGanar2 )
        {
            JOptionPane.showMessageDialog(null,"Nivel 1 - Completado");
            Nivel2Edg.main(null);
            super.dispose();
            
        }
    }
    public void mouseClicked(MouseEvent e){}
    public void mouseEntered(MouseEvent e){}
    public void mouseExited(MouseEvent e){}
}
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JButton;
import javax.swing.JOptionPane;
import java.awt.event.MouseListener;
import java.awt.event.MouseEvent;
import java.awt.Dimension;
import java.awt.Container;
import java.awt.FlowLayout;
import java.awt.Color;
import java.awt.geom.*;
import javax.swing.*;
import javax.swing.border.Border;
import java.awt.Graphics;
import java.awt.Insets;
import java.awt.*;
import java.awt.event.*;
import java.awt.Component;
class Nivel2Edg extends JFrame implements MouseListener{
    int botonSize=80; //tamaño de los botones 
    int xRatonAnt, yRatonAnt, xRatonAct, yRatonAct; // posiciones del raton en el panel
    int botonPressed; //1=boton 1, 2=boton 2, 0=ninguno
    int f1=1, c1=1, f2=1, c2=2, f3=1, c3=3, f4=1, c4=4; //fila y columna de los botones boton 1 y boton 2
    int fGanar1=3, cGanar1=2; // fila y columna de ganar boton 1
    int fGanar2=6, cGanar2=7; //ganar boton 2
    int fGanar3=3, cGanar3=8; // fila y columna de ganar boton 1
    int fGanar4=2, cGanar4=5; //ganar boton 2
    JButton meta1 = new RoundButton();//botones de meta
    JButton meta2 = new RoundButton();
    JButton meta3 = new RoundButton();//botones de meta
    JButton meta4 = new RoundButton();
    JButton [][]botones = new JButton[8][11]; //Matriz de botones
    public static void main(String[] args) {
        Nivel2Edg window = new Nivel2Edg();
        window.setVisible(true);
        window.setPreferredSize(new Dimension(900,690));
        window.pack();
        window.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    }

    public Nivel2Edg(){
        super("Nivel 1");
        Container contenedor = getContentPane();
        contenedor.setLayout(new FlowLayout());

        JPanel panel = new JPanel();
        panel.setLayout(null);
        panel.setPreferredSize(new Dimension(880,640));
        panel.setBackground(Color.white);
        contenedor.add(panel);
        panel.addMouseListener(this);
        panel.setBackground(new Color(236,240,241));
        for (int f=0; f<botones.length; f++) {
            for(int c=0; c<botones[f].length; c++) {
                //Colocar los botones de fondo del panel
                if(f==0||f==botones.length-1||c==0||c==botones[f].length-1|| c == 5 && f==1 || c == 6 && f==2 || c==8 && f==2 || 
                c==1 && f==3 || c==2 && f==4 || c==4 && f==4 || c==6 && f==4 || c==7 && f==5 || c==9 && f==5 || c==4 && f==6 || c==6 && f==6 || c==9 && f==6 || c==9 && f==3){
                    botones[f][c]=new JButton();
                    botones[f][c].setBounds(c*botonSize, f*botonSize, botonSize, botonSize);
                    botones[f][c].setBackground(new Color(52,73,94));
                    panel.add(botones[f][c]);
                }
                //Colocar botones Rojos
                if((f==f1&&c==c1)||(f==f2&&c==c2) || (f==f3&&c==c3) || (f==f4&&c==c4)){
                    botones[f][c]=new JButton();
                    if(f==f1&&c==c1){
                        botones[f][c].setBackground(new Color(255,51,0));
                    }else if(f==f2&&c==c2){
                        botones[f][c].setBackground(new Color(0,126,229));
                    }else if(f==f3&&c==c3){
                        botones[f][c].setBackground(new Color(9,184,62));
                    }else if(f==f4&&c==c4){
                        botones[f][c].setBackground(new Color(65,0,147));
                    }
                    botones[f][c].setBounds(c*botonSize, f*botonSize, botonSize, botonSize);
                    panel.add(botones[f][c]);
                    botones[f][c].addMouseListener(this);
                }
            }
        }
        meta1.setBounds(cGanar1*botonSize,fGanar1*botonSize,botonSize,botonSize);
        meta1.setBackground(new Color(255,51,0));
        panel.add(meta1);
        meta2.setBounds(cGanar2*botonSize,fGanar2*botonSize,botonSize,botonSize);
        meta2.setBackground(new Color(0,126,229));
        panel.add(meta2);
        meta3.setBounds(cGanar3*botonSize,fGanar3*botonSize,botonSize,botonSize);
        meta3.setBackground(new Color(9,184,62));
        panel.add(meta3);
        meta4.setBounds(cGanar4*botonSize,fGanar4*botonSize,botonSize,botonSize);
        meta4.setBackground(new Color(65,0,147));
        panel.add(meta4);
    }

    public void mousePressed(MouseEvent e){
        //Coordenadas del raton ANTES
        if (e.getSource()==botones[f1][c1]){//Si el boton presionado es el boton 1
            xRatonAnt=botones[f1][c1].getX()+e.getX();
            yRatonAnt=botones[f1][c1].getY()+e.getY();
            botonPressed=1;
        } else if (e.getSource()==botones[f2][c2]) { //Si el boton presionado es el boton 2
            xRatonAnt=botones[f2][c2].getX()+e.getX();
            yRatonAnt=botones[f2][c2].getY()+e.getY();
            botonPressed=2;
        } else if(e.getSource()==botones[f3][c3]){
            xRatonAnt=botones[f3][c3].getX()+e.getX();
            yRatonAnt=botones[f3][c3].getY()+e.getY();
            botonPressed=3;
        }else if(e.getSource()==botones[f4][c4]){
            xRatonAnt=botones[f4][c4].getX()+e.getX();
            yRatonAnt=botones[f4][c4].getY()+e.getY();
            botonPressed=4;
        }else
            botonPressed=0;
    }

    public void mouseReleased(MouseEvent e){
        //Coordenadas del raton ACTUALES
        if (e.getSource()==botones[f1][c1]) { //Si el boton presionado fue el 1
            xRatonAct=botones[f1][c1].getX()+e.getX();
            yRatonAct=botones[f1][c1].getY()+e.getY();
        } else if (e.getSource()==botones[f2][c2]) { //Si el boton presionado fue el 2
            xRatonAct=botones[f2][c2].getX()+e.getX();
            yRatonAct=botones[f2][c2].getY()+e.getY();
        } else if(e.getSource()==botones[f3][c3]){
            xRatonAct=botones[f3][c3].getX()+e.getX();
            yRatonAct=botones[f3][c3].getY()+e.getY();
        }else if(e.getSource()==botones[f4][c4]){
            xRatonAct=botones[f4][c4].getX()+e.getX();
            yRatonAct=botones[f4][c4].getY()+e.getY();
        }
        for (int f=0; f<botones.length; f++) {
            for (int c=0; c<botones[f].length; c++) {
                if(f==0||f==botones.length-1||c==0||c==botones[f].length-1||(f==5&&c==1)||(f==4&&c==8)
                ||(botonPressed==1&&f==f2&&c==c2)|| (botonPressed==1&&f==f3&&c==c3)||(botonPressed==1&&f==f4&&c==c4) ||
                (botonPressed==2&&f==f1&&c==c1)|| (botonPressed==2&&f==f3&&c==c3)||(botonPressed==2&&f==f4&&c==c4)||
                (botonPressed==3&&f==f2&&c==c2)|| (botonPressed==3&&f==f1&&c==c1)||(botonPressed==3&&f==f4&&c==c4)||
                (botonPressed==4&&f==f2&&c==c2)|| (botonPressed==4&&f==f3&&c==c3)||(botonPressed==4&&f==f1&&c==c1)){ //botones prohibidos
                  if ((xRatonAct>c*botonSize&&xRatonAct<c*botonSize+botonSize)
                    &&(yRatonAct>f*botonSize&&yRatonAct<f*botonSize+botonSize)) // Raton se levanta dentro de estos botones
                        botonPressed=0; //es como si ningun boton fue presionado
                }
            }
        }

        //DIRECCION del raton
        int fAux=0, cAux=0;
        if (Math.abs(yRatonAct-yRatonAnt)>Math.abs(xRatonAct-xRatonAnt)&&botonPressed!=0) { //Movimiento vertical
            if (yRatonAct>yRatonAnt) {//hacia abajo
                if (botonPressed==1) {
                    fAux=f1;
                    while(botones[fAux+1][c1]==null)
                        fAux++;
                    botones[fAux][c1]=botones[f1][c1];
                    botones[f1][c1]=null;
                    f1=fAux;
                    botones[f1][c1].setLocation(c1*botonSize, f1*botonSize);
                } else if (botonPressed==2) {
                    fAux=f2;
                    while(botones[fAux+1][c2]==null)
                        fAux++;
                    botones[fAux][c2]=botones[f2][c2];
                    botones[f2][c2]=null;
                    f2=fAux;
                    botones[f2][c2].setLocation(c2*botonSize, f2*botonSize);
                } else if (botonPressed==3) {
                    fAux=f3;
                    while(botones[fAux+1][c3]==null)
                        fAux++;
                    botones[fAux][c3]=botones[f3][c3];
                    botones[f3][c3]=null;
                    f3=fAux;
                    botones[f3][c3].setLocation(c3*botonSize, f3*botonSize);
                } else if (botonPressed==4) {
                    fAux=f4;
                    while(botones[fAux+1][c4]==null)
                        fAux++;
                    botones[fAux][c4]=botones[f4][c4];
                    botones[f4][c4]=null;
                    f4=fAux;
                    botones[f4][c4].setLocation(c4*botonSize, f4*botonSize);
                }
            }
            else if (yRatonAct<yRatonAnt) {//hacia arriba
                if (botonPressed==1) {
                    fAux=f1;
                    while(botones[fAux-1][c1]==null)
                        fAux--;
                    botones[fAux][c1]=botones[f1][c1];
                    botones[f1][c1]=null;
                    f1=fAux;
                    botones[f1][c1].setLocation(c1*botonSize, f1*botonSize);
                } else if (botonPressed==2) {
                    fAux=f2;
                    while(botones[fAux-1][c2]==null)
                        fAux--;
                    botones[fAux][c2]=botones[f2][c2];
                    botones[f2][c2]=null;
                    f2=fAux;
                    botones[f2][c2].setLocation(c2*botonSize, f2*botonSize);
                } else if (botonPressed==3) {
                    fAux=f3;
                    while(botones[fAux-1][c3]==null)
                        fAux--;
                    botones[fAux][c3]=botones[f3][c3];
                    botones[f3][c3]=null;
                    f3=fAux;
                    botones[f3][c3].setLocation(c3*botonSize, f3*botonSize);
                }else if (botonPressed==4) {
                    fAux=f4;
                    while(botones[fAux-1][c4]==null)
                        fAux--;
                    botones[fAux][c4]=botones[f4][c4];
                    botones[f4][c4]=null;
                    f4=fAux;
                    botones[f4][c4].setLocation(c4*botonSize, f4*botonSize);
                }
            }
        } else if (Math.abs(yRatonAct-yRatonAnt)<Math.abs(xRatonAct-xRatonAnt)&&botonPressed!=0) { //Movimiento horizontal
            if (xRatonAct>xRatonAnt) {//a la derecha
                if (botonPressed==1) {
                    cAux=c1;
                    while(botones[f1][cAux+1]==null)
                        cAux++;
                    botones[f1][cAux]=botones[f1][c1];
                    botones[f1][c1]=null;
                    c1=cAux;
                    botones[f1][c1].setLocation(c1*botonSize, f1*botonSize);
                } else if (botonPressed==2) {
                    cAux=c2;
                    while(botones[f2][cAux+1]==null)
                        cAux++;
                    botones[f2][cAux]=botones[f2][c2];
                    botones[f2][c2]=null;
                    c2=cAux;
                    botones[f2][c2].setLocation(c2*botonSize, f2*botonSize);
                }else if (botonPressed==3) {
                    cAux=c3;
                    while(botones[f3][cAux+1]==null)
                        cAux++;
                    botones[f3][cAux]=botones[f3][c3];
                    botones[f3][c3]=null;
                    c3=cAux;
                    botones[f3][c3].setLocation(c3*botonSize, f3*botonSize);
                } else if (botonPressed==4) {
                    cAux=c4;
                    while(botones[f4][cAux+1]==null)
                        cAux++;
                    botones[f4][cAux]=botones[f4][c4];
                    botones[f4][c4]=null;
                    c4=cAux;
                    botones[f4][c4].setLocation(c4*botonSize, f4*botonSize);
                }
            }
            else if (xRatonAct<xRatonAnt) {//a la izquierda
                if (botonPressed==1) {
                    cAux=c1;
                    while(botones[f1][cAux-1]==null)
                        cAux--;
                    botones[f1][cAux]=botones[f1][c1];
                    botones[f1][c1]=null;
                    c1=cAux;
                    botones[f1][c1].setLocation(c1*botonSize, f1*botonSize);
                } else if (botonPressed==2) {
                    cAux=c2;
                    while(botones[f2][cAux-1]==null)
                        cAux--;
                    botones[f2][cAux]=botones[f2][c2];
                    botones[f2][c2]=null;
                    c2=cAux;
                    botones[f2][c2].setLocation(c2*botonSize, f2*botonSize);
                }else if (botonPressed==3) {
                    cAux=c3;
                    while(botones[f3][cAux-1]==null)
                        cAux--;
                    botones[f3][cAux]=botones[f3][c3];
                    botones[f3][c3]=null;
                    c3=cAux;
                    botones[f3][c3].setLocation(c3*botonSize, f3*botonSize);
                } else if (botonPressed==4) {
                    cAux=c4;
                    while(botones[f4][cAux-1]==null)
                        cAux--;
                    botones[f4][cAux]=botones[f4][c4];
                    botones[f4][c4]=null;
                    c4=cAux;
                    botones[f4][c4].setLocation(c4*botonSize, f4*botonSize);
                }
            }
        }

        //Ganar
        if(c1==cGanar1 && f1==fGanar1 && c2==cGanar2 && f2==fGanar2 && c3==cGanar3 && f3==fGanar3 && c4==cGanar4 && f4==fGanar4)
        {
            JOptionPane.showMessageDialog(null,"Ultimo nivel completado");
            super.dispose();
        }
    }

    public void mouseClicked(MouseEvent e){}

    public void mouseEntered(MouseEvent e){}

    public void mouseExited(MouseEvent e){}
   
}

class RoundButton extends JButton {

    public RoundButton() {
        setBackground(Color.lightGray);
        setFocusable(false);
        Dimension size = getPreferredSize();
        size.width = size.height = 20;
        setPreferredSize(size);
        setContentAreaFilled(false);
    }

    protected void paintComponent(Graphics g) {
        if (getModel().isArmed()) {
            g.setColor(Color.gray);
        } else {
            g.setColor(getBackground());
        }
        g.fillOval(60/2, 60/2, 19, 19);
        super.paintComponent(g);
    }

    protected void paintBorder(Graphics g) {
        g.setColor(null);
        g.drawOval(70/2, 70/2, 0, 0);
    }
    Shape forma;
    public boolean contains(int x, int y) {
        if (forma == null || !forma.getBounds().equals(getBounds())) {
            forma = new Ellipse2D.Float(0, 0, getWidth(), getHeight());
        }
        return forma.contains(x, y);
    }
}