Results 1 to 7 of 7
Thread: JButton Problem
- 04-26-2011, 10:37 PM #1
Member
- Join Date
- Apr 2011
- Posts
- 24
- Rep Power
- 0
JButton Problem
Ok so I'm trying to create a basic JFrame class that has a JPanel on the bottom half and buttons on the top half. The JPanel class uses mouse events to draw lines (similiar to Paint or a drawing program) and the Buttons on the top half are suppose to change the color of the lines drawn and to clear the JPanel screen. I keep getting NullPointerExceptions and have no idea why.
Class 1 (JPanel + JFrame test class):
Class 2 (Buttons):Java Code:import javax.swing.JComboBox; import javax.swing.SwingUtilities; import javax.swing.JFrame; import javax.swing.JPanel; import javax.swing.BorderFactory; import java.awt.Color; import java.awt.Dimension; import java.awt.Frame; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.GridLayout; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.MouseEvent; import java.awt.event.MouseListener; import java.awt.event.MouseAdapter; import java.awt.event.MouseMotionListener; import java.awt.event.MouseMotionAdapter; public class Scribble extends JPanel { public static void main(String[] args) { SwingUtilities.invokeLater(new Runnable() { public void run() { createAndShowGUI(); } } ); } private static void createAndShowGUI() { MyPanel myPanel1 = new MyPanel(); ColorBox f = new ColorBox(myPanel1); f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); f.pack(); f.setVisible(true); } private ColorBox f; private JComboBox facenameCombo; private String facename; private ActionListener listener; private static final int FRAME_WIDTH = 600; private static final int FRAME_HEIGHT=800; private Graphics2D g2; private JPanel panel; public Color color; } class MyPanel extends JPanel { private int last_x; private int last_y; private int x; private int y; private Graphics g; public MyPanel() { setBorder(BorderFactory.createLineBorder(Color.black)); addMouseListener(new MouseAdapter() { public void mousePressed(MouseEvent e) { last_x = e.getX(); last_y = e.getY(); } } ); addMouseMotionListener(new MouseAdapter() { public void mouseDragged(MouseEvent e) { x = e.getX(); y = e.getY(); repaint(); } } ); } public void Clear() { repaint(); } public Dimension getPreferredSize() { return new Dimension(250,200); } protected void paintComponent(Graphics g, Color color) { g.drawString("This is my custom Panel!",10,20); g.setColor(color); g.drawLine(last_x, last_y, x, y); last_x = x; last_y = y; } }
All I know is that whenever the ClearButton is clicked nothing happens (if i remove MyPanel mypanel = new MyPanel(); statement, it becomes NullPointerException) so that means it is not running the Clear method (not sure why tho) and whenever I change the color on the JComboBox the color changes in the setColor method, but whenever the getColor method is accesssed, the color is null. I'm using Java Eclipse and any help would be much appreciated =)Java Code:import javax.swing.JButton; import javax.swing.JFrame; import java.applet.*; import javax.swing.JPanel; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import javax.swing.JComboBox; import java.awt.BorderLayout; import java.awt.Color; import java.awt.Graphics2D; import java.awt.event.*; import java.awt.*; import javax.swing.*; import java.awt.GridLayout; public class ColorBox extends JFrame { private MyPanel myPanel; public ColorBox(MyPanel myPanel) { this.myPanel = myPanel; Color color = Color.black; class ChoiceListener implements ActionListener { public void actionPerformed (ActionEvent event) { JComboBox cb = (JComboBox) event.getSource(); Object newItem = cb.getSelectedItem(); setColor((String) newItem); } } listener = new ChoiceListener(); setLayout(new GridLayout(2,2)); createControlPanel(); setSize(FRAME_WIDTH, FRAME_HEIGHT); System.out.println("Constructor " + color); } public void createControlPanel() { JPanel facenamePanel = createComboBox(); JPanel clearPanel = createClearBox(); JPanel scribble = new MyPanel(); JPanel controlPanel = new JPanel(); controlPanel.setLayout(new GridLayout(3,1)); controlPanel.add(facenamePanel); controlPanel.add(clearPanel); controlPanel.add(scribble); add(controlPanel); } public JPanel createComboBox() { facenameCombo = new JComboBox(); facenameCombo.addItem("Black"); facenameCombo.addItem("Blue"); facenameCombo.addItem("Red"); facenameCombo.addItem("Blue"); facenameCombo.addItem("Green"); facenameCombo.addItem("Orange"); facenameCombo.addItem("Pink"); facenameCombo.addItem("Yellow"); facenameCombo.setEditable(true); facenameCombo.addActionListener(listener); JPanel panel = new JPanel(); panel.add(facenameCombo); return panel; } public void setColor(String newItem) { if (newItem.equals("Blue")) color = (Color.BLUE); else if(newItem.equals("Black")) color = (Color.BLACK); else if (newItem.equals("Blue")) color = (Color.BLUE); else if (newItem.equals("Red")) color = (Color.RED); else if (newItem.equals("Green")) color = (Color.GREEN); else if (newItem.equals("Orange")) color = (Color.ORANGE); else if (newItem.equals("Pink")) color = (Color.PINK); else if (newItem.equals("Yellow")) color = (Color.YELLOW); System.out.println("setColor method " + color); getColor(); } public void getColor() { System.out.println(color); } public JPanel createClearBox() { clearButton = new JButton("Clear"); clearButton.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { myPanel.Clear(); } }); JPanel panel = new JPanel(); panel.add(clearButton); return panel; } private JComboBox facenameCombo; private JButton clearButton; private ActionListener listener; private static final int FRAME_WIDTH = 600; private static final int FRAME_HEIGHT=800; private JPanel panel; public Color color; private MyPanel mypanel; }Last edited by PorgrammingNoob117; 04-28-2011 at 10:46 PM.
-
When you create a new MyPanel object in your clear button's action listener, you must understand that this is a completely new and distinct object from the MyPanel object that is being displayed, and so calling methods on the MyPanel object in the listener will have absolutely no effect on the MyPanel object that is being displayed.
To solve this, your ColorBox class needs a reference to the MyPanel class so that it can peform actions on the MyPanel that the user sees. One way is to pass the ColorBox class a reference to the MyPanel object via a constructor parameter. Something like:
Java Code:private static void createAndShowGUI() { MyPanel myPanel = new MyPanel(); // create the MyPanel object for display ColorBox f = new ColorBox(myPanel); // pass it into ColorBox f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); // f.add(new MyPanel()); // don't even need this f.pack(); f.setVisible(true); }
And you'd change your ColorBox class to allow it to accept the reference passed into its constructor and place it into your class MyPanel field that you already have:
Java Code:public class ColorBox extends JFrame { public ColorBox(MyPanel myPanel) // allow constructor to accept reference to myPanel { this.myPanel = myPanel; // set the myPanel field to hold this reference Color color = Color.black; // .... etc...
Then you can use this reference in your inner class listener:
Java Code:public JPanel createClearBox() { clearButton = new JButton("Clear"); clearButton.addActionListener(new ActionListener() { // MyPanel mypanel = new MyPanel(); // no need for this now as we have the reference! public void actionPerformed(ActionEvent e) { mypanel.clear(); } }); JPanel panel = new JPanel(); panel.add(clearButton); return panel; }
- 04-27-2011, 10:50 PM #3
Member
- Join Date
- Apr 2011
- Posts
- 24
- Rep Power
- 0
Ok 2 things: One I actually do need the f.add(new MyPanel()); or else the class won't be added to the JFrame and second the Statement actually runs, but doesn't clear the screen because the repaint method just runs the paintComponent() and justs draw another line at the previous location. The only thing I can thing of is adding a super.paintComponent(g) to the paintComponent method, but that will never allow me to draw lines and I could try to minimize and reopen the frame using frame.setState(FRAME.NORMAL or FRAME.ICONIFIED), but that requires me accessed the Scribble class as well....
-
No, in fact you don't, not if you add the JPanel to the JFrame in the JFrame-extending class's constructor. If you follow my recommendation, the ColorBox class will get an instance of MyPanel passed into its constructor and you can use this instance and add it to the JFrame's contentPane.
Adding super.paintComponent(g) is in fact a great idea and I heartily endorse it, and it should not prevent you from drawing lines if it's the first method in the paintComponent override. Your MyPanel class should hold and ArrayList of Point that is added to by the MouseListener and your paintComponent method should iterate through this list drawing the lines. Also you should not create new ColorBox object in paintComponent but rather if you need to access pass an instance of ColorBox into MyPanel. You would probably need a setter method for this in MyPanel, i.e.,and second the Statement actually runs, but doesn't clear the screen because the repaint method just runs the paintComponent() and justs draw another line at the previous location. The only thing I can thing of is adding a super.paintComponent(g) to the paintComponent method, but that will never allow me to draw lines and I could try to minimize and reopen the frame using frame.setState(FRAME.NORMAL or FRAME.ICONIFIED), but that requires me accessed the Scribble class as well....
Java Code:public void setColorBox(ColorBox colorBox) { this.colorBox = colorBox; }
- 04-28-2011, 10:20 PM #5
Member
- Join Date
- Apr 2011
- Posts
- 24
- Rep Power
- 0
What I am saying is if I add super.paintComponent(g) to paintComponent such as this:
What will happen is whenever I'm trying to draw, the lines disappear because they are being cleared when the mouseAction accesses the paintComponent method.Java Code:protected void paintComponent(Graphics g) { super.paintComponent(g); g.drawString("This is my custom Panel!",10,20); g.drawLine(last_x, last_y, x, y); last_x = x; last_y = y; }
Also if I add the super.paintComponent(g); in the clear method:
Post*Java Code:public void clear() { super.paintComponent(g); }
I get the NullPointerException....
*Edit Updated Code in First Post*Last edited by PorgrammingNoob117; 04-28-2011 at 10:47 PM.
-
Right, and that's because your paintComponent method only draws one line. If you want it to draw multiple lines, you need to do what I told you to in my post above: create an ArrayList of data, and then in paintComponent iterate through the list in a loop and draw multiple lines. Regardless, super.paintComponent(g) should be the first call of your paintComponent method.
Yeah, that's a very bad idea; don't do it.Also if I add the super.paintComponent(g); in the clear method:
I get the NullPointerException....Java Code:public void clear() { super.paintComponent(g); }
- 04-29-2011, 10:53 PM #7
Member
- Join Date
- Apr 2011
- Posts
- 24
- Rep Power
- 0
Similar Threads
-
Problem with JButton
By yontan8888 in forum AWT / SwingReplies: 2Last Post: 03-09-2011, 05:10 PM -
Jbutton problem
By blue50 in forum AWT / SwingReplies: 10Last Post: 12-01-2010, 04:43 AM -
JButton click problem
By mine0926 in forum NetBeansReplies: 7Last Post: 06-11-2010, 03:00 AM -
JButton Problem
By wassim in forum AWT / SwingReplies: 6Last Post: 02-18-2009, 10:29 PM -
Problem with JButton
By Marcus in forum AWT / SwingReplies: 1Last Post: 07-05-2007, 05:56 AM


LinkBack URL
About LinkBacks
Reply With Quote

Bookmarks