A lot of daily software, some of the components (pictures, buttons, etc.) can be dragged in the window. How is this achieved? Let me share a demo of Java's draggable components.
We mainly use mouse events in Java.
First of all, in Java, we have a coordinate system in our screen. The left vertex of the screen is (0,0), the positive direction of x axis is from left to right, and the positive direction of y axis is from top to bottom. For example, this screenshot:
In our commonly used JFrame method setLocation method (set window position), the coordinates set are relative to the coordinate system in this screen. The left vertex position of the window is the window position.
Of course, the mouse listener can get the coordinates of the mouse in the screen.
Then, for a window in Java, there is a coordinate system inside the window. The left vertex of the window is (0,0), the positive direction of x axis is from left to right, and the positive direction of y axis is from top to bottom. For example, this window:
If we understand the coordinate system in the window, we can set the position of the window component.
The setBounds method is used to set the component location. For example, set the location for the JLabel object:
JLabel l=new JLabel("assembly"); l.setBounds(10,10,120,169); //setBounds usage: component object name. setBounds(x coordinate, y coordinate, component width, component height); coordinates refer to the coordinates of the coordinate system of this window
The location of the above component refers to the location (coordinate) of the left vertex of the component.
The coordinate system of components and windows is as follows:
Through the mouse listener of the window, we can also get the coordinates of the mouse in the window.
Similarly, any window component also has its internal coordinate system. The left vertex of the component is (0,0), the x-axis positive direction is from left to right, and the y-axis positive direction is from top to bottom, as shown in the figure:
In this way, you can add a mouse listener to the component and get the location of the mouse in the component.
The above three coordinate systems are introduced: screen coordinate system (for the whole computer screen), window coordinate system (for the whole window) and window component coordinate system (only for this component). We must not confuse them!
Understand the meaning of these coordinates, then the idea is very clear: we only need to get the real-time position coordinates in each coordinate system when clicking and dragging the mouse through the listener, and then through calculation, and then setBounds set the component position in real time, can't we?
First, we set two global int values to represent the position of the mouse when it is pressed in the component:
static int mlx; //Represents the x coordinate of the mouse in the component (component coordinate system) static int mly; //Represents the y coordinate of the mouse in the component (component coordinate system)
Create a global JLabel object:
static JLabel l=new JLabel(new ImageIcon("Picture path"));
JLabel object can be used to set both text content and picture content, but more details are provided here.
When we drag a thing with the mouse, we must first click and then (hold the mouse) drag, so first get the position when clicking, and then get the real-time position when dragging. (common sense 2333)
Then, first add a mouse listener to the JLabel object to obtain the position coordinates in the coordinate system of the component where the mouse is when the mouse first clicks the component:
l.addMouseListener(new MouseAdapter() { //Mouse click event public void mousePressed(MouseEvent e) { mlx=e.getPoint().x; mly=e.getPoint().y; } });
Then, add a mouse action listener to the JLabel object to obtain the real-time position coordinates in the component coordinate system and screen coordinate system of the mouse when dragging this component, and obtain the coordinates of the window in the screen to calculate the position of the real-time setting component in the window:
l.addMouseMotionListener(new MouseMotionAdapter() { //Mouse drag event public void mouseDragged(MouseEvent e) { l.setBounds(e.getXOnScreen()-jf.getX()-mlx,e.getYOnScreen()-jf.getY()-mly,120,169); } });
Above, e.getXOnScreen() is to get the x coordinate of the mouse on the screen, e.getYOnScreen() is to get the y coordinate of the mouse on the screen (within the screen coordinate system)
jf is the name of my window object (JFrame), jf.getX() is to get the x coordinate of the window in the screen, jf.getY() is to get the y coordinate of the window in the screen (in the screen coordinate system)
According to these three coordinates, we can get the position of the component after dragging.
Set up such two mouse monitors, and successfully drag the components!
Effect:
Full code:
import java.awt.*; import javax.swing.*; import java.awt.event.*; public class ActCoTest { static int mlx; static int mly; static JLabel l=new JLabel(new ImageIcon("res\\drgt.png")); public static void main(String[] args) { JFrame jf=new JFrame(); jf.setUndecorated(true); //Window de border jf.setSize(750,500); jf.setDefaultCloseOperation(jf.EXIT_ON_CLOSE); Toolkit kit=Toolkit.getDefaultToolkit(); Dimension sc=kit.getScreenSize(); jf.setLocation(sc.width/2-200,sc.height/2-100); l.setBounds(30,65,120,169); //Initialize JLabel position first l.addMouseListener(new MouseAdapter() { //Mouse click event public void mousePressed(MouseEvent e) { mlx=e.getPoint().x; //Get the x coordinate of the mouse in the component and assign it to mlx (component coordinate system) mly=e.getPoint().y; //Get y coordinate of mouse in component and assign it to mly (component coordinate system) } }); l.addMouseMotionListener(new MouseMotionAdapter() { //Mouse drag event public void mouseDragged(MouseEvent e) { l.setBounds(e.getXOnScreen()-jf.getX()-mlx,e.getYOnScreen()-jf.getY()-mly,120,169); } }); JPanel jp=new JPanel(); jp.add(l); jp.setLayout(null); jf.getContentPane().add(jp); jf.show(); } }