elhacker.net cabecera Bienvenido(a), Visitante. Por favor Ingresar o Registrarse
¿Perdiste tu email de activación?.

 

 


Tema destacado: Tutorial básico de Quickjs


  Mostrar Temas
Páginas: [1]
1  Programación / Java / Obligar a una clase a tener un cierto método estático. en: 4 Agosto 2023, 10:29 am
Hola.

Quisiera saber si es posible obligar a una clase a tener un método estático que encaje en un cierto patrón. Me explico. Por ejemplo, imaginemos que tenemos una clase "Entero" que pretende implementar las operaciones con números enteros y que tiene un método estático llamado "suma", que básicamente devuelve la suma de dos números enteros pasados por parámetro y cuya declaración es del tipo:

Código
  1. public static Entero suma (Entero entero1, Entero entero2){/*...*/}
  2.  

También podríamos tener una clase "Real" que pretenda implementar las operaciones que se pueden hacer con números reales y que podría tener declarado un método "suma" tipo:


Código
  1. public static Real suma (Real real1, Real real2){/*...*/}
  2.  

Pues bien, me gustaría poder trabajar con una clase que trabaje con elementos de una clase genérica que obligatoriamente tenga declarado un método de este tipo sin importar que sean enteros, reales o lo que sea... Por ejemplo, imaginemos que queremos declarar una clase "Vector", que contendrá elementos de una clase genérica (que pueden ser enteros o reales) y queremos definir la suma de vectores a partir de la suma de sus elementos. Algo así:

Código
  1. public class Vector <Elemento /*Aqui es donde me gustaria indicar que Elemento debe implementar una interfaz, o extender una clase o algo asi*/>
  2. {
  3.    ...
  4.  
  5.    public static Vector <Elemento> suma (Vector <Elemento> vector1, Vector<Elemento> vector2){
  6.        Vector <Elemento> nuevo=new Vector<Elemento> (vector1. getTamanyo());
  7.        for (int i=0; i<nuevo.getTamanyo(); i++){
  8.             nuevo.setElemento(i, Elemento.suma(vector1.getElemento(i),vector2.getElemento(i));
  9.    }
  10.  
  11. }
  12.  

Mi intento ha sido el de declarar una interfaz "Grupo" de la siguiente manera:

Código
  1. public interface Grupo<TipoGrupo extends Grupo>
  2. {
  3.    public static TipoGrupo suma (TipoGrupo e1, TipoGrupo e2);
  4. }
  5.  

Y luego la clase "Entero" declararla así:

Código
  1. public class Entero implements Grupo <Entero> {
  2.  
  3.    ...
  4.  
  5.    public static Entero suma(Entero entero1, Entero entero2){...}
  6.  
  7.  

Pero no funciona... En la interfaz Grupo, en la línea del método "suma", me sale un error que dice que "un tipo de variable no estático como "TipoGrupo" no se puede referenciar desde un entorno estático" lo cual tiene su lógica, y otro error que dice que "falta el cuerpo del método o declararlo abstracto". Si lo declaro abstracto el primer error se mantiene y aparece otro que dice que es ilegal combinar los modificadores static y abstract.

¿Realmente se puede obligar a que una clase tenga un método estático que encaje en una cierta declaración?

Gracias de antemano por la ayuda. Un saludo.
2  Programación / Java / Duda con interfaces gráficas en Java. en: 6 Septiembre 2019, 16:58 pm
Hola.

He tenido una pequeña sorpresa programando interfaces gráficas con Java. He simplificado el código manteniendo el problema para que se haga más sencilla su comprensión. Tenemos una clase Prueba2 que extiende un JFrame:

Código
  1. package prueba2;
  2. import java.awt.event.WindowAdapter;
  3. import java.awt.event.WindowEvent;
  4. import java.io.IOException;
  5. import javax.swing.JFrame;
  6. public class Prueba2 extends JFrame   {
  7.    private PanelPrueba Juego;
  8.    public Prueba2() throws IOException{
  9.        Juego=new PanelPrueba();
  10.        getContentPane().add(Juego);
  11.        addWindowListener(new WindowAdapter(){
  12.            public void windowClosing(WindowEvent e){
  13.                System.exit(0);
  14.            }
  15.        });
  16.       Juego.setVisible(true);
  17. }
  18.    public static void main(String[] args) throws IOException {
  19.        Prueba2 J=new Prueba2();
  20.        J.setBounds(0, 0, 400, 400);
  21.        J.setVisible(true);
  22.    }
  23. }
  24.  

Y otra clase PanelPrueba, que extiende un JPanel e implementa un KeyListener:

Código
  1. package prueba2;
  2.  
  3. import java.awt.Color;
  4. import java.awt.Graphics;
  5. import java.awt.event.KeyEvent;
  6. import java.awt.event.KeyListener;
  7. import static javax.swing.JOptionPane.PLAIN_MESSAGE;
  8. import static javax.swing.JOptionPane.YES_NO_OPTION;
  9. import static javax.swing.JOptionPane.YES_OPTION;
  10. import static javax.swing.JOptionPane.showConfirmDialog;
  11. import javax.swing.JPanel;
  12.  
  13. public class PanelPrueba extends JPanel implements KeyListener {
  14.    public PanelPrueba(){
  15.        setBounds(0,0,200,500);
  16.        addKeyListener(this);
  17.        setFocusable(true);
  18.        requestFocus();
  19. }
  20.    public void paint(Graphics g){
  21.        g.setColor(Color.WHITE);
  22.        g.fillRect(0, 0, 200, 500);
  23.    }
  24.    public void reiniciar() {
  25.        repaint();
  26.    }
  27.    @Override
  28.    public void keyTyped(KeyEvent que) {}
  29.  
  30.    @Override
  31.    public void keyPressed(KeyEvent que)  {
  32.        if(showConfirmDialog(this,"Has ganado,deseas empezar otra partida?","Fin de Partida",YES_NO_OPTION,PLAIN_MESSAGE)==YES_OPTION){
  33.            reiniciar();
  34.        }  
  35.        else{
  36.           System.exit(0);
  37.        }
  38.    }
  39.  
  40.    @Override
  41.    public void keyReleased(KeyEvent que) {}
  42. }

Básicamente lo que pasa cuando aprietas una tecla es que te sale un cuadro de diálogo con dos botones. Si se pulsa "No" la aplicación finaliza y si se pulsa "Sí" vuelve a la situación inicial. La sorpresa está en que si se pulsa "Sí" aparece un molesto texto detrás del JPanel. ¿Alguien sabría explicarme por qué pasa eso, y cómo se puede solucionar el problema?

He estado probando cosas, y si el cuadro de diálogo haces que aparezca con un showMessageDialog en lugar de con un showConfirmDialog el problema desaparece.

Por otro lado, si hago que la clase PanelPrueba extienda un Canvas en lugar de un JPanel el problema desaparece. No obstante, quisiera solucionar el problema con un JPanel, ya que éste es el "peso pesado" de los contenedores, y aporta muchas ventajas, ¿verdad?  ;)

También me gustaría comentar que me han pasado cosas parecidas cuando he añadido objetos de clases JPanel y JButton a un mismo JFrame, y que estos problemas han desaparecido igualmente utilizando Canvas.

Agradezco de antemano cualquier tipo de ayuda o comentario y el tiempo que os haya tomado atenderme.

Un saludo a todos.
3  Programación / Java / Duda manejando eventos de teclado en Java en: 11 Julio 2019, 12:26 pm
Hola.

Soy algo novato en todo esto de las interfaces gráficas y animaciones y tengo algunas dudas con un código en Java que estoy confeccionando. Necesito crear una animación controlada por cuatro teclas del teclado que empiece o se detenga cuando se aprieta un botón con el ratón.

Para eso defino utilizo una clase a la que he llamado Panel:

Código
  1. public class Panel extends Canvas implements Runnable, KeyListener{
  2.  
  3.    //Atributos:
  4.    private int ancho, alto; //el alto y el ancho del panel
  5.    private boolean play=false;//Variable que nos indica si la animación ha comenzado o no.
  6.    //... Más atributos. En general, objetos que deben ser pintados. Y variables que indican lo que
  7.    //tienen que hacer esos objetos durante la animación
  8.  
  9.    //Constructor:
  10.    public Panel(int anch, int alt)
  11.    {
  12.         ancho=anch;
  13.         alto=alt;
  14.         play=false;
  15.         //Se construyen los demás atributos
  16.    }
  17.  
  18.    public void paint (Graphics G)
  19.    {
  20.         //Aquí se pintan algunos de los atributos del objeto utilizando técnicas de doble bouffering
  21.    }
  22.  
  23.    public void update (Graphics G)
  24.    {
  25.        paint (G);
  26.    }
  27.  
  28.    public void actualizar()
  29.    {
  30.        //Nada.. Aquí se actualiza la posición de los objetos (atributos de Panel) que deben ser
  31.        //pintados durante la animación
  32.    }
  33.  
  34.    public void run()
  35.    {
  36.        while (play)
  37.        {
  38.            actualizar();
  39.            repaint();
  40.            try
  41.            {
  42.                Thread.sleep((int)espera);
  43.            }
  44.            catch (InterruptedException E)
  45.            {}
  46.            //Y más cosas que no creo que vengan a cuento.
  47.        }
  48.    }
  49.    public void Iniciar()
  50.    {
  51.        play=true;
  52.        Thread hilo=new Thread(this);
  53.        hilo.start();
  54.    }
  55.    public void Detener()
  56.    {
  57.        play=false;
  58.    }
  59.    //Metodos de KeyListener
  60.    public void keyTyped(KeyEvent e) {
  61.    }
  62.    public void keyPressed(KeyEvent e)
  63.    {
  64.        if (e.getKeyChar()=='a')
  65.        {
  66.            //Se modifican los atributos necesarios para que la animación haga lo que tiene que
  67.            //hacer cuando se pulsa una 'a'
  68.        }
  69.        if (e.getKeyChar()=='s')
  70.        {
  71.            //Lo mismo para la 's'
  72.        }
  73.        if (e.getKeyChar()=='l')
  74.        {
  75.            //...
  76.        }
  77.        if (e.getKeyChar()=='ñ')
  78.        {
  79.            //...
  80.        }
  81.    }
  82.  
  83.    @Override
  84.    public void keyReleased(KeyEvent e)
  85.    {
  86.        if (e.getKeyChar()=='a')
  87.        {
  88.            //Se modifican los atributos necesarios para que la animación haga lo que tiene que
  89.            //hacer cuando se suelta la 'a'
  90.        }
  91.        if (e.getKeyChar()=='s')
  92.        {
  93.           //...
  94.        }
  95.        if (e.getKeyChar()=='l')
  96.        {
  97.           //...
  98.        }
  99.        if (e.getKeyChar()=='ñ')
  100.        {
  101.            //...
  102.        }
  103.    }
  104.  
  105. }
  106.  

Y otra clase, la clase Juego2:

Código
  1. public class Juego2 extends JFrame implements ActionListener
  2. {
  3.    private Panel P;
  4.    private JButton boton;
  5.    private boolean play=false;
  6.    private int anchoP=900, altoP=700;
  7.  
  8.    //El constructor. No creo que tenga mucho interés para lo de mi duda pero lo pongo por si
  9.    //acaso:
  10.    public Juego2()
  11.    {
  12.        P=new Panel (anchoP,altoP);
  13.        boton=new JButton("play");
  14.        setBackground(new Color(240,240,240));
  15.        setLayout(null);        
  16.        boton.addActionListener(this);
  17.  
  18.        getContentPane().add(boton);
  19.        boton.setBounds(20,330,250,30);
  20.  
  21.        getContentPane().add(P);
  22.        P.setBounds(300, 30, anchoP, altoP);
  23.        P.setVisible(true);
  24.  
  25.        addWindowListener(new WindowAdapter(){
  26.            public void windowClosing(WindowEvent e){
  27.                System.exit(0);
  28.            }
  29.        });
  30.    }
  31.  
  32.    //el main
  33.    public static void main(String[] args) {
  34.        final Juego2 F = new Juego2();
  35.        F.setBounds(0, 0, 1300, 800);
  36.        F.setVisible(true);
  37.    }
  38.  
  39.    //El actionPerformed de la clase ActionListener
  40.    public void actionPerformed(ActionEvent e) {
  41.        if (e.getSource()==boton)
  42.        {
  43.            if (play)
  44.            {
  45.                play=false;
  46.                boton.setText("play");
  47.                P.Detener();
  48.            }
  49.            else
  50.            {
  51.                play=true;
  52.                boton.setText("pause");
  53.                P.Iniciar();
  54.            }
  55.        }
  56.    }
  57. }
  58.  

A continuación explicaré el fenómeno que me crea dudas.Cuando el código está listo hago lo siguiente:

1) Ejecuto el código. La cosa va bien, todo se construye y se visualiza correctamente.
2) Le doy al play. Y la animación comienza correctamente.
3) Le doy a una de las teclas controladoras y no ocurre nada. ¡Nada de nada!
4) Hago un 'click' de ratón sobre el panel y desde entonces ya sí funciona todo bien. El 'click' tiene que ser sobre el panel, si lo hago sobre otro punto de la ventana o fuera de ella las teclas controladoras siguen inactivas.

¿Alguien sabe por qué pasa esto y cómo puedo solucionarlo? Es decir, me gustaría que las teclas controladoras funcionasen desde que le doy al play, que no fuese necesario hacer ese 'click'.

Muchas gracias de antemano por vuestro tiempo. Un saludo.
4  Programación / Java / Eventos de ratón y cuadros de texto en Java en: 4 Julio 2019, 09:56 am
Hola muy buenas a todos y a todas.

Antes de nada quisiera aclarar que soy algo nuevo en el foro y tengo poca experiencia en cuanto a exponer dudas sobre códigos. He estado sobre esto en alguno de los posts que hay en el foro y agradezco cualquier sugerencia que me hagáis encaminada a conseguir que ayudarme sea una tarea sencilla.

Hace unos días publiqué una duda en este hilo. Abro un nuevo hilo para ver si resulta algo más interesante y también para comentar que la cosa ha ido avanzando, aunque todavía me queda un pequeño problema por solucionar. Vuelvo a enlazar aquí un vídeo con un ejemplo con lo que debo conseguir. Aquí va el código completo de las clases que he creado para el ejercicio:

Clase Aplicacion:
Código
  1. /*
  2.  * To change this license header, choose License Headers in Project Properties.
  3.  * To change this template file, choose Tools | Templates
  4.  * and open the template in the editor.
  5.  */
  6. package practica.pkg2;
  7.  
  8.  
  9.  
  10. import java.awt.Color;
  11. import java.awt.event.ActionEvent;
  12. import java.awt.event.ActionListener;
  13. import java.awt.event.ItemEvent;
  14. import java.awt.event.ItemListener;
  15. import java.awt.event.WindowAdapter;
  16. import java.awt.event.WindowEvent;
  17. import java.io.IOException;
  18. import javax.swing.JCheckBox;
  19. import javax.swing.JFrame;
  20. import javax.swing.JTextField;
  21.  
  22.  
  23. /**
  24.  *
  25.  * @author joseb
  26.  */
  27. public  class Aplicacion  extends JFrame implements ItemListener,ActionListener{
  28.  
  29.  
  30.  
  31.    private JCheckBox Check1;
  32.    private JCheckBox Check2;
  33.    private JTextField Text;
  34.    private PanelCercles Panel;
  35.    /**
  36.      *
  37.      */
  38.  
  39.  
  40.  
  41.    public   Aplicacion(){
  42.        Panel= new PanelCercles(5,false,false,380,680,new vector(0,0));
  43.  
  44.        this.getContentPane().setBackground(new Color(240,240,240));
  45.  
  46.        Text=new JTextField();
  47.        Check1=new JCheckBox("With Walls");
  48.        Check2=new JCheckBox("Follow mouse");
  49.  
  50.        Check1.addItemListener(this);
  51.        Check2.addItemListener(this);
  52.        Text.addActionListener(this);
  53.  
  54.        getContentPane().setLayout(null);
  55.  
  56.        getContentPane().add(Text);
  57.        Text.setBounds(20,20,250,30);
  58.  
  59.        getContentPane().add(Check1);
  60.        Check1.setBounds(20, 70, 250, 30);
  61.  
  62.        getContentPane().add(Check2);
  63.        Check2.setBounds(20, 120, 250, 30);
  64.  
  65.        getContentPane().add(Panel);
  66.        Panel.setBounds(300, 30, 700, 400);
  67.  
  68.        addWindowListener(new WindowAdapter(){
  69.            public void windowClosing(WindowEvent e){
  70.                System.exit(0);
  71.            }
  72.        });
  73.  
  74.  
  75.  
  76.  
  77.  
  78.  
  79.  
  80.    }
  81.  
  82.    @Override
  83.    public void itemStateChanged(ItemEvent E){
  84.        if(E.getItemSelectable()==Check1){
  85.            Panel.cambiar_walls(Check1.isSelected());            
  86.  
  87.        }
  88.        if(E.getItemSelectable()==Check2){
  89.            Panel.cambiar_mouse(Check2.isSelected());
  90.  
  91.            if (Check2.isSelected()==false)
  92.            {
  93.                Panel.reiniciarAceleraciones();
  94.            }
  95.        }
  96.  
  97.    }
  98.  
  99.    /**
  100.      *
  101.      * @param A
  102.      */
  103.    @Override
  104.    public void actionPerformed(ActionEvent A){  
  105.        if (A.getSource()==Text)
  106.        {
  107.            int n =Integer.parseInt(Text.getText());
  108.            vector c=new vector (0,0);
  109.            c.cambiarx(Panel.obtCentro().obtenerx());
  110.            c.cambiary(Panel.obtCentro().obtenery());
  111.            Panel= new PanelCercles(n,Check1.isSelected(),Check2.isSelected(),380,680,c);
  112.            getContentPane().setLayout(null);
  113.            getContentPane().add(Panel);
  114.            Panel.setBounds(300, 30, 700, 400);
  115.        }
  116.  
  117.    }    
  118.    public void bucle() throws IOException
  119.    {
  120.  
  121.        Panel.actualizar_Bolas();
  122.        Panel.repaint();
  123.    }
  124.    /**
  125.      *
  126.      * @param Args
  127.      */
  128.    public static void main (String Args[]) throws InterruptedException, IOException{
  129.       final Aplicacion F = new Aplicacion();
  130.  
  131.        F.setBounds(0, 0, 1300, 800);
  132.        F.setVisible(true);
  133.  
  134.        while (1==1)
  135.        {
  136.            F.bucle();
  137.            F.setVisible(true);
  138.            Thread.sleep((long)50);
  139.        }
  140.   }
  141. }
  142.  
  143.  

Clase PanelCercles
Código
  1. /*
  2.  * To change this license header, choose License Headers in Project Properties.
  3.  * To change this template file, choose Tools | Templates
  4.  * and open the template in the editor.
  5.  */
  6. package practica.pkg2;
  7.  
  8. import java.awt.Color;
  9. import java.awt.Graphics;
  10.  
  11. import java.awt.event.MouseEvent;
  12. import static java.awt.event.MouseEvent.MOUSE_MOVED;
  13. import java.awt.event.MouseListener;
  14. import java.awt.event.MouseMotionListener;
  15. import java.io.IOException;
  16. import javax.swing.JPanel;
  17.  
  18.  
  19. /**
  20.  *
  21.  * @author joseb
  22.  */
  23. public  class PanelCercles extends JPanel implements MouseMotionListener {
  24.  
  25. private Cercle[] bolas;
  26. private int Nbolas;
  27. private boolean with_walls;
  28. private boolean followmouse;
  29. private vector centro;
  30. private int alto;
  31. private int ancho;
  32.  
  33.  
  34.    public PanelCercles(int Nbols, boolean walls, boolean mouse, int alt, int anch, vector cen){
  35.    vector v,p,a;
  36.    centro=new vector (cen.obtenerx(),cen.obtenery());
  37.    followmouse=mouse;
  38.    with_walls=walls;
  39.    alto=alt;
  40.    ancho=anch;
  41.    setSize(ancho,alto);
  42.    setBackground(Color.WHITE);
  43.    a=new vector(0,1);
  44.    Nbolas=Nbols;
  45.    bolas= new Cercle[Nbolas];
  46.        for (int i =0;i<Nbolas;i++){
  47.        p=new vector((int)(Math.random()*ancho),(int)(Math.random()*alto));
  48.        v=new vector((int)(Math.random()*10-5),(int)(Math.random()*10)-5);
  49.        Color c=new Color((int)(Math.random()*255),(int)(Math.random()*255),(int)(Math.random()*255));
  50.  
  51.        bolas [i]=new Cercle(20,a,v,c,p);
  52.    }
  53.    addMouseMotionListener(this);
  54. }
  55.  
  56.    /**
  57.      *
  58.      * @param G
  59.      */
  60. @Override
  61.    public void paint(Graphics G){
  62.        G.setColor(Color.WHITE);
  63.        G.fillRect(0, 0, 1500,1500);
  64.         for(int i=0;i<Nbolas;i++){
  65.        bolas[i].dibujar(G,true);
  66.  
  67.    }
  68.    for(int i=0;i<Nbolas;i++){
  69.        bolas[i].dibujar(G,false);
  70.  
  71.    }
  72.  
  73.  
  74. }
  75.  
  76. public void actualizar_Bolas() throws IOException{
  77.  
  78.    for (int i=0;i<Nbolas;i++){
  79.  
  80.        bolas[i].actualizar(alto, ancho, with_walls, followmouse, centro);
  81.        //System.out.printf("Centro: ("+obtCentro().obtenerx()+","+obtCentro().obtenery()+")\n\n");
  82.        //System.out.printf("Has actualizado la bola "+i+" "+followmouse+"\n");
  83.  
  84.  
  85.    }
  86. }
  87. @Override
  88. public void mouseDragged(MouseEvent e){}
  89.  
  90. @Override
  91. public void mouseMoved(MouseEvent e){
  92.    //System.out.printf("Estas moviendo el ratón: "+followmouse+"\n");
  93.    if(followmouse==true){
  94.        //System.out.printf("Entras??\n");
  95.        centro.cambiarx(e.getX());
  96.        centro.cambiary(e.getY());
  97.  
  98.    }  
  99. }
  100.  
  101. public void cambiar_mouse(boolean m){
  102.    followmouse=m;
  103. }
  104. public void cambiar_walls(boolean w){
  105.    with_walls=w;
  106. }
  107. public void reiniciarAceleraciones()
  108. {
  109.    for (int i=0;i<Nbolas;i++){      
  110.        bolas[i].initAceleracion();          
  111.    }
  112.  
  113. }
  114. public vector obtCentro()
  115. {
  116.    return centro;
  117. }
  118.  
  119. //
  120. public boolean obtFollowm()
  121. {
  122.    return followmouse;
  123. }
  124.  
  125. }
  126.  

Clase Cercle
Código
  1. /*
  2.  * To change this license header, choose License Headers in Project Properties.
  3.  * To change this template file, choose Tools | Templates
  4.  * and open the template in the editor.
  5.  */
  6. package practica.pkg2;
  7.  
  8. import java.awt.Color;
  9. import java.awt.Graphics;
  10.  
  11. /**
  12.  *
  13.  * @author joseb
  14.  */
  15. public class Cercle {
  16.  
  17.    private int diametre;
  18.    private Color col;
  19.    private vector velocitat;
  20.    private vector acceleracio;
  21.    private vector posicio;
  22.    private vector anterior;
  23.  
  24.  
  25. public Cercle(int diam,vector accel, vector vel, Color color, vector pos){
  26. diametre= diam;
  27. col=color;
  28. posicio=pos;
  29. acceleracio=accel;
  30. velocitat=vel;
  31. anterior=new vector(0,0);
  32.  
  33. }    
  34.  
  35.    public void controlar(int alto,int ancho,boolean with_walls){
  36.        boolean sentido=false;
  37.        if (velocitat.obtenerx()>=0)
  38.        {
  39.            sentido=true;
  40.        }
  41.        if(posicio.obtenerx()>ancho && with_walls==false){
  42.            posicio.cambiarx(posicio.obtenerx()-ancho);          
  43.  
  44.        }
  45.        if(posicio.obtenerx()<0 && with_walls==false){
  46.            posicio.cambiarx(posicio.obtenerx()+ancho);          
  47.  
  48.        }
  49.        if(posicio.obtenery()>alto && with_walls==false){
  50.            posicio.cambiary(posicio.obtenery()-alto);          
  51.  
  52.        }
  53.        if(posicio.obtenery()<0 && with_walls==false){
  54.            posicio.cambiary(posicio.obtenery()+alto);          
  55.  
  56.        }
  57.  
  58.        if(posicio.obtenerx()>ancho && with_walls==true){
  59.            posicio.cambiarx(-posicio.obtenerx()+2*ancho);
  60.            velocitat.cambiarx(-velocitat.obtenerx());
  61.  
  62.        }
  63.        if(posicio.obtenerx()<0 && with_walls==true){
  64.            posicio.cambiarx(-posicio.obtenerx());  
  65.            velocitat.cambiarx(-velocitat.obtenerx());
  66.  
  67.        }
  68.        if(posicio.obtenery()>alto && with_walls==true){
  69.            posicio.cambiary(-posicio.obtenery()+2*alto);
  70.            velocitat.cambiary(-velocitat.obtenery());
  71.  
  72.        }
  73.        if(posicio.obtenery()<0 && with_walls==true){
  74.            posicio.cambiary(-posicio.obtenery());
  75.            velocitat.cambiary(-velocitat.obtenery());
  76.  
  77.        }
  78.        if (velocitat.limitaciomod(20))
  79.        {
  80.            if (sentido&&velocitat.obtenerx()==0)
  81.            {
  82.                velocitat.cambiarx(2);
  83.            }
  84.            if (!sentido&&velocitat.obtenerx()==0)
  85.            {
  86.                velocitat.cambiarx(-2);
  87.            }
  88.  
  89.        }
  90.  
  91.    }
  92.    public void actualizar(int alto,int ancho,boolean with_walls,boolean followmouse,vector puntero){
  93.        double k=0.1;
  94.        anterior.cambiarx(posicio.obtenerx());
  95.        anterior.cambiary(posicio.obtenery());
  96.  
  97.        if(followmouse){
  98.            acceleracio.cambiarx(puntero.obtenerx());
  99.            acceleracio.cambiary(puntero.obtenery());
  100.            acceleracio.resta(posicio);
  101.            acceleracio.multiplicacion(k);
  102.  
  103.        }
  104.  
  105.        velocitat.suma(acceleracio);
  106.  
  107.        posicio.suma(velocitat);
  108.  
  109.        controlar(alto,ancho,with_walls);
  110.  
  111.  
  112.    }
  113.    public void dibujar(Graphics pincel, boolean blanco){
  114.       if(blanco==true){
  115.        Color d=new Color (255,255,255);
  116.        pincel.setColor(d);
  117.        pincel.fillOval(anterior.obtenerx(), anterior.obtenery(), diametre, diametre);
  118.        pincel.drawOval(anterior.obtenerx(), anterior.obtenery(), diametre, diametre);  
  119.       }
  120.  
  121.  
  122.       else{
  123.        pincel.setColor(col);
  124.        pincel.fillOval(posicio.obtenerx(), posicio.obtenery(), diametre, diametre);
  125.  
  126.        Color c = new Color(0,0,0);
  127.        pincel.setColor(c);
  128.        pincel.drawOval(posicio.obtenerx(), posicio.obtenery(), diametre, diametre);
  129.       }
  130.    }
  131.  
  132.    public vector obtenerAceleracion ()
  133.    {
  134.        return  acceleracio;
  135.    }
  136.    public vector obtenerVelocidad (){
  137.       return velocitat;
  138.    }
  139.    public vector obtenerPosicion(){
  140.       return posicio;
  141.    }
  142.    public vector obtenerAnterior(){
  143.       return anterior;
  144.    }
  145.    public void initAceleracion()
  146.  
  147.    {
  148.        acceleracio=new vector(0,1);
  149.    }
  150.  
  151. }
  152.  
  153.  

Clase vector
Código
  1. /*
  2.  * To change this license header, choose License Headers in Project Properties.
  3.  * To change this template file, choose Tools | Templates
  4.  * and open the template in the editor.
  5.  */
  6. package practica.pkg2;
  7.  
  8. import static java.lang.Math.sqrt;
  9.  
  10. /**
  11.  *
  12.  * @author joseb
  13.  */
  14. public class vector {
  15.  
  16. private int x;
  17. private int y;
  18.  
  19.  
  20. public vector(int posx, int posy){
  21. x=posx;
  22. y=posy;
  23.  
  24. }
  25.  
  26.    vector() {
  27.        throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates.
  28.    }
  29. public void suma(vector a){
  30.  x=a.x+x;
  31.  y=a.y+y;    
  32. }
  33.  
  34. public void resta(vector a){
  35.  x=x-a.x;
  36.  y=y-a.y;    
  37. }
  38.  
  39.  
  40. public void multiplicacion(double k){
  41.  
  42.  x=(int) (k*x);
  43.  y=(int) (y*k);
  44.  
  45. }
  46. public void division(double k){
  47.  
  48.  x=(int) (x/k);
  49.  y=(int) (y/k);
  50.  
  51. }
  52.  
  53.  
  54.  
  55. public double modulo(){
  56.    return  sqrt(x*x+y*y);
  57.  
  58. }
  59.  
  60. public void unitari(){
  61.    division(modulo());
  62. }
  63.  
  64. public boolean limitaciomod(double Max){
  65.    if(modulo()>Max){
  66.        multiplicacion(Max/modulo());
  67.        return true;
  68.  
  69.    }
  70.    return false;
  71. }
  72. /*
  73. public void limitaciox(int with_walls,int ancho){
  74.     if(x>ancho)
  75.    
  76. }*/
  77. public  int obtenerx(){
  78.    return x;
  79. }
  80. public  int obtenery(){
  81.  
  82.    return y;
  83. }
  84. public void cambiarx(int nueva){
  85.    x=nueva;
  86. }
  87. public void cambiary(int nueva){
  88.    y=nueva;
  89. }
  90.  
  91. }
  92.  

El programa empieza bien. Responde correctamente al cambio de estado de las casillas de activación y al movimiento del puntero del ratón sobre el panel de bolas. Cuando en el cuadro de texto cambio del número de bolas también hace lo correcto, es decir, crear un nuevo panel con ese número de bolas y las visualiza correctamente. No obstante, después de cambiar ese parámetro, el programa no responde bien al cambio de estado de la casilla de activación "Follow mouse".

No alcanzo a entender dónde está el problema. Creo que está relacionado con la gestión de eventos de ratón. En concreto el método mouseMoved de la clase PanelCercles funciona de una manera un tanto aleatoria. Sí que se ejecuta cuando toca, pero el parámetro booleano followmouse lo lee de manera un tanto aleatoria (o eso es lo que a mí, dentro de mi ignorancia, me parece). Además, cuando lo lee como true entra en el condicional para cambiar el parámetro centro pero no lo hace. Insisto en que el problema sólo aparece después de cambiar, al menos una vez, el número de bolas en el cuadro de texto correspondiente.

He puesto una serie de "printf"s ocultos al compilador para que si ejecutáis el código y quitáis las barras // veáis lo que os digo. Esos "printf"s están en las líneas 81, 82, 92 y 94 de la clase PanelCercles.

El primero de ellos es para mostrar que el atributo centro no cambia.
El segundo es para mostrar que en este punto del código el atributo followmouse es correcto. Es decir, corresponde con el estado de la casilla de activación "Follow mouse".
El tercero es para mostrar que en este punto el atributo followmouse puede cambiar en relación al punto anterior. Su estado aquí es aleatorio, a veces toma el valor true y a veces el valor false, y no cambia con el estado de la casilla de activación correspondiente.
El cuarto es para mostrar que a veces entra en el condicional en el que se debería cambiar el atributo centro, pero como se ve en el primer "printf" no lo hace.

En fin, estoy algo perdido con esto. ¿Cómo lo veis vosotros? ¿Tenéis alguna sugerencia o idea. Utilizo el NetBeans en un Windows 10.

Agradezco de antemano cualquier tipo de comentario o de ayuda. Un saludo.
5  Programación / Java / Simulación gráfica animada en: 26 Junio 2019, 08:30 am
Hola, buenos días.

Estoy haciendo una especie de animación simulada con java y resulta que soy algo nuevo en esto de la programación gráfica, por lo que tengo muchas dudas. Voy a intentar subiros los fragmentos de código que me generan más dudas de la manera más resumida posible para ver si podéis echarme una mano, ya que el programa no funciona. Gracias a todos y todas de antemano.

Pues bien, la simulación lo que tiene que hacer es dibujar unos círculos en un panel que se deben ir moviendo según unos parámetros booleanos que introducimos en unas casillas de activación. El número de círculos que se deben dibujar se introducen en un cuadro de texto. En este enlace hay un vídeo con el resultado que debo conseguir.

Lo que creo que debo hacer es definir:

Una clase vector con las operaciones básicas que se pueden hacer con los vectores en dos dimensiones. Esto va bien.

Una clase circulo con los atributos de cada uno de los círculos (diámetro, color, posición, velocidad, aceleración), con un método pintar que dibuje un círculo a partir de un objeto de la clase graphics y otro método actualizar que en cada iteración actualice la posición de un círculo según sus propios atributos. También contiene otros métodos. Esto creo que también va más o menos bien.

Una clase Panel, que debe ser un panel gráfico sensible a los movimientos del ratón que contenga como atributos una colección de círculos y los datos de la IGU. Aquí empiezan mis problemas. Entiendo, en un principio, que Panel podría ser una subclase de java.awt.graphics2D y que podría utilizar la interfaz MouseMotionListener.

Un programa principal que contenga la definición y comportamiento de la interfaz. Mi idea es hacer esto con una subclase de JFrame, pero también ando algo perdido con esto.

Bueno, ahí va lo que en un principio había concebido para la clase Panel. Lo que ocurrió es me surgieron muchos problemas y lo fui modificando. Entre esos problemas, el NetBeans me obligaba a poner un abstract en la declaración de la clase. Pero no me daba buena espina eso, por lo que también fui probando con la clase java.awt.Canvas sin conseguir mucho. En cualquier caso, me gustaría hacerlo con graphics2D:

Código:
public class Panel extends java.awt.graphics2D implements MouseMotionListener
{
    //Atributos de la clase. No creo que tenga problemas aquí.
    circulo bolas[]; // Un array con las bolas;
    int nbolas; // El número de bolas
    boolean follow_mouse // Nos indica si la casilla Follow Mouse está activada o no.
    //...

    //Luego el constructor.
    public Panel (int Nbolas, boolean walls, boolean mouse, int ancho, int alto)
    {
        setSize(ancho, alto); // Dimensiono el panel
        bolas = new circulo (...);  // Reservo memoria para el array de círculos y construyo
                                              //esos círculos según el constructor de esa clase.
        // Y otras cosas así
        //...
    }
    //...

    public void paintComponent (Graphics g)
    {
        //Aquí hay un bucle en el que llamo al método [b]pintar [/b] para cada uno de los
        //circulos del array introduciéndolo el arguento g.
    }
    public void actualizarBolas (void);
    {
        //Aquí hay un bucle en el que llamo al método [b]actualizar[/b] para cada uno de
        //los circulos del array
    }

    //Los métodos de la interfaz.
    //Cuando el ratón se mueva y en el caso de que la casilla Follow Mousse esté activada
    //se debe cambiar el centro del movimiento
    public void mouseDragged (MouseEvent e)
    {
        if (follow_mouse==1)
        {
            Centro.cambiarx(e.getX());
            Centro.cambiary(e.getY());
        }
    }
    public void mouseDragged (MouseEvent e) {}
}

Y ahora un esbozo de la clase principal. Creo que aquí es donde la lío más. Me gustaría hacerlo con un JFrame, aunque si tuviese que cambiar de clase no me importaría con tal de que el programa funcionase. Esto lo fui también modificando de una manera un tanto arbitraria, pero nada. Ni siquiera fui capaz de visualizar el panel:

Código:
public class app extends JFrame implements ItemListener, ActionListener
{
    //Atributos:
    JCheckBox check1, check2;
    JTextField text;
    Panel p;
    Graphics g;
   
    //Constructor. No creo que esto esté bien:
    public app()
    {
        p=new Panel(....) // Construyo el panel con unos parámetros adecuados.
        Container c=getContentPane();
        check1=new JCheckBox("With walls");
        check2=new JCheckBox("Follow mouse");
        text=new JTextField (20);

        check1.addItemListener(this);
        check2.addItemListener(this);
        text.addActionListener(this);

        c.add(check1);
        c.add(check2);
        c.add(p);

       
 
    }
   
    //Los métodos de las interfaces:
    public void itemStateChanged (ItemEvent e)
    {
        if (e.getItemSelectable==check1)
        {
              p.cambiarWalls(check1.isSelected());
        }
        if (e.getItemSelectable==check2)
        {
              p.cambiarMouse(check2.isSelected());
        }
 
    }
    public void actionPerformed (ActionEvent e)
    {
        if (e.getSource==text)
        {
             //Aquí obtengo el texto que hay en el cuadro, lo paso a un int y vuelvo a
             //construir el panel p con los parámetros actuales.
        }
    }
    // El main.
    public static void main (String args[])
    {
        final JFrame f=new app();
        fsetBounds(50,50,500,500);
        f.setVisible(true);

        // Y ahora el bucle que crea la simulación. No estoy seguro de que esto vaya aquí,
        // pero  no sé dónde meterlo... :)
        while (1==1)
        {
             p.paintComponent(g);
             p.actualizarBolas();
             p.repaint();
        }
    }
}

A ver qué os parece. Yo estoy bastante perdido y falto de ideas.

Muchísimas gracias de antemano por vuestro tiempo.
6  Programación / Programación C/C++ / Problemas con CodeBlocks en: 7 Junio 2019, 12:53 pm
Hola, buenos días.

Me he instalado el CodeBlocks 17.12 en un Windows 10 hace unos días para crear, principalmente, aplicaciones de consola con C. Resulta que parece que compila bien el código que sea, ya que CodeBlocks lo ejecuta correctamente (supongo que en una especie de simulación o algo así). Sin embargo, cuando le doy directamente al ejecutable que se haya en la carpeta "...\bin\Debug" me sale un cuadro de diálogo cuyo mensaje no entiendo y que dice: "La ejecución de código no puede continuar porque no se encontró libgcc_s_dw2-1.dll. Este problema se puede solucionar reinstalando el programa". Le doy a la única opción, "Aceptar", y todo desaparece.

He desinstalado y reinstalado el CodeBlocks pero la cosa sigue igual. El proyecto está en una carpeta cuyo nombre no tiene espacios que se haya directamente en la raíz del disco duro.

¿Alguien sabe cómo puedo hacer para que el CodeBlocks me genere ese ejecutable correctamente?

Gracias de antemano por las respuestas. Un saludo.
7  Programación / Programación C/C++ / Entrada y salida con formato en: 6 Abril 2019, 10:36 am
Hola buenas.

Tengo un problema con un programa en el que pretendo utilizar el especificador de formato %g. Según tengo entendido la entrada puede hacerse por teclado introduciendo, por ejemplo, 2e-4. Lo que quiere decir 0.0002. Pues bien, introduzco el dato y luego al mostrarlo por pantalla me sale algo que no tiene nada que ver. El código es el siguiente:

main()
{
double x;
scanf("%g",&x);
printf("%g",x);
}

Como ya he dicho, al imprimir por pantalla el número que he introducido previamente por teclado me sale algo que no tiene nada que ver. Por ejemplo, meto 2e-4 y me imprime 1.#NAN . O sea, que algo no funciona bien. ¿Alguien sabe qué es lo que está pasando?

Agradezco de antemano cualquier ayuda. Un Saludo.
Páginas: [1]
WAP2 - Aviso Legal - Powered by SMF 1.1.21 | SMF © 2006-2008, Simple Machines