Hallo,
ich habe folgendes vor: Ich habe ein Programm, das diverse Formulare anzeigt. Wenn jetzt in diesem Programm ein länger dauernder, blockender Prozess gestartet wird, soll das zuletzt gezeigte Formular im Hintergrund sichtbar bleiben, darüber wird ein grau-transparenter Farbverlauf gelegt und darüber wiederum ein Panel mit dem JProgressBar und einigen Labels, die weitere Infos zu dem Prozess liefern. Sozusagen ein schönerer modaler Dialog, dem einen oder anderen vielleicht von Picasa bekannt.
Um das technisch umsetzen zu können, habe ich vor, einen Screenshot des jeweils letzten Formulars zu nehmen, um dieses im Hintergrund anzeigen zu können. Leider kriege ich es nicht hin, den Screenshot genau auf den entsprechenden JComponent auszurichten, es fehlt oben und links jeweils ein Pixel (Was zu Pixelsprüngen des "Hintergrundes" aka Formulars führt und so bestimmt nicht durch die Testabteilung kommt ...).
Hier der Code, den ich zur Anpassung des Bildschirmbereichs benutze (target ist der abzulichtende JComponent):
Die clone() / setLocation()-Konstruktion habe ich gewählt, weil Rectangle anscheinend eine Kopie des benutzten Points rausgibt (Direkte Änderungen an der gelieferten Referenz bringen jedenfalls nichts). Das clone() macht diesen Umstand nur deutlicher.
Für alle, die das Problem live erleben wollen:
Das Anzeigen des Screenshots ist ziemlich hakelig. Mehrfaches Drücken des Buttons "Screenshot" hilft. Verschieben des SplitPane-Dividers ist tödlich für dieses Testprogramm (im Sinne von "Angezeigter Screenshot verschwindet dann").
mpG
Tobias
EDIT. Oben und links fehlt je ein Pixel, nicht "oben und rechts".
ich habe folgendes vor: Ich habe ein Programm, das diverse Formulare anzeigt. Wenn jetzt in diesem Programm ein länger dauernder, blockender Prozess gestartet wird, soll das zuletzt gezeigte Formular im Hintergrund sichtbar bleiben, darüber wird ein grau-transparenter Farbverlauf gelegt und darüber wiederum ein Panel mit dem JProgressBar und einigen Labels, die weitere Infos zu dem Prozess liefern. Sozusagen ein schönerer modaler Dialog, dem einen oder anderen vielleicht von Picasa bekannt.
Um das technisch umsetzen zu können, habe ich vor, einen Screenshot des jeweils letzten Formulars zu nehmen, um dieses im Hintergrund anzeigen zu können. Leider kriege ich es nicht hin, den Screenshot genau auf den entsprechenden JComponent auszurichten, es fehlt oben und links jeweils ein Pixel (Was zu Pixelsprüngen des "Hintergrundes" aka Formulars führt und so bestimmt nicht durch die Testabteilung kommt ...).
Hier der Code, den ich zur Anpassung des Bildschirmbereichs benutze (target ist der abzulichtende JComponent):
Code:
Rectangle r = target.getBounds();
Point newLoc = (Point) r.getLocation().clone();
SwingUtilities.convertPointToScreen(newLoc, target);
r.setLocation(newLoc);
BufferedImage screen = new Robot().createScreenCapture(r);
Die clone() / setLocation()-Konstruktion habe ich gewählt, weil Rectangle anscheinend eine Kopie des benutzten Points rausgibt (Direkte Änderungen an der gelieferten Referenz bringen jedenfalls nichts). Das clone() macht diesen Umstand nur deutlicher.
Für alle, die das Problem live erleben wollen:
Code:
public class ScreenshotTest extends JFrame implements ActionListener {
private JPanel left = createLeftPanel();
private JPanel right = new JPanel();
public ScreenshotTest() {
super("ScreenshotTest");
setLayout(new BorderLayout());
setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
setExtendedState(JFrame.MAXIMIZED_BOTH);
JSplitPane split = new JSplitPane(JSplitPane.HORIZONTAL_SPLIT);
split.setDividerLocation(Toolkit.getDefaultToolkit().getScreenSize().width / 2);
split.add(left);
split.add(right);
add(split, BorderLayout.CENTER);
add(createButtonBar(), BorderLayout.SOUTH);
setVisible(true);
}
public Box createButtonBar() {
Box b = new Box(BoxLayout.LINE_AXIS);
JButton butt = new JButton("Screenshot!");
butt.addActionListener(this);
b.add(butt);
b.add(Box.createGlue());
return b;
}
public JPanel createLeftPanel() {
JPanel p = new JPanel();
p.setLayout(new BoxLayout(p, BoxLayout.PAGE_AXIS));
p.setBorder(BorderFactory.createMatteBorder(1, 1, 1, 1, Color.RED));
p.add(new JLabel("Toller Text!"));
p.add(new JTextField(25) {
@Override
public Dimension getMaximumSize() {
return getPreferredSize();
}
});
p.add(Box.createRigidArea(new Dimension(10, 10)));
p.add(new JLabel("Hallo Tobias!"));
p.add(Box.createGlue());
return p;
}
public JXPanel createScreenshotPanel(JComponent target) throws AWTException {
JXPanel screenShot = new JXPanel();
Rectangle r = target.getBounds();
Point newLoc = (Point) r.getLocation().clone();
SwingUtilities.convertPointToScreen(newLoc, target);
r.setLocation(newLoc);
BufferedImage screen = new Robot().createScreenCapture(r);
ImagePainter paint = new ImagePainter(screen);
Color transGray = new Color(Color.GRAY.getRed() / 255f, Color.GRAY.getGreen() / 255f, Color.GRAY.getBlue() / 255f, 0.7f);
Color transLightGray = new Color(Color.LIGHT_GRAY.getRed() / 255f, Color.LIGHT_GRAY.getGreen() / 255f, Color.LIGHT_GRAY.getBlue() / 255f, 0.7f);
GradientPaint gPaint = new GradientPaint(
0f, 0f,
transLightGray,
1f, 1f,
transGray);
BasicGradientPainter bgPaint = new BasicGradientPainter(gPaint);
// PinstripePainter psPaint = new PinstripePainter(transLightGray, 45);
// psPaint.setSpacing(16);
// psPaint.setStripeWidth(1.0);
screenShot.setBackgroundPainter(new CompoundPainter(paint, bgPaint/*, psPaint*/));
screenShot.setSize(target.getSize());
screenShot.setLayout(null);
JLabel label = new JLabel("Hallo!");
label.setLocation(screenShot.getSize().width / 2, screenShot.getSize().height / 2);
label.setSize(new Dimension(100, 100));
label.setOpaque(true);
screenShot.add(label);
return screenShot;
}
/**
* @param args
* @throws AWTException
*/
public static void main(String[] args) {
new ScreenshotTest();
}
/*
* @see java.awt.event.ActionListener#actionPerformed(java.awt.event.ActionEvent)
*/
public void actionPerformed(ActionEvent e) {
try {
right.removeAll();
right.add(createScreenshotPanel(left));
repaint();
}
catch(Exception ex) {
}
}
}
Das Anzeigen des Screenshots ist ziemlich hakelig. Mehrfaches Drücken des Buttons "Screenshot" hilft. Verschieben des SplitPane-Dividers ist tödlich für dieses Testprogramm (im Sinne von "Angezeigter Screenshot verschwindet dann").
mpG
Tobias
EDIT. Oben und links fehlt je ein Pixel, nicht "oben und rechts".