I needed to draw an image and paint a needle on it. Since my image is stationary(it doesnt change) I dont want to paint it each time I call repaint. Thats why I thought of using JLabel with an Icon image. The problem is I cant paint anything on top of label. If I use drawImage method I can paint on it.
Following is my code

import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Stroke;
import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.geom.AffineTransform;
import java.awt.image.BufferedImage;
import java.text.DecimalFormat;
import java.text.NumberFormat;
import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.Timer;
import javax.swing.UIManager;

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

/**
 *
 * @author Gunjan Nigam
 */
public class Odometer extends JPanel {

    int start1X,start1Y;

    int image1x,image1y;
    BufferedImage img;
    float speed;

    public Odometer()
    {
        super(null);
        try
        {

            JFrame frame = new JFrame("Chariot");
            frame.setSize(1280, 720);
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            UIManager.setLookAndFeel("com.sun.java.swing.plaf.windows.WindowsLookAndFeel");
            Toolkit toolkit = Toolkit.getDefaultToolkit();
            frame.setLocation((int) ((toolkit.getScreenSize().getWidth()-1280)/2), (int) ((toolkit.getScreenSize().getHeight()-700)/2));

            this.setBackground(Color.BLACK);
            frame.add(this);
            frame.setResizable(false);

            ImageIcon myImage1 = new ImageIcon(getClass().getResource("/images/od.PNG"));
            image1x=myImage1.getIconWidth();
            image1y=myImage1.getIconHeight();
            JLabel image1 = new JLabel(myImage1);
            image1.setOpaque(true);
            add(image1);
            img = ImageIO.read(getClass().getResource("/images/od.PNG"));
            frame.setVisible(true);
            image1.setBounds((getWidth()-image1x)/2,(getHeight()-image1y)/2,image1x,image1y);
            
           speed=0;
            DataGenerator dg = new DataGenerator(90);
            dg.start();
         } catch (Exception ex) {
            ex.printStackTrace();
        }
    }
    @Override
    public void paintComponent(Graphics g)
    {
      super.paintComponent(g);

      Graphics2D g2d = (Graphics2D)g;

      start1X = (getWidth())/2;
      start1Y = (getHeight())/2;

      //System.out.println(start1X+" "+start1Y);
      //g2d.drawImage(img,(getWidth()-image1x)/2,(getHeight()-image1y)/2,image1x,image1y,null);
      g2d.setColor(Color.white);

      AffineTransform affineTransform = g2d.getTransform();
		AffineTransform newTransform = (AffineTransform)(affineTransform.clone());
		g2d.setPaint(Color.orange);

		g2d.transform(newTransform.getRotateInstance((speed*30-210)/57.29,start1X,start1Y));
		int[]coordinateXs={start1X,start1X+100,start1X+107,start1X+100,start1X};
		int[]coordinateYs={start1Y-5,start1Y-5,start1Y,start1Y+5,start1Y+5};
		g2d.fillPolygon(coordinateXs,coordinateYs,5);
		Stroke stroke = new BasicStroke(3);
		g2d.setStroke(stroke);
		g2d.drawLine(start1X+105,start1Y,start1X+130,start1Y);
		stroke=new BasicStroke(1);
		g2d.setStroke(stroke);
		g2d.setTransform(affineTransform);
        g2d.setColor(Color.BLACK);
        g2d.fillRect(start1X-30, start1Y-20, 60, 40);
         g2d.setColor(Color.orange);
         g2d.drawRect(start1X-30, start1Y-20, 60, 40);
         NumberFormat formatter = new DecimalFormat("0.0");
		String str=formatter.format(speed);
        g2d.setFont(new Font("Arial",Font.BOLD,30));
		g2d.drawString(str,start1X-20,start1Y+10);
    }
    

    class DataGenerator extends Timer implements ActionListener
    {
        public DataGenerator(int interval)
        {
            super(interval,null);
            addActionListener(this);
        }

        public void actionPerformed(ActionEvent e) {
          
            speed = speed+0.02f;
            if(speed>8)
                speed=0;
            
            repaint();
        }

    }
    public static void main(String[] args)
    {
        Odometer ch = new Odometer();
    }
}

Suggest a way so that I can paint the image once and that paint on the top of image

Recommended Answers

All 3 Replies

As far as I recall calling super.paintComponent is going to clear the surface that you are painting on, which is not what you want to do, so I'd erase that line of code. Recompile&run, then tell me what happens.

The super.paintComponent() call just let's the component perform whatever normal painting the super class would if the method weren't overridden.

To the OP: you may want to glance over this bit of info on the Swing painting mechanism: http://java.sun.com/docs/books/tutorial/uiswing/painting/closer.html

Your paintComponent() code is painting the JPanel portion and then paintChildren() renders the other components (such as the label with image) on top of that JPanel area.

If you created a class that extended JLabel you could paint over its icon image just fine by placing your custom code after a super.paintComponent() call.

The super.paintComponent() call just let's the component perform whatever normal painting the super class would if the method weren't overridden.

To the OP: you may want to glance over this bit of info on the Swing painting mechanism: http://java.sun.com/docs/books/tutorial/uiswing/painting/closer.html

Your paintComponent() code is painting the JPanel portion and then paintChildren() renders the other components (such as the label with image) on top of that JPanel area.

If you created a class that extended JLabel you could paint over its icon image just fine by placing your custom code after a super.paintComponent() call.

Well I couldn't get what you meant about what I shall do. I am painting after calling the super.paintCOmponent call. What I should do. Please describe it once again

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.