aboutsummaryrefslogtreecommitdiff
path: root/test/sun/java2d/pipe/hw/VSyncedBufferStrategyTest/VSyncedBufferStrategyTest.java
diff options
context:
space:
mode:
Diffstat (limited to 'test/sun/java2d/pipe/hw/VSyncedBufferStrategyTest/VSyncedBufferStrategyTest.java')
-rw-r--r--test/sun/java2d/pipe/hw/VSyncedBufferStrategyTest/VSyncedBufferStrategyTest.java338
1 files changed, 338 insertions, 0 deletions
diff --git a/test/sun/java2d/pipe/hw/VSyncedBufferStrategyTest/VSyncedBufferStrategyTest.java b/test/sun/java2d/pipe/hw/VSyncedBufferStrategyTest/VSyncedBufferStrategyTest.java
new file mode 100644
index 000000000..cec37046c
--- /dev/null
+++ b/test/sun/java2d/pipe/hw/VSyncedBufferStrategyTest/VSyncedBufferStrategyTest.java
@@ -0,0 +1,338 @@
+/*
+ * Copyright 2007-2008 Sun Microsystems, Inc. All Rights Reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
+ * CA 95054 USA or visit www.sun.com if you need additional information or
+ * have any questions.
+ */
+/*
+ * @test
+ * @bug 6678218 6681745 6691737
+ * @summary Tests that v-synced BufferStrategies works (if vsync is supported)
+ * @author Dmitri.Trembovetski@sun.com: area=Graphics
+ * @compile -XDignore.symbol.file=true VSyncedBufferStrategyTest.java
+ * @run main/manual/othervm VSyncedBufferStrategyTest
+ * @run main/manual/othervm -Dsun.java2d.opengl=True VSyncedBufferStrategyTest
+ */
+
+import java.awt.AWTException;
+import java.awt.BufferCapabilities;
+import java.awt.BufferCapabilities.FlipContents;
+import java.awt.Button;
+import java.awt.Canvas;
+import java.awt.Color;
+import java.awt.Dimension;
+import java.awt.EventQueue;
+import java.awt.FlowLayout;
+import java.awt.Font;
+import java.awt.Frame;
+import java.awt.Graphics;
+import java.awt.HeadlessException;
+import java.awt.ImageCapabilities;
+import java.awt.Panel;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+import java.awt.event.WindowAdapter;
+import java.awt.event.WindowEvent;
+import java.awt.image.BufferStrategy;
+import java.util.concurrent.CountDownLatch;
+import javax.swing.JButton;
+import javax.swing.JFrame;
+import javax.swing.JPanel;
+import javax.swing.JScrollPane;
+import javax.swing.JTextArea;
+
+public class VSyncedBufferStrategyTest extends Canvas implements Runnable {
+
+ private static final int BLOCK_W = 50;
+ private static final int BLOCK_H = 200;
+
+ BufferStrategy bs;
+ Thread renderThread;
+
+ int blockX = 10;
+ int blockY = 10;
+
+ private volatile boolean done = false;
+ private volatile boolean requestVSync;
+ private boolean currentBSVSynced;
+
+ public VSyncedBufferStrategyTest(boolean requestVSync) {
+ this.requestVSync = requestVSync;
+ this.currentBSVSynced = !requestVSync;
+ renderThread = new Thread(this);
+ renderThread.start();
+ }
+
+ private static final BufferCapabilities defaultBC =
+ new BufferCapabilities(
+ new ImageCapabilities(true),
+ new ImageCapabilities(true),
+ null);
+
+ private void createBS(boolean requestVSync) {
+ if (bs != null && requestVSync == currentBSVSynced) {
+ return;
+ }
+
+ BufferCapabilities bc = defaultBC;
+ if (requestVSync) {
+ bc = new sun.java2d.pipe.hw.ExtendedBufferCapabilities(
+ new ImageCapabilities(true),
+ new ImageCapabilities(true),
+ FlipContents.COPIED,
+ sun.java2d.pipe.hw.ExtendedBufferCapabilities.VSyncType.VSYNC_ON);
+ }
+ try {
+ createBufferStrategy(2, bc);
+ } catch (AWTException e) {
+ System.err.println("Warning: cap is not supported: "+bc);
+ e.printStackTrace();
+ createBufferStrategy(2);
+ }
+ currentBSVSynced = requestVSync;
+ bs = getBufferStrategy();
+ String s =
+ getParent() instanceof Frame ?
+ ((Frame)getParent()).getTitle() : "parent";
+ System.out.println("Created BS for \"" + s + "\" frame, bs="+bs);
+ }
+
+ @Override
+ public void paint(Graphics g) {
+ }
+ @Override
+ public void update(Graphics g) {
+ }
+
+ @Override
+ public void run() {
+ while (!isShowing()) {
+ try { Thread.sleep(5); } catch (InterruptedException e) {}
+ }
+ try { Thread.sleep(2000); } catch (InterruptedException e) {}
+
+ try {
+ while (!done && isShowing()) {
+ createBS(requestVSync);
+ do {
+ step();
+ Graphics g = bs.getDrawGraphics();
+ render(g);
+ if (!bs.contentsRestored()) {
+ bs.show();
+ }
+ } while (bs.contentsLost());
+ Thread.yield();
+ }
+ } catch (Throwable e) {
+ // since we're not bothering with proper synchronization, exceptions
+ // may be thrown when the frame is closed
+ if (isShowing()) {
+ throw new RuntimeException(e);
+ }
+ }
+ }
+
+ int inc = 5;
+ private void step() {
+ blockX += inc;
+ if (blockX > getWidth() - BLOCK_W - 10) {
+ inc = -inc;
+ blockX += inc;
+ }
+ if (blockX < 10) {
+ inc = -inc;
+ blockX += inc;
+ }
+ }
+
+ private void render(Graphics g) {
+ g.setColor(Color.white);
+ g.fillRect(0, 0, getWidth(), getHeight());
+
+ g.setColor(Color.black);
+ g.fillRect(blockX, blockY, BLOCK_W, BLOCK_H);
+ }
+
+ private void setRequestVSync(boolean reqVSync) {
+ requestVSync = reqVSync;
+ }
+
+ @Override
+ public Dimension getPreferredSize() {
+ return new Dimension(BLOCK_W*10+20, BLOCK_H+20);
+ }
+
+ private static int frameNum = 0;
+ private static Frame createAndShowBSFrame() {
+ final Frame f = new Frame("Not V-Synced");
+
+ int myNum;
+ synchronized (VSyncedBufferStrategyTest.class) {
+ myNum = frameNum++;
+ }
+
+ final VSyncedBufferStrategyTest component =
+ new VSyncedBufferStrategyTest(false);
+ f.setIgnoreRepaint(true);
+ f.add("Center", component);
+
+ Panel p = new Panel();
+
+ Button b = new Button("Request VSync");
+ b.addActionListener(new ActionListener() {
+ public void actionPerformed(ActionEvent e) {
+ f.setTitle("Possibly V-Synced");
+ component.setRequestVSync(true);
+ }
+ });
+ p.add(b);
+
+ b = new Button("Relinquish VSync");
+ b.addActionListener(new ActionListener() {
+ int inc = 1;
+ public void actionPerformed(ActionEvent e) {
+ f.setTitle("Not V-Synced");
+ component.setRequestVSync(false);
+ f.setSize(f.getWidth()+inc, f.getHeight());
+ inc = -inc;
+ }
+ });
+ p.add(b);
+
+ f.add("South", p);
+
+ f.pack();
+ f.setLocation(10, myNum * f.getHeight());
+ f.setVisible(true);
+ f.addWindowListener(new WindowAdapter() {
+ @Override
+ public void windowClosing(WindowEvent e) {
+ component.done = true;
+ f.dispose();
+ }
+ @Override
+ public void windowClosed(WindowEvent e) {
+ component.done = true;
+ }
+ });
+
+ return f;
+ }
+
+ private static final String description =
+ "Tests that v-synced BufferStrategy works. Note that it in some\n" +
+ "cases the v-sync can not be enabled, and it is accepted.\n" +
+ "The following however is true: only one buffer strategy at a time can\n"+
+ "be created v-synced. In order for other BS to become v-synced, the one\n"+
+ "that currently is v-synched (or its window) needs to be disposed.\n" +
+ "Try the following scenarios:\n" +
+ " - click the \"Request VSync\" button in one of the frames. If the\n"+
+ " behavior of the animation changes - the animation becomes smooth\n" +
+ " it had successfully created a v-synced BS. Note that the animation\n" +
+ " in other frames may also become smoother - this is a side-effect\n"+
+ " of one of the BS-es becoming v-synched\n" +
+ " - click the \"Relinquish VSync\" button on the same frame. If the\n"+
+ " behavior changes to the original (tearing)- it had successfully\n" +
+ " created a non-vsynced strategy.\n" +
+ " - next, try making another one v-synced. It should succeed.\n" +
+ " - next, try making another one v-synced - while there's already\n" +
+ " a v-synced frame. It should not succeed - meaning, it shouldn't\n" +
+ " appear to become smoother, and the behavior of the current v-synced\n" +
+ " frame shouldn't change.\n" +
+ "\n" +
+ "If there aren't any BufferStrategy-related exceptions or other\n" +
+ "issues, and the scenarios worked, the test passed, otherwise it\n"+
+ "failed.\n";
+
+ private static void createAndShowDescGUI(final Frame f3, final Frame f1,
+ final Frame f2)
+ throws HeadlessException, RuntimeException
+ {
+ final JFrame desc =
+ new JFrame("VSyncedBufferStrategyTest - Description");
+ desc.addWindowListener(new WindowAdapter() {
+
+ @Override
+ public void windowClosing(WindowEvent e) {
+ f1.dispose();
+ f2.dispose();
+ f3.dispose();
+ l.countDown();
+ }
+ });
+ JPanel p = new JPanel();
+ JButton bPassed = new JButton("Passed");
+ bPassed.addActionListener(new ActionListener() {
+ public void actionPerformed(ActionEvent e) {
+ desc.dispose();
+ f1.dispose();
+ f2.dispose();
+ f3.dispose();
+ l.countDown();
+ }
+ });
+ JButton bFailed = new JButton("Failed");
+ bFailed.addActionListener(new ActionListener() {
+ public void actionPerformed(ActionEvent e) {
+ failed = true;
+ desc.dispose();
+ f1.dispose();
+ f2.dispose();
+ f3.dispose();
+ l.countDown();
+ }
+ });
+ p.setLayout(new FlowLayout());
+ p.add(bPassed);
+ p.add(bFailed);
+ JTextArea ta = new JTextArea(24, 75);
+ ta.setFont(new Font(Font.MONOSPACED, Font.PLAIN, 12));
+ ta.setEditable(false);
+ ta.setText(description);
+ desc.add("Center", new JScrollPane(ta));
+ desc.add("South", p);
+ desc.pack();
+ desc.setLocation(BLOCK_W*10+50, 0);
+ desc.setVisible(true);
+ }
+
+ private static void createTestFrames() {
+ Frame f1 = createAndShowBSFrame();
+ Frame f2 = createAndShowBSFrame();
+ Frame f3 = createAndShowBSFrame();
+ createAndShowDescGUI(f1, f2, f3);
+ }
+
+ static boolean failed = false;
+ static CountDownLatch l = new CountDownLatch(1);
+ public static void main(String[] args) throws Exception {
+ EventQueue.invokeLater(new Runnable() {
+ public void run() {
+ createTestFrames();
+ }
+ });
+ l.await();
+ if (failed) {
+ throw new RuntimeException("Test FAILED");
+ }
+ System.out.println("Test PASSED");
+ }
+
+}