I would like to know if theres a possibility to implement the resizing of a JFrame in that manner, that it's been resized like for example the standart windows in linux. To be more precise: If the user starts do drag, only the future size if the window will be previewed, while the original content is not resized. As soon as the user releases the mouse, the Frame resizes to that size. In images:
(1) state before resizing
(2) user starts to drage (at the red circle)
(3) user releases the mouse, the frame gets resized
Is it possible to realize that in Java Swing?
EDIT:
As this program one day should run also in lower Java RE as the 7, I tried to combine mKorbel suggestions with and the suggestion in the comment with the translucend Frame. The result is close to the goal, except that
- The content of the contentPane resizes after I stop moving the mouse, not when the mouse is released
- The frame title is resized immediately, not just whend I stop dragging the frame border.
- It works only if resized from right or bottom, otherwise the content moves with the dragging.
I think the first point is resolvable by a combination of the code and a MouseListener, something like if mouseReleased(), then resize . Here is the code, feel free to try it. For further suggestions I'm still happy about any suggestions.
The code is a slightly modification of the GradientTranslucentWindowDemo.java from the Java Tutorials. I hope it's permitted to post it here, otherwise please indicate me any violation against copyright causas. The black JPanel is supposed to be the content of the application, where as the contentPane stays invisible.
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ComponentEvent;
import java.awt.event.ComponentListener;
import java.beans.PropertyChangeListener;
import javax.swing.*;
import static java.awt.GraphicsDevice.WindowTranslucency.*;
public class GroundFrame extends JFrame {
Timer timer;
JPanel panel2;
public GroundFrame() {
super("GradientTranslucentWindow");
setBackground(new Color(0,0,0,0));
setSize(new Dimension(300,200));
setLocationRelativeTo(null);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JPanel panel = new JPanel() {
panel.setBackground(new Color(0,0,0,0));
setContentPane(panel);
setLayout(null);
panel2 = new JPanel();
panel2.setBackground(Color.black);
panel2.setBounds(0,0,getContentPane().getWidth(), getContentPane().getHeight());
getContentPane().add(panel2);
addComponentListener(new ComponentListener() {
@Override
public void componentShown(ComponentEvent e) {}
@Override
public void componentResized(ComponentEvent e) {
timer = new Timer(50, new Action() {
@Override
public void actionPerformed(ActionEvent e) {
if(timer.isRunning()){
}else{
resizePanel(getContentPane().getSize());
}
}
@Override
public void setEnabled(boolean b) {}
@Override
public void removePropertyChangeListener(PropertyChangeListener listener) {}
@Override
public void putValue(String key, Object value) {}
@Override
public boolean isEnabled() {return false;}
@Override
public Object getValue(String key) {return null;}
@Override
public void addPropertyChangeListener(PropertyChangeListener listener) {}
});
timer.setRepeats(false);
timer.start();
}
@Override
public void componentMoved(ComponentEvent e) {}
@Override
public void componentHidden(ComponentEvent e) {}
});
}
public void resizePanel(Dimension dim){
panel2.setBounds(0,0,dim.width, dim.height);
repaint();
}
public static void main(String[] args) {
GraphicsEnvironment ge =
GraphicsEnvironment.getLocalGraphicsEnvironment();
GraphicsDevice gd = ge.getDefaultScreenDevice();
boolean isPerPixelTranslucencySupported =
gd.isWindowTranslucencySupported(PERPIXEL_TRANSLUCENT);
if (!isPerPixelTranslucencySupported) {
System.out.println(
"Per-pixel translucency is not supported");
System.exit(0);
}
JFrame.setDefaultLookAndFeelDecorated(true);
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
GroundFrame gtw = new GroundFrame();
gtw.setVisible(true);
}
});
}
}
+1 to mKorbel and Denis Tulskiy's answers.
I did a sort of abstract solution which might be of help. It supports resizing (increasing and decreasing height and width) of
JFrame
from all four sides of theJFrame
(NORTH, EAST, SOUTH and WEST) it also can be re-sized by width and height simultaneously when mouse is moved to one of the for corners.Basically what I did was:
MouseMotionListener
andMouseListener
toJFrame
mouseDragged(..)
,mouseMoved(..)
,mousePressed(..)
andmouseReleased(..)
ofListener
s.JFrame
to be non resizable.mouseMoved(..)
listen for when mouse is 10px or less from bottom or right side. ofJFrame
, it then sets the appropriate direction of resize (height or width), changes mouseCursor
(Cursor.getPredefinedCursor(Cursor.E_RESIZE_CURSOR)
for far right/width resizing,Cursor.getPredefinedCursor(Cursor.S_RESIZE_CURSOR)
for bottom/hieght resizing,Cursor.getPredefinedCursor(Cursor.N_RESIZE_CURSOR)
for top of frame height resizing orCursor.getPredefinedCursor(Cursor.W_RESIZE_CURSOR)
for left side width resizing) accordingly and callcanResize(true)
.mouseDragged(..)
update the width or height for new size as its dragged in directionmouseReleased(..)
set theJFrame
to the new size.mousePressed(..)
we check for user pressed co-ordinates (this allows us to see if frame size is decreasing/increasing).Check out this example I made:
UPDATE:
Great example you made I fixed the code by adding
MouseAdapter
which overridesmouseReleased(..)
which callsresizePanel(...)
whenmouseReleased(..)
see here for the fixed code (also fixed a few minor things like added
ComponentAdapter
instead ofComponentListener
andAbstractAction
instead ofAction
):