关于Swing或GUI编程的一个(有点哲学的)问题:是否有公认的最佳实践来确定应用程序中使用的JFrame实例的位置?
- 第一个和主要的框架应该放在哪里?总是在中心(
setLocationRelativeTo(null)
)吗? - 子JFrame应该放在哪里?相对于其父JFrame,在屏幕中心,无论我们想要什么位置?
我一直认为有些最佳实践,就像一本“GUI圣经”一样,我错了吗,我应该(吸气)任意决定要做什么?
关于Swing或GUI编程的一个(有点哲学的)问题:是否有公认的最佳实践来确定应用程序中使用的JFrame实例的位置?
setLocationRelativeTo(null)
)吗?我一直认为有些最佳实践,就像一本“GUI圣经”一样,我错了吗,我应该(吸气)任意决定要做什么?
这里是一个示例,结合了以下建议:
Hovercraft Full Of Eels - 按平台设置位置.
Aardvocate Akintayo Olu - 序列化位置。
但是又增加了两个小改进:
这4个点结合起来提供了最佳用户体验!
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.util.Properties;
import java.io.*;
class RestoreMe {
/** This will end up in the current directory
A more sensible location is a sub-directory of user.home.
(left as an exercise for the reader) */
public static final String fileName = "options.prop";
/** Store location & size of UI */
public static void storeOptions(Frame f) throws Exception {
File file = new File(fileName);
Properties p = new Properties();
// restore the frame from 'full screen' first!
f.setExtendedState(Frame.NORMAL);
Rectangle r = f.getBounds();
int x = (int)r.getX();
int y = (int)r.getY();
int w = (int)r.getWidth();
int h = (int)r.getHeight();
p.setProperty("x", "" + x);
p.setProperty("y", "" + y);
p.setProperty("w", "" + w);
p.setProperty("h", "" + h);
BufferedWriter br = new BufferedWriter(new FileWriter(file));
p.store(br, "Properties of the user frame");
}
/** Restore location & size of UI */
public static void restoreOptions(Frame f) throws IOException {
File file = new File(fileName);
Properties p = new Properties();
BufferedReader br = new BufferedReader(new FileReader(file));
p.load(br);
int x = Integer.parseInt(p.getProperty("x"));
int y = Integer.parseInt(p.getProperty("y"));
int w = Integer.parseInt(p.getProperty("w"));
int h = Integer.parseInt(p.getProperty("h"));
Rectangle r = new Rectangle(x,y,w,h);
f.setBounds(r);
}
public static void main(String[] args) {
final JFrame f = new JFrame("Good Location & Size");
f.setDefaultCloseOperation(JFrame.DO_NOTHING_ON_CLOSE);
f.addWindowListener( new WindowAdapter() {
public void windowClosing(WindowEvent we) {
try {
storeOptions(f);
} catch(Exception e) {
e.printStackTrace();
}
System.exit(0);
}
});
JTextArea ta = new JTextArea(20,50);
f.add(ta);
f.pack();
File optionsFile = new File(fileName);
if (optionsFile.exists()) {
try {
restoreOptions(f);
} catch(IOException ioe) {
ioe.printStackTrace();
}
} else {
f.setLocationByPlatform(true);
}
f.setVisible(true);
}
}
Timer
,设置相同的延迟时间,虽然可能会与关闭进程冲突。1)使用Thread.sleep(n)
暂停EDT可能会导致框架保持相同的大小。 - Andrew Thompson我通常会从主框架的屏幕中心开始,或者从父级别的中心开始对子框架进行定位,并记录该位置。随后,当用户将框架移动到他们想要的任何位置时,我会记录新位置,并在下次启动应用程序时使用最后的位置来放置框架。
不确定是否存在“最佳实践”,因为这是非常主观的。
将其设置在中心并允许用户更改为他们喜欢的位置似乎是理想的选择。
关于子框架,根据其大小,在父框架的中心或只是一些易于使用的东西。
setVisible(true)
上设置的框架的位置设定。 - Andrew Thompson