简体   繁体   中英

Java: Rotate image towards mouse position?

So I'm having this guy:

鲍勃

Let's call him Bob.

I want to make him rotate towards my mouse position. I have already figured out that by drawing a line between Bob and the mouse and by finding the angle of this line, i can find out what the angle is, that Bob needs to face in order to 'point' towards the mouse. However I still don't know how to accomplish this task.

Thanks in advance!

You should not include the image in a JLabel . It simply does not offer much flexibility. The positioning may be odd, and you can't draw the image rotated. (You could only create a rotated image and put this into the label, but this would be inefficient, and the sizing and position issues would drive you mad).

Instead, you should paint your image manually, in the overridden paintComponent method of a JPanel . There are still some details to consider. For example, the image should probably have a certain position , and the position should probably refer to the center of the image - namely, to the point that it will be rotated about.

However, when you have computed the angle of the line between the image center and the mouse position, you can simply paint the image with the desired orientation, by

  • moving the image so that its center is at the origin
  • rotating the image
  • moving the image so that its center is at the desired position

Here is a MCVE :

import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.RenderingHints;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
import java.awt.geom.AffineTransform;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;

import javax.imageio.ImageIO;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;

public class ImageFollowingMouseTest
{
    public static void main(String[] args)
    {
        SwingUtilities.invokeLater(new Runnable()
        {
            @Override
            public void run()
            {
                createAndShowGUI();
            }
        });
    }

    private static void createAndShowGUI()
    {
        JFrame f = new JFrame();
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.getContentPane().add(new ImageFollowingMousePanel());
        f.setSize(400,400);
        f.setLocationRelativeTo(null);
        f.setVisible(true);
    }

}

class ImageFollowingMousePanel extends JPanel implements MouseMotionListener
{
    private final BufferedImage image;
    private Point imagePosition = new Point(150,150);
    private double imageAngleRad = 0;

    public ImageFollowingMousePanel()
    {
        BufferedImage i = null;
        try
        {
            i = ImageIO.read(new File("6Wu0b.png"));
        }
        catch (IOException e)
        {
            e.printStackTrace();
        }
        image = i;
        addMouseMotionListener(this);
    }

    protected void paintComponent(Graphics gr) 
    {
        super.paintComponent(gr);
        Graphics2D g = (Graphics2D)gr;
        g.setRenderingHint(
            RenderingHints.KEY_RENDERING, 
            RenderingHints.VALUE_RENDER_QUALITY);

        int cx = image.getWidth() / 2;
        int cy = image.getHeight() / 2;
        AffineTransform oldAT = g.getTransform();
        g.translate(cx+imagePosition.x, cy+imagePosition.y);
        g.rotate(imageAngleRad);
        g.translate(-cx, -cy);
        g.drawImage(image, 0, 0, null);
        g.setTransform(oldAT);

    }

    @Override
    public void mouseDragged(MouseEvent e)
    {
    }

    @Override
    public void mouseMoved(MouseEvent e)
    {
        double dx = e.getX() - imagePosition.getX();
        double dy = e.getY() - imagePosition.getY();
        imageAngleRad = Math.atan2(dy, dx);
        repaint();
    }


}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM