2012-08-31 8 views
5

Ho un JFrame con 2 JPanel in esso: uno PaintPanel (con un metodo paint()) e uno ButtonPanel (con pulsanti). Quando invoco lo PaintPanelPaintPanel (ma facendo clic sul pulsante) il pulsante di ButtonPanel viene dipinto nello PaintPanel! Non è cliccabile o altro, è solo lì.JButton copiato quando si ridisegna?

ho cercato di ricreare il problema con questo codice:

public class Main { 

    public static void main(String[] args) { 
     JFrame frame = new JFrame("frame"); 
     frame.setSize(400,400); 
     frame.setLayout(new GridLayout(2,1)); 
     PaintPanel paint = new PaintPanel(); 
     ButtonPanel buttons = new ButtonPanel(paint); 
     frame.add(paint); 
     frame.add(buttons); 
     frame.setVisible(true); 
    } 
} 

public class PaintPanel extends JPanel{ 
    public void paint(Graphics g){ 
     g.drawRect(10, 10, 10, 10); 
    } 
} 

public class ButtonPanel extends JPanel implements ActionListener{ 

    private PaintPanel paintPanel; 

    public ButtonPanel(PaintPanel paintPanel){ 
     this.paintPanel=paintPanel; 
     JButton button = new JButton("button"); 
     button.addActionListener(this); 
     add(button); 
    } 

    @Override 
    public void actionPerformed(ActionEvent arg0) { 
     paintPanel.repaint();   
    } 
} 

Questa Sould ricreare il problema che ho (scusate per la marcatura di codice dispari, non riesco a farlo bene).

spero davvero uno di voi sa cosa sta succedendo qui, perché io non ...

+1

Tali manufatti di rendering spesso nascono dal non riuscire a onorare la [Opacità] (http://java.sun.com/products/jfc/tsc/articles/painting/index.html#props) proprietà. Inoltre, "i programmi Swing dovrebbero sovrascrivere' paintComponent() 'invece di sovrascrivere' paint() '." - [* Pittura in AWT e Swing: i metodi Paint *] (http://java.sun.com/products/jfc /tsc/articles/painting/index.html#callbacks). – trashgod

risposta

6

Prima di tutto, si dovrebbe ignorare paintComponent() invece di paint(). Fa parte delle migliori pratiche in Swing quando si tratta di personalizzare alcuni pannelli.

In secondo luogo, qui è il codice che funziona per me (non so il motivo per cui il vostro non però: S):

public class Main { 

    public static void main(String[] args) { 

     JFrame frame = new JFrame("frame"); 
     frame.setSize(400, 400); 
     // frame.setLayout(new GridLayout(2, 1)); 
     PaintPanel paint = new PaintPanel(); 
     ButtonPanel buttons = new ButtonPanel(paint); 
     // frame.add(paint); 
     // frame.add(buttons); 
     frame.setVisible(true); 

     JPanel pan = new JPanel(new BorderLayout()); 
     pan.add(paint); 
     pan.add(buttons, BorderLayout.SOUTH); 
     frame.add(pan); 

    } 
} 

class PaintPanel extends JPanel { 

    @Override 
    protected void paintComponent(Graphics g) { 
     super.paintComponent(g); 
     g.setColor(new Color(new Random().nextInt())); 
     g.drawRect(10, 10, 10, 10); 
    } 
} 

class ButtonPanel extends JPanel implements ActionListener { 

    private final PaintPanel paintPanel; 

    public ButtonPanel(PaintPanel paintPanel) { 

     this.paintPanel = paintPanel; 
     JButton button = new JButton("button"); 
     button.addActionListener(this); 
     add(button); 
    } 

    @Override 
    public void actionPerformed(ActionEvent arg0) { 
     if (getParent() != null) { 
      getParent().repaint(); 
     } 
    } 
} 
+1

Spesso si desidera avere super.paintComponent (g); come prima riga nel metodo paintComponent sovrascritto. Cancellerà tutto ciò che non stai disegnando in quella particolare chiamata a ridisegnare. – mrranstrom

+0

@mrranstrom Proprio così! Ho corretto il mio esempio, grazie! – aymeric

+2

+1 per paintComponent e super.paintCompont. @aymeric che devi ricordare, l'oggetto Graphics viene riutilizzato, quindi se non ti prendi il tempo per assicurarti di averlo pulito prima, ti ritroverai con artefatti di pittura inaspettati – MadProgrammer

Problemi correlati