Results 1 to 11 of 11
  1. #1
    gothrog is offline Member
    Join Date
    May 2010
    Posts
    6
    Rep Power
    0

    Default setColor() gives a null error on execution

    I am trying to create a circle. Everything compiles, but dies during the execution. I have a button that is supposed to add the circle graphics to the screen. The buttons and the event action listener works otherwise it wouldn't get this far.

    Can anyone help?

    The error message printed when it hits the setColor() function is "null".
    I assume that is because it thinks g is null. I'm confused in how to new g, since it doesn't let me. Graphics is an abstract class so I don't think that was possible.

    Java Code:
    public class Circle extends JComponent 
    {
         public Circle()
         {
    	          x = 0;
    		  y = 0;
         }
    
         // Draw a circle that can have a transposable position
         public void paint (int x, int y)
         {
           System.out.println("In Function:  paint");
    	    this.x = x;
    		 this.y = y;
           System.out.println("Set X and Y");
           g.setColor (Color.red);     
           System.out.println("Set color");  //  <--------NEVER PRINTS LINE BEFORE FAILS
           g.fillOval (50 + x, 50 + x, 50 + y, 50 + y);
           System.out.println("Fill image");
         }
    
         Graphics g;
         int x, y;
    }
    
    // Constructor
        public MyConstructor()
                throws Exception
        {
    
            sampleField = new JLabel(myName);
            add(sampleField, BorderLayout.CENTER);
    		  
            cirG = new Circle();
            add(cirG, BorderLayout.CENTER);
    
    ...........
    
    	public void setSampleFont(ActionEvent event)
    	{
    	   System.out.println("In Function:  setSampleFont");
               // Check for any button click     
    		
              // Random Generated variables
    	  int myX = 0;
    	  int myY = 0;
    		
    	   if ( event.getSource() instanceof JButton )
    	   {
    		// Circle Button Clicked
    		if (event.getActionCommand().equals(cirName) 
    		   && cirButtonFlag == false )
                    {
    		   cirButtonFlag = true;
                       myX = getMyRandomNum();
       		   myY = getMyRandomNum();
    		   cirG.paint(myX, myY);
    		}
             ...............
               }
              ......
           }
       ......
    }
    Last edited by Fubarable; 08-30-2010 at 09:10 PM. Reason: Moderator edit: code tags added

  2. #2
    Fubarable's Avatar
    Fubarable is offline Moderator
    Join Date
    Jun 2008
    Posts
    19,316
    Blog Entries
    1
    Rep Power
    25

    Default

    Please read the tutorials on how to use graphics as you're currently doing it wrong. For one you're using a paint method that doesn't exist in the JComponent class, that doesn't accept a Graphics object, and so your current Graphics object has never been initialized and will be null. Instead you'll want to do your drawing in a paintComponent method override, a method that takes just one parameter, a Graphics object. The tutorials will explain all.

    edit: for instance, you'll want to use a graphics method that the JVM will call whenever the component is painted, and for a JComponent, paintComponent is better to use than paint, since if you use paint, you are fully responsible for not only painting the component but also its borders and children, and you really don't want that responsibility if you can avoid it. Either way, if you use paint or paintComponent, the signature of the method has to match that for JComponent exactly including the parameter type and number and the return type. For JComponent and most all Swing components (which are derived from JComponent) paint and paintComponent take just one parameter, a Graphics object, and so your paint or paintComponent should do the same. If not, your method will never be called by the JVM.

    For more, please start here: Custom painting with Swing.

    Luck
    Last edited by Fubarable; 08-30-2010 at 09:15 PM.

  3. #3
    Norm's Avatar
    Norm is online now Moderator
    Join Date
    Jun 2008
    Location
    Eastern Florida
    Posts
    16,589
    Rep Power
    23

    Default

    When overriding methods, the compiler will tell you if you have done it correctly if you precede the overridden method with this statement. It can save you lots of problems.
    @Override

  4. #4
    gothrog is offline Member
    Join Date
    May 2010
    Posts
    6
    Rep Power
    0

    Default

    Ok, so I'm not getting the null error anymore. I can see it going through and executing paintComponent(). The problem is that now I don't get any errors and no circle on the panel. If I follow the same steps and use JPanel and it works.

    I would assume that if it goes through paintComponent() it would work.... any ideas?

    ----------------------------------------------
    private class Circle
    {
    public Circle()
    {
    x = 150;
    y = 150;
    clear = false;
    }

    public void setPosition(int x, int y)
    {
    this.x = x;
    this.y = y;
    }

    public void setClear(boolean clear)
    {
    this.clear = clear;
    }

    public int x, y;
    boolean clear;
    }

    public class CirclePanel extends JPanel
    {
    public CirclePanel(Circle circle)
    {
    this.circle = circle;
    }

    // Draw a circle that can have a transposable position
    public void paintComponent(Graphics g)
    {
    System.out.println("In Function: CirclePanel::paintComponent");
    super.paintComponent(g);

    if ( !circle.clear )
    {
    g.setColor (Color.red);
    System.out.println("Set Red");
    }
    else
    {
    g.setColor(Color.white);
    System.out.println("Set White");
    }
    g.fillOval (50 + circle.x, 50 + circle.x, 50 + circle.y, 50 + circle.y);
    System.out.println("Fill image");
    }

    private Circle circle;
    }

    ........

    // Create the control panel
    public void createControlPane2() // <------- Called in constructor
    {
    JPanel textButtonPane2 = createGUI();

    JPanel controlPanel = new JPanel();
    controlPanel.setLayout(new FlowLayout());

    controlPanel.add(textButtonPane2);
    add(controlPanel, BorderLayout.CENTER);
    }

    // create GUI images
    public JPanel createGUI()
    {
    sampleField = new JLabel(myName);

    cirG = new Circle();
    cirP = new CirclePanel(cirG);

    JPanel panel = new JPanel();
    panel.add(sampleField);
    panel.add(cirP);

    return panel;
    }

  5. #5
    curmudgeon is offline Senior Member
    Join Date
    May 2010
    Posts
    436
    Rep Power
    4

    Default

    Quote Originally Posted by gothrog View Post
    Ok, so I'm not getting the null error anymore. I can see it going through and executing paintComponent(). The problem is that now I don't get any errors and no circle on the panel. If I follow the same steps and use JPanel and it works.

    I would assume that if it goes through paintComponent() it would work.... any ideas?

    ----------------------------------------------
    Java Code:
       private class Circle
    	{
         public Circle() 
    	  {
    	     x = 150;
    		  y = 150;
    		  clear = false;
    	  }
    
         public void setPosition(int x, int y)
    	  {
      	    this.x = x;
    		 this.y = y;
         }
    	  
    	  public void setClear(boolean clear)
    	  {
      	    this.clear = clear;
         }
    
         public int x, y;
    	  boolean clear;
    	}
    
       public class CirclePanel extends JPanel
       {
         public CirclePanel(Circle circle) 
    	  {
            this.circle = circle;
    	  }
    	  
         // Draw a circle that can have a transposable position
         public void paintComponent(Graphics g)
         {
           System.out.println("In Function:  CirclePanel::paintComponent");
           super.paintComponent(g);
    
     		 if ( !circle.clear )
           {   
    		    g.setColor (Color.red);
              System.out.println("Set Red");
           }
    		 else
    		 {
    		    g.setColor(Color.white);
    			 System.out.println("Set White");
    		 }
           g.fillOval (50 + circle.x, 50 + circle.x, 50 + circle.y, 50 + circle.y);
           System.out.println("Fill image");
         }
    
         private Circle circle;
    	}
    
    ........
    
    	 // Create the control panel
        public void createControlPane2()  // <------- Called in constructor
        {
            JPanel textButtonPane2  = createGUI();
    
            JPanel controlPanel = new JPanel();
            controlPanel.setLayout(new FlowLayout());
    
            controlPanel.add(textButtonPane2);
            add(controlPanel, BorderLayout.CENTER);
        }
    
        // create GUI images
        public JPanel createGUI()
        {
            sampleField = new JLabel(myName);
          	  
            cirG = new Circle();
            cirP = new CirclePanel(cirG);
     
            JPanel panel = new JPanel();
            panel.add(sampleField);
            panel.add(cirP);
    
            return panel;
        }
    I think that you're going to want to add code tags for us to see your code with formatting (like I've done in a quote from your post above). I see that you're adding a CirclePanel to another JPanel, but I have to wonder if the CirclePanel is big enough to be seen, though not being able to run your program means that I'm just guessing. To really be able to help you debug this, you will probably have to show us code that we can run and test.

  6. #6
    curmudgeon is offline Senior Member
    Join Date
    May 2010
    Posts
    436
    Rep Power
    4

    Default

    For instance, try changing your paintComponent method to show the CirclePanel's size:
    Java Code:
       public void paintComponent(Graphics g) {
          System.out.println("In Function:  CirclePanel::paintComponent");
          super.paintComponent(g);
    
          // **** add this line ****
          System.out.printf("CirclePanel Size: [%d, %d]%n" , getWidth(), getHeight());
    
          if (!circle.clear) {
             g.setColor(Color.red);
             System.out.println("Set Red");
          } else {
             g.setColor(Color.white);
             System.out.println("Set White");
          }
          g.fillOval(50 + circle.x, 50 + circle.x, 50 + circle.y, 50 + circle.y);
          System.out.println("Fill image");
       }
    and then you'll see how big it is. If you still can't fix it, again, you'll want to post compilable and runnable code.

  7. #7
    Norm's Avatar
    Norm is online now Moderator
    Join Date
    Jun 2008
    Location
    Eastern Florida
    Posts
    16,589
    Rep Power
    23

    Default

    What print outs do you see when you execute the code? Can you copy and paste them here?

    If I follow the same steps and use JPanel and it works.
    Its not clear what you mean here. Do you have two versions of the program? One that works and one that doesn't. Which version did you post?

  8. #8
    gothrog is offline Member
    Join Date
    May 2010
    Posts
    6
    Rep Power
    0

    Default

    I'm beginning to assume that somehow, something is out of order. I add the code to print out the width and length. It is both size 1. This would mean that something wasn't initialized right.

    You should be able to just drop this code in and for it too work. I created a separate .java for these edits.

    Java Code:
       //  Set imports
       import java.awt.*;
       import java.awt.event.*;
       import javax.swing.*;
       import java.util.Random;
       import java.applet.*;
       import java.awt.Graphics.*;
    
       // This class handle the main GUI frame.
       public class MyGUIExample extends JFrame
       {
          // Declare and Intialize variables
          private static final String myName = "Michael";
          private static final String cirName = "Draw Circle";
          private static final String meName = "Me";
          private static final String clrAllName = "Clear All";
          private static final int FRAME_WIDTH = 501;
          private static final int FRAME_HEIGHT = 501;
    
          // GUI elements
          private JTextField inputText;
          private JTextField outputText;
          private JButton cirButton;
          private JButton meButton;
          private JButton clrAllButton;
    
          // Control Flags
          private boolean cirButtonFlag = false;
          private boolean meButtonFlag = false;
          private boolean clrAllButtonFlag = false;
    
          // Event Listener
          private ActionListener listener;
    
          // Adding graphics
          private Circle cirG;
          private JLabel sampleField;
          private CirclePanel cirP;
    
          private class Circle
          {
             public Circle()
             {
                x = 150;
                y = 150;
                clear = false;
             }
    
             public void setPosition(int x, int y)
             {
                this.x = x;
                this.y = y;
             }
    
             public void setClear(boolean clear)
             {
                this.clear = clear;
             }
    
             public int x, y;
             boolean clear;
          }
    
          public class CirclePanel extends JComponent
          {
             public CirclePanel(Circle circle)
             {
                this.circle = circle;
             }
    
             // Draw a circle that can have a transposable position
             public void paintComponent(Graphics g)
             {
                System.out.println("In Function:  CirclePanel::paintComponent");
                super.paintComponent(g);
                Graphics2D g2d = (Graphics2D)g;
    
                if ( !circle.clear )
                {
                   g.setColor (Color.red);
                   System.out.println("Set Red");
                }
                else
                {
                   g.setColor(Color.white);
                   System.out.println("Set White");
                }
    
                System.out.printf("CirclePanel1 Size: [%d, %d]%n" , getWidth(), getHeight());
                g.fillOval (50 + circle.x, 50 + circle.x, 50 + circle.y, 50 + circle.y);
                System.out.printf("CirclePanel2 Size: [%d, %d]%n" , getWidth(), getHeight());
                System.out.println("Fill image");
             }
    
             private Circle circle;
          }
    
    
          // Constructor for MyGUIExample frame.
          public MyGUIExample()
             throws Exception
          {
    
             // Format listening function.
             class RefreshListener implements ActionListener
             {
                public void actionPerformed(ActionEvent event)
                {
                   //Run query based on text field value
                   try
                   {
                      setSampleFont(event);
                      repaint();
    
                   }
                   catch(Exception e)
                   {
                      System.out.println(e.getMessage());
                   }
                }
             }
    
             listener = new RefreshListener();
    
             createControlPanel();
             createControlPane2();
             setSize(FRAME_WIDTH, FRAME_HEIGHT);
          }
    
          // Get user choice for font name, style, size and set the font of the
          // sample text
          public void setSampleFont(ActionEvent event)
          {
             System.out.println("In Function:  setSampleFont");
    
             // Random Generated variables
             int myX = 0;
             int myY = 0;
    
             if ( event.getSource() instanceof JButton )
             {
                // Circle Button Clicked
                if (event.getActionCommand().equals(cirName)
                   && cirButtonFlag == false )
                {
                   cirButtonFlag = true;
                   myX = getMyRandomNum();
                   myY = getMyRandomNum();
                   cirG.setPosition(myX, myY);
                   cirG.setClear(false);
                //cirP.repaint();
                }
                // Me Button Clicked
                else if (event.getActionCommand().equals(meName)
                && meButtonFlag == false )
                {
                   meButtonFlag = true;
                   sampleField.setText(myName);
                }
                // Clear All Button Clicked
                else if (event.getActionCommand().equals(clrAllName)
                && clrAllButtonFlag == false )
                {
                   System.out.println("Clear All");
                   clrAllButtonFlag = true;
                   cirG.setClear(true);
                   sampleField.setText("");
    
                }
             }
    
    
             if (clrAllButtonFlag)
             {
    
             // reprint images
                cirP.repaint();
                sampleField.repaint();
    
             // reset control flags
                cirButtonFlag = false;
                meButtonFlag = false;
                clrAllButtonFlag = false;
             }
             else
             {
                if (cirButtonFlag)
                {
                //sampleField.setFont(new Font("Monospaced", Font.BOLD, 24));
                //sampleField.repaint();
                }
                if (meButtonFlag)
                {
                   sampleField.setFont(new Font("Monospaced", Font.BOLD, 24));
                   sampleField.repaint();
                }
             }
          }
    
          // Create the control panel
          public void createControlPanel()
          {
             JPanel textButtonPanel  = createButton();
    
             JPanel controlPanel = new JPanel();
             controlPanel.setLayout(new GridLayout(3,1));
    
             controlPanel.add(textButtonPanel);
             add(controlPanel, BorderLayout.SOUTH);
          }
    
          // Create the control panel
          public void createControlPane2()
          {
             JPanel textButtonPane2  = createGUI();
    
             JPanel controlPanel = new JPanel();
             controlPanel.setLayout(new FlowLayout());
    
             controlPanel.add(textButtonPane2);
             add(controlPanel, BorderLayout.CENTER);
          }
    
          // create the button for the query
          public JPanel createButton()
          {
             cirButton = new JButton(cirName);
             cirButton.addActionListener(listener);
    
             meButton = new JButton(meName);
             meButton.addActionListener(listener);
    
             clrAllButton = new JButton(clrAllName);
             clrAllButton.addActionListener(listener);
    
             JPanel panel = new JPanel();
             panel.add(cirButton);
             panel.add(meButton);
             panel.add(clrAllButton);
    
             return panel;
          }
    
          // create GUI images
          public JPanel createGUI()
          {
             sampleField = new JLabel(myName);
    
             cirG = new Circle();
             cirP = new CirclePanel(cirG);
    
             JPanel panel = new JPanel();
             panel.add(sampleField);
             panel.add(cirP);
    
             return panel;
          }
    
    
          // Create random number
          public int getMyRandomNum()
          {
             Random r = new Random();
             return r.nextInt(500);
          }
    
          // Main function for MyGUIExample.
          public static void main(String[] args)
             throws Exception
          {
             JFrame frame = new MyGUIExample();
             frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
             frame.setTitle("Advanced GUI Example");
             frame.setVisible(true);
          }
       }

  9. #9
    Fubarable's Avatar
    Fubarable is offline Moderator
    Join Date
    Jun 2008
    Posts
    19,316
    Blog Entries
    1
    Rep Power
    25

    Default

    Your problem is one of using layouts that will help you. To figure this out, I often give all my key JPanels titleBorders, such as:

    Java Code:
        // changes indicated by these comments: [color="red"]//!![/color]
        public void createControlPane2() {
            JPanel textButtonPane2 = createGUI();
            //!!
            textButtonPane2.setBorder(BorderFactory.createTitledBorder("textButtonPane2"));
    
    
            JPanel controlPanel = new JPanel();
            controlPanel.setLayout(new FlowLayout());
            
            //!!
            controlPanel.setBorder(BorderFactory.createTitledBorder("controlPanel"));
    
            controlPanel.add(textButtonPane2);
            add(controlPanel, BorderLayout.CENTER);
        }
    and
    Java Code:
        public JPanel createGUI() {
            sampleField = new JLabel(myName);
    
            cirG = new Circle();
            cirP = new CirclePanel(cirG);
            
            //!! 
            cirP.setBorder(BorderFactory.createTitledBorder("circle panel"));
    
            //.... etc...
        }
    You'll find that you some of your JPanels are very small and some are not visible at all, mostly for overusing FlowLayout. Experiment with different layouts to see changes. For instance many of the places you use FlowLayout (which is the default layout for JPanels) may be better served with BorderLayout, but if you use BorderLayout, be sure to use the BorderLayout constants when adding components so that components are all added to the same location.

  10. #10
    gothrog is offline Member
    Join Date
    May 2010
    Posts
    6
    Rep Power
    0

    Default

    Thanks, I have added the changes in. I can see how small the borders were. I changed FlowLayout to Gridlayout. Unfortunately I still can't see my circle. It should be in the textButtonPane2 border....... but not...

    The size output is still 1,1 regardless of the change to GridLayout:
    CirclePanel1 Size: [1, 1]

    What would make it's size be 1 width and 1 height?

    Java Code:
          // Create the control panel
          public void createControlPane2()
          {
             JPanel textButtonPane2  = createGUI();
    			
    textButtonPane2.setBorder(BorderFactory.createTitledBorder("textButtonPane2"));
    
             JPanel controlPanel = new JPanel();
             controlPanel.setLayout(new GridLayout(1,1)); // <----- CHANGED TO REMOVE FLOWLAYOUT
    
    controlPanel.setBorder(BorderFactory.createTitledBorder("controlPanel"));
    
    
             controlPanel.add(textButtonPane2);
             add(controlPanel, BorderLayout.CENTER);
          }

  11. #11
    gothrog is offline Member
    Join Date
    May 2010
    Posts
    6
    Rep Power
    0

    Default

    Ok I have seen the light at the end of the tunnel. Did some research on JComponent. I knew that something wasn't getting initiated right with these many levels of encapsulation.

    Using Dimensions have saved the day and thanks for all the help. I would have never of figured out that last problem.

    // I can see my preview pane and my circle now.
    Dimension myDimension = new Dimension(100,100);
    setPreferredSize(myDimension);


    Java Code:
             public void paintComponent(Graphics g)
             {
                System.out.println("In Function:  CirclePanel::paintComponent");
                super.paintComponent(g);
    
                if ( !circle.clear )
                {
                   g.setColor (Color.red);
                   System.out.println("Set Red");
                }
                else
                {
                   g.setColor(Color.white);
                   System.out.println("Set White");
                }
    
                System.out.printf("CirclePanel1 Size: [%d, %d]%n" , getWidth(), getHeight());
                if ( !isPreferredSizeSet() )
    				{
                   getPreferredSize();
                   System.out.println("Called1:  getPreferredSize()");
    				}
    				else
    				{
                   System.out.println("isPreferredSizeSet1 = true");
                   System.out.println("Call getPreferredSize()1 anyway");
                   getPreferredSize();				
    				}
    
                Dimension myDimension = new Dimension(100,100);
                setPreferredSize(myDimension);
    
                System.out.printf("CirclePanel2 Size: [%d, %d]%n" , getWidth(), getHeight());
    								
                g.fillOval (25 + circle.x, 25 + circle.x, 25 + circle.y, 25 + circle.y);
    
                   System.out.println("Call getPreferredSize()2 anyway");
                   getPreferredSize();				
    
                System.out.printf("CirclePanel3 Size: [%d, %d]%n" , getWidth(), getHeight());
                System.out.println("Fill image");
             }
    
             private Circle circle;
          }

Similar Threads

  1. help with with my null error
    By zhangster in forum New To Java
    Replies: 3
    Last Post: 03-20-2010, 12:32 AM
  2. Execution error: NoSuchMethodError: Main
    By kjharn in forum New To Java
    Replies: 4
    Last Post: 11-02-2009, 08:23 PM
  3. .BAT execution error
    By hunterbdb in forum Advanced Java
    Replies: 5
    Last Post: 02-23-2009, 05:41 AM
  4. Null Error
    By scoleman123 in forum New To Java
    Replies: 2
    Last Post: 09-19-2008, 04:04 PM
  5. Replies: 2
    Last Post: 05-01-2008, 10:14 AM

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •