Java如何使用鼠标拖动调整无边框窗口的大小?

时间:2012-09-16 21:21:52

标签: java swing

我有一个没有装饰的jFrame只有gui是由图形GD绘制的。我希望用户调整此窗口的大小,但不可能没有边框。因此,当我从一个特殊的位置拖动时,我制作了一个鼠标监听器来调整大小。它有点工作,但直到停止都没有延伸。有更简单的方法吗?还有其他选择吗?有没有人用纯GD做过这个?

 this.addMouseListener(new MouseAdapter()
{
public void mousePressed(MouseEvent e)
{
  posX=e.getX();
  posY=e.getY();

}     

 }}); 

 this.addMouseMotionListener(new MouseAdapter()
{
 public void mouseDragged(MouseEvent evt)
 {
if (posX >= getWidth()-25 && posY >=getHeight()-45){
int nlx= evt.getXOnScreen()-(location().x-12);
int nly= evt.getYOnScreen()-(location().y-32);

        setSize(nlx,nly);
 setBackground(new Color(0, 0, 0, 0));
 invalidate(); 
    }else{
    setLocation (evt.getXOnScreen()-posX,evt.getYOnScreen()-posY);

    }

 }
 });  
}

2 个答案:

答案 0 :(得分:2)

我用jFrame做了类似的事情,我通过在jFrame的外部添加4个非常薄的按钮来解决它,并使用按钮上的鼠标按下和mousedragged监听器来控制jFrame调整大小,它运行得相当顺利。

mousePressed侦听器让我们获取起始位置,以便我可以计算拖动/调整帧的距离

如果要保存资源,则应在释放鼠标时调整所有子组件的大小,而不是在拖动鼠标时调整其大小

编辑:在X轴上调整框架大小的示例。

public class NewJFrame extends javax.swing.JFrame
{
    //demo locations
    int X1 = 0;
    int X2 = 0;

    public NewJFrame()
    {
    initComponents();
    }

    @SuppressWarnings("unchecked")
    private void initComponents() {

        ResizeEast = new javax.swing.JButton();
        jButton1 = new javax.swing.JButton();

        setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE);
        setUndecorated(true);

        ResizeEast.addMouseListener(new java.awt.event.MouseAdapter() {
            public void mousePressed(java.awt.event.MouseEvent evt) {
                ResizeEastMousePressed(evt);
            }
            public void mouseReleased(java.awt.event.MouseEvent evt) {
                ResizeEastMouseReleased(evt);
            }
        });
        ResizeEast.addMouseMotionListener(new java.awt.event.MouseMotionAdapter() {
            public void mouseDragged(java.awt.event.MouseEvent evt) {
                ResizeEastMouseDragged(evt);
            }
        });

        jButton1.setText("Close");
        jButton1.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                jButton1ActionPerformed(evt);
            }
        });

        javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane());
        getContentPane().setLayout(layout);
        layout.setHorizontalGroup(
            layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(layout.createSequentialGroup()
                .addContainerGap()
                .addComponent(jButton1)
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, 320, Short.MAX_VALUE)
                .addComponent(ResizeEast, javax.swing.GroupLayout.PREFERRED_SIZE, 11, javax.swing.GroupLayout.PREFERRED_SIZE))
        );
        layout.setVerticalGroup(
            layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(layout.createSequentialGroup()
                .addContainerGap()
                .addComponent(jButton1)
                .addContainerGap(266, Short.MAX_VALUE))
            .addComponent(ResizeEast, javax.swing.GroupLayout.DEFAULT_SIZE, 300, Short.MAX_VALUE)
        );

        pack();
    }

    private void ResizeEastMousePressed(java.awt.event.MouseEvent evt)
    {
    //set mosuepressed location to X1 and Y1
    X1 = evt.getX();
    }

    private void ResizeEastMouseReleased(java.awt.event.MouseEvent evt)
    {
    //update the location and size of all child components
    }

    private void ResizeEastMouseDragged(java.awt.event.MouseEvent evt)
    {
    //resize jframe on the fly
    X2 = evt.getX();
    //set minimum size to 100 wide
    if ((getWidth() - (X1 - X2)) < 100)
    {
        X2 = X1;
    }

    //resize east side only
    this.setSize(getWidth() - (X1 - X2), getHeight());
    }

    private void jButton1ActionPerformed(java.awt.event.ActionEvent evt)
    {
    System.exit(0);
    }

    public static void main(String args[])
    {
    java.awt.EventQueue.invokeLater(new Runnable()
    {
        public void run()
        {
        new NewJFrame().setVisible(true);
        }
    });
    }
    // Variables
    private javax.swing.JButton ResizeEast;
    private javax.swing.JButton jButton1;
}

要从角落重新调整大小,请创建小角落按钮,调整X和Y的大小,如下所示:YourFrame.setSize(getWidth() - (X1 - X2), getHeight() - (Y1 - Y2));

答案 1 :(得分:2)

这是我现在使用的完整鼠标适配器:

import javax.swing.*;
import java.awt.*;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;

/**
 * @see http://stackoverflow.com/a/12456113/909085
 */

public class WindowResizeAdapter extends MouseAdapter implements SwingConstants
{
    private boolean resizing = false;
    private int prevX = -1;
    private int prevY = -1;

    private int resizeSide = 0;

    public static void install ( Component component, int resizeSide )
    {
        WindowResizeAdapter wra = new WindowResizeAdapter ( resizeSide );
        component.addMouseListener ( wra );
        component.addMouseMotionListener ( wra );
    }

    public WindowResizeAdapter ( int resizeSide )
    {
        super ();
        this.resizeSide = resizeSide;
    }

    public void mousePressed ( MouseEvent e )
    {
        if ( SwingUtilities.isLeftMouseButton ( e ) )
        {
            resizing = true;
        }
        prevX = e.getXOnScreen ();
        prevY = e.getYOnScreen ();
    }

    public void mouseDragged ( MouseEvent e )
    {
        if ( prevX != -1 && prevY != -1 && resizing )
        {
            Window w = SwingUtilities.getWindowAncestor ( e.getComponent () );
            Rectangle rect = w.getBounds ();

            Dimension dim;
            boolean undecorated;
            if ( w instanceof JDialog )
            {
                dim = ( ( JDialog ) w ).getContentPane ().getPreferredSize ();
                undecorated = ( ( JDialog ) w ).isUndecorated ();
            }
            else if ( w instanceof JFrame )
            {
                dim = ( ( JFrame ) w ).getContentPane ().getPreferredSize ();
                undecorated = ( ( JFrame ) w ).isUndecorated ();
            }
            else
            {
                dim = w.getPreferredSize ();
                undecorated = true;
            }

            // Checking for minimal width and height
            int xInc = e.getXOnScreen () - prevX;
            int yInc = e.getYOnScreen () - prevY;
            if ( undecorated )
            {
                if ( resizeSide == SwingConstants.NORTH_WEST || resizeSide == SwingConstants.WEST ||
                        resizeSide == SwingConstants.SOUTH_WEST )
                {
                    if ( rect.width - xInc < dim.width )
                    {
                        xInc = 0;
                    }
                }
                else if ( resizeSide == SwingConstants.NORTH_EAST ||
                        resizeSide == SwingConstants.EAST ||
                        resizeSide == SwingConstants.SOUTH_EAST )
                {
                    if ( rect.width + xInc < dim.width )
                    {
                        xInc = 0;
                    }
                }
                if ( resizeSide == SwingConstants.NORTH_WEST ||
                        resizeSide == SwingConstants.NORTH ||
                        resizeSide == SwingConstants.NORTH_EAST )
                {
                    if ( rect.height - yInc < dim.height )
                    {
                        yInc = 0;
                    }
                }
                else if ( resizeSide == SwingConstants.SOUTH_WEST ||
                        resizeSide == SwingConstants.SOUTH ||
                        resizeSide == SwingConstants.SOUTH_EAST )
                {
                    if ( rect.height + yInc < dim.height )
                    {
                        yInc = 0;
                    }
                }
            }

            // Resizing window if any changes are done
            if ( xInc != 0 || yInc != 0 )
            {
                if ( resizeSide == SwingConstants.NORTH_WEST )
                {
                    w.setBounds ( rect.x + xInc, rect.y + yInc, rect.width - xInc,
                            rect.height - yInc );
                }
                else if ( resizeSide == SwingConstants.NORTH )
                {
                    w.setBounds ( rect.x, rect.y + yInc, rect.width, rect.height - yInc );
                }
                else if ( resizeSide == SwingConstants.NORTH_EAST )
                {
                    w.setBounds ( rect.x, rect.y + yInc, rect.width + xInc, rect.height - yInc );
                }
                else if ( resizeSide == SwingConstants.WEST )
                {
                    w.setBounds ( rect.x + xInc, rect.y, rect.width - xInc, rect.height );
                }
                else if ( resizeSide == SwingConstants.EAST )
                {
                    w.setBounds ( rect.x, rect.y, rect.width + xInc, rect.height );
                }
                else if ( resizeSide == SwingConstants.SOUTH_WEST )
                {
                    w.setBounds ( rect.x + xInc, rect.y, rect.width - xInc, rect.height + yInc );
                }
                else if ( resizeSide == SwingConstants.SOUTH )
                {
                    w.setBounds ( rect.x, rect.y, rect.width, rect.height + yInc );
                }
                else if ( resizeSide == SwingConstants.SOUTH_EAST )
                {
                    w.setBounds ( rect.x, rect.y, rect.width + xInc, rect.height + yInc );
                }
                prevX = e.getXOnScreen ();
                prevY = e.getYOnScreen ();
            }
        }
    }

    public void mouseReleased ( MouseEvent e )
    {
        resizing = false;
    }
}

只需使用其“install”方法将窗口大小调整行为添加到任何Component。 resizeSide变量用于定义应调整窗口的哪一侧(例如,SwingConstants.SOUTH_EAST将强制组件调整窗口右下角的大小)。

编辑:您可能还想修改特定情况的代码,以便只从组件上的某个特定区域开始拖动(调整大小)。只需修改mousePressed方法即可。