使JPanel可拖动

时间:2013-05-24 15:40:49

标签: java swing user-interface

我使用JPanel扩展了Mac上的工具栏(参见图片),但是作为实际工具栏(不是JPanel)的部分是您可以单击并拖动的唯一部分。如何允许用户单击并拖动JPanel来移动窗口,就像工具栏

一样

图像的顶部mm左右是实际的工具栏(带有文本),其余的是JPanel(带按钮)。 enter image description here

以下是UnifiedToolPanel的代码,它设置在JFrame中边框布局的北部:

package gui;
import java.awt.Color;
import java.awt.GradientPaint;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Window;
import java.awt.event.WindowEvent;
import java.awt.event.WindowFocusListener;
import java.awt.event.WindowListener;

import javax.swing.BorderFactory;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.border.Border;

import com.jgoodies.forms.factories.Borders;

public class UnifiedToolbarPanel extends JPanel implements WindowFocusListener {

    public static final Color OS_X_UNIFIED_TOOLBAR_FOCUSED_BOTTOM_COLOR =
            new Color(64, 64, 64);
    public static final Color OS_X_UNIFIED_TOOLBAR_UNFOCUSED_BORDER_COLOR =
            new Color(135, 135, 135);    

    public static final Color OS_X_TOP_FOCUSED_GRADIENT = new Color(214+8, 214+8, 214+8);
    public static final Color OS_X_BOTTOM_FOCUSED_GRADIENT = new Color(217, 217, 217);
    public static final Color OS_X_TOP_UNFOCUSED_GRADIENT = new Color(240+3, 240+3, 240+3);
    public static final Color OS_X_BOTTOM_UNFOCUSED_GRADIENT = new Color(219, 219, 219);


    public UnifiedToolbarPanel() {
        // make the component transparent
        setOpaque(true);
        Window window = SwingUtilities.getWindowAncestor(this);
        // create an empty border around the panel
        // note the border below is created using JGoodies Forms
        setBorder(Borders.createEmptyBorder("3dlu, 3dlu, 1dlu, 3dlu"));
    }


    @Override
    public void paintComponent(Graphics g) {
        super.paintComponent(g);
        Graphics2D g2d = (Graphics2D) g;
        Window window = SwingUtilities.getWindowAncestor(this);
        Color color1  = window.isFocused() ? OS_X_TOP_FOCUSED_GRADIENT
                : OS_X_TOP_UNFOCUSED_GRADIENT;
        Color color2 = window.isFocused() ? color1.darker()
                : OS_X_BOTTOM_UNFOCUSED_GRADIENT;
        int w = getWidth();
        int h = getHeight();
        GradientPaint gp = new GradientPaint(
            0, 0, color1, 0, h, color2);
        g2d.setPaint(gp);
        g2d.fillRect(0, 0, w, h);
    }

    @Override
    public Border getBorder() {
        Window window = SwingUtilities.getWindowAncestor(this);
        return window != null && window.isFocused()
                ? BorderFactory.createMatteBorder(0,0,1,0,
                        OS_X_UNIFIED_TOOLBAR_FOCUSED_BOTTOM_COLOR)
                : BorderFactory.createMatteBorder(0,0,1,0,
                       OS_X_UNIFIED_TOOLBAR_UNFOCUSED_BORDER_COLOR);
    }


    @Override
    public void windowGainedFocus(WindowEvent e) {
        repaint();
    }


    @Override
    public void windowLostFocus(WindowEvent e) {
        repaint();
    }
}

2 个答案:

答案 0 :(得分:2)

如何让用户点击并拖动JPanel来移动窗口
这是方法:

   private int x;
    private int y;
    //.....
    //On mouse pressed:
    jpanel.addMouseListener(new MouseAdapter(){
       public void mousePressed(MouseEvent ev){
        x = ev.getX ();
        y = ev.getY();
       }
    });
    //....
    //on mouse dragged
    jpanel.addMouseMotionListener(new MouseMotionAdapter() {
                public void mouseDragged(MouseEvent evt) {
                    int x = evt.getXOnScreen()-this.x;
                    int y = evt.getYOnScreen -this.y;
                    this.setLocation(x,y); 

                }
            });

this.setLocation(x,y)将移动框架而非面板,我认为您的课程已延长JFrame
但是,您可以创建一个返回点(x,y)并将其设置为窗口的方法。

答案 1 :(得分:0)

Point类实际上没有答案,因此我将添加自己的贡献而不是存储MouseEvent的x, y线,我们存储Point

这里显示您可以做到,定义类java.awt.Point的全局变量

private Point currentLocation;

然后,一旦使用currentLocation按下鼠标,我们便将点存储到MouseListener

panel.addMouseListener(new MouseAdapter() {
   public void mousePressed(MouseEvent e) {
       currentLocation = e.getPoint();
    }
});

,我们使用MouseMotionListener

拖动鼠标时设置了JFrame的位置
panel.addMouseMotionListener(new MouseAdapter() {
    public void mouseDragged(MouseEvent e) {
        Point currentScreenLocation = e.getLocationOnScreen();
        setLocation(currentScreenLocation.x - currentLocation.x, currentScreenLocation.y - currentLocation.y);
    }
});

,然后将所有代码放到一个HelperMethod中,以便在任何地方使用

public void setDraggable(JPanel panel) {
    panel.addMouseListener(new MouseAdapter() {
        public void mousePressed(MouseEvent e) {
            currentLocation = e.getPoint();
        }
    });

    panel.addMouseMotionListener(new MouseAdapter() {
        public void mouseDragged(MouseEvent e) {
            Point currentScreenLocation = e.getLocationOnScreen();
            setLocation(currentScreenLocation.x - currentLocation.x, currentScreenLocation.y - currentLocation.y);
        }
    });
}

我将HelperMethod存储在扩展JFrame的类中,因此为什么我可以访问不带变量的属于JFrame的setLocation