如何在java中以全屏独占模式处理来自键盘和鼠标的事件?

发布于 2024-12-04 20:15:54 字数 2296 浏览 1 评论 0原文

在被动渲染模式下,可以使用KeyListenerActionListener接口来处理来自用户的事件。

全屏模式下事件处理的正确方法是什么?请扩展此框架,提供鼠标单击和按键事件的实现,请不要膨胀您的示例(该示例启动全屏独占模式,使用 Timer 更新窗口中的图形):

import java.applet.Applet;
import java.awt.Color;
import java.awt.DisplayMode;
import java.awt.Graphics2D;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.Rectangle;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferStrategy;
import javax.swing.JFrame;
import javax.swing.Timer;

public class applet extends Applet
{
    Timer timer;
    JFrame frame;
    DisplayMode[] displayModes = new DisplayMode[] {
            new DisplayMode(1280, 800, 32, 60)
    };

    BufferStrategy bufferStrategy;
    Rectangle bounds;

    /**
     * 
     */
    private static final long serialVersionUID = 1L;

    /**
     * @param args
     */

    public void init()
    {

        GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment(); //displays, fonts, color shemes...
        GraphicsDevice device = env.getDefaultScreenDevice(); //for one-display systems

        setIgnoreRepaint(true);

        GraphicsConfiguration gc = device.getDefaultConfiguration();
        frame = new JFrame(gc);

        device.setFullScreenWindow(frame);

        if (device.isDisplayChangeSupported())
            device.setDisplayMode(displayModes[0]);

        frame.createBufferStrategy(2);
        bufferStrategy = frame.getBufferStrategy();

        timer = new Timer(1000 / 50, new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent arg0) {
                Graphics2D g = null;
                try {
                    g = (Graphics2D) bufferStrategy.getDrawGraphics();
                    render(g);
                } finally {
                    g.dispose();
                }
                bufferStrategy.show();
            }

        });

    }

    private void render(Graphics2D g) {
        g.setColor(Color.BLACK);
        g.fillRect(0, 0, bounds.width, bounds.height);
    }

    public void start()
    {
        timer.start();

    }

    public void stop()
    {
        timer.stop();
    }

}

In passive rendering mode one can use KeyListener and ActionListener interfaces to handle events from user.

What is the correct way of event handling in full screen mode? Please extend this skeleton providing implementation for mouse click and key press events, please don't bloat your example (the example starts full screen exclusive mode, using a Timer to update graphics in window):

import java.applet.Applet;
import java.awt.Color;
import java.awt.DisplayMode;
import java.awt.Graphics2D;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.Rectangle;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferStrategy;
import javax.swing.JFrame;
import javax.swing.Timer;

public class applet extends Applet
{
    Timer timer;
    JFrame frame;
    DisplayMode[] displayModes = new DisplayMode[] {
            new DisplayMode(1280, 800, 32, 60)
    };

    BufferStrategy bufferStrategy;
    Rectangle bounds;

    /**
     * 
     */
    private static final long serialVersionUID = 1L;

    /**
     * @param args
     */

    public void init()
    {

        GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment(); //displays, fonts, color shemes...
        GraphicsDevice device = env.getDefaultScreenDevice(); //for one-display systems

        setIgnoreRepaint(true);

        GraphicsConfiguration gc = device.getDefaultConfiguration();
        frame = new JFrame(gc);

        device.setFullScreenWindow(frame);

        if (device.isDisplayChangeSupported())
            device.setDisplayMode(displayModes[0]);

        frame.createBufferStrategy(2);
        bufferStrategy = frame.getBufferStrategy();

        timer = new Timer(1000 / 50, new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent arg0) {
                Graphics2D g = null;
                try {
                    g = (Graphics2D) bufferStrategy.getDrawGraphics();
                    render(g);
                } finally {
                    g.dispose();
                }
                bufferStrategy.show();
            }

        });

    }

    private void render(Graphics2D g) {
        g.setColor(Color.BLACK);
        g.fillRect(0, 0, bounds.width, bounds.height);
    }

    public void start()
    {
        timer.start();

    }

    public void stop()
    {
        timer.stop();
    }

}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

夏末 2024-12-11 20:15:54

它看起来像如何使用键绑定如何编写鼠标监听器正常工作在 全屏独占模式

import java.awt.Color;
import java.awt.EventQueue;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.WindowEvent;
import javax.swing.AbstractAction;
import javax.swing.Action;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.KeyStroke;

/** @see http://stackoverflow.com/questions/7456227 */
public class FullScreenTest extends JPanel {

    private static final String EXIT = "Exit";
    private JFrame f = new JFrame("FullScreenTest");
    private Action exit = new AbstractAction(EXIT) {

            @Override
            public void actionPerformed(ActionEvent e) {
                f.dispatchEvent(new WindowEvent(
                    f, WindowEvent.WINDOW_CLOSING));
            }
        };
    private JButton b = new JButton(exit);

    public FullScreenTest() {
        this.add(b);
        f.getRootPane().setDefaultButton(b);
        this.getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_Q, 0), EXIT);
        this.getActionMap().put(EXIT, exit);
        this.addMouseMotionListener(new MouseAdapter() {

            @Override
            public void mouseMoved(MouseEvent e) {
                FullScreenTest.this.setToolTipText(
                    "("+ e.getX() + "," + e.getY() + ")");
            }
        });
    }

    private void display() {
        GraphicsEnvironment env =
            GraphicsEnvironment.getLocalGraphicsEnvironment();
        GraphicsDevice dev = env.getDefaultScreenDevice();
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.setBackground(Color.darkGray);
        f.setResizable(false);
        f.setUndecorated(true);
        f.add(this);
        f.pack();
        dev.setFullScreenWindow(f);
    }

    public static void main(String[] args) {
        EventQueue.invokeLater(new Runnable() {

            @Override
            public void run() {
                new FullScreenTest().display();
            }
        });
    }
}

It looks like the usual approaches shown in How to Use Key Bindings and How to Write a Mouse Listener work correctly in Full-Screen Exclusive Mode.

import java.awt.Color;
import java.awt.EventQueue;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.WindowEvent;
import javax.swing.AbstractAction;
import javax.swing.Action;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.KeyStroke;

/** @see http://stackoverflow.com/questions/7456227 */
public class FullScreenTest extends JPanel {

    private static final String EXIT = "Exit";
    private JFrame f = new JFrame("FullScreenTest");
    private Action exit = new AbstractAction(EXIT) {

            @Override
            public void actionPerformed(ActionEvent e) {
                f.dispatchEvent(new WindowEvent(
                    f, WindowEvent.WINDOW_CLOSING));
            }
        };
    private JButton b = new JButton(exit);

    public FullScreenTest() {
        this.add(b);
        f.getRootPane().setDefaultButton(b);
        this.getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_Q, 0), EXIT);
        this.getActionMap().put(EXIT, exit);
        this.addMouseMotionListener(new MouseAdapter() {

            @Override
            public void mouseMoved(MouseEvent e) {
                FullScreenTest.this.setToolTipText(
                    "("+ e.getX() + "," + e.getY() + ")");
            }
        });
    }

    private void display() {
        GraphicsEnvironment env =
            GraphicsEnvironment.getLocalGraphicsEnvironment();
        GraphicsDevice dev = env.getDefaultScreenDevice();
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.setBackground(Color.darkGray);
        f.setResizable(false);
        f.setUndecorated(true);
        f.add(this);
        f.pack();
        dev.setFullScreenWindow(f);
    }

    public static void main(String[] args) {
        EventQueue.invokeLater(new Runnable() {

            @Override
            public void run() {
                new FullScreenTest().display();
            }
        });
    }
}
零時差 2024-12-11 20:15:54

正如此处所建议的,Mac OS X 用户可能对全屏应用程序有不同的期望。 此处显示的另一种方法依赖于com.apple.eawt 类“提供了一种简单的方法来实现本机功能,以在 Mac OS X 上微调 Java 应用程序”。 FullScreenUtilities 方法 setWindowCanFullScreen() 启用该功能,Application 方法 requestToggleFullScreen() 动态更改设置。请注意版本之间的展开图标有何不同。

Mac OS 10.9,小牛队:

10.9

Mac OS 10.10,优胜美地:

10.10

Mac OS X 10.11、El Capitan:

在此处输入图像描述

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.EventQueue;
import java.awt.Window;
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import javax.swing.AbstractAction;
import javax.swing.Action;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.KeyStroke;

/**
 * @see https://stackoverflow.com/a/30308671/230513
 * @see https://stackoverflow.com/questions/7456227
 * @see https://stackoverflow.com/q/13064607/230513
 * @see https://stackoverflow.com/q/30089804/230513
 * @see https://stackoverflow.com/q/25270465/230513
 * @see http://hg.openjdk.java.net/jdk8/jdk8/jdk/file/687fd7c7986d/src/macosx/classes/com/apple/
 */
public class FullScreenTest extends JPanel {

    private static final String NAME = "Mac OS X Full Screen Test";
    private static final String TOGGLE = "Toggle Full Screen";
    private final JFrame f = new JFrame(NAME);
    private final Action exit = new AbstractAction(TOGGLE) {

        @Override
        public void actionPerformed(ActionEvent e) {
            toggleOSXFullscreen(f);
        }
    };
    private final JButton b = new JButton(exit);

    public FullScreenTest() {
        this.add(b);
        f.getRootPane().setDefaultButton(b);
        this.getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_Q, 0), TOGGLE);
        this.getActionMap().put(TOGGLE, exit);
        this.addMouseMotionListener(new MouseAdapter() {

            @Override
            public void mouseMoved(MouseEvent e) {
                FullScreenTest.this.setToolTipText(
                        "(" + e.getX() + "," + e.getY() + ")");
            }
        });
    }

    private void display() {
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.setBackground(Color.darkGray);
        f.add(this);
        f.add(new JLabel(NAME, JLabel.CENTER), BorderLayout.SOUTH);
        f.pack();
        f.setLocationRelativeTo(null);
        f.setVisible(true);
        if (System.getProperty("os.name").startsWith("Mac OS X")) {
            enableOSXFullscreen(f);
            toggleOSXFullscreen(f);
            enableOSXQuitStrategy();
        }
        f.addWindowListener(new WindowAdapter() {

            @Override
            public void windowClosing(WindowEvent e) {
                System.out.println(e);
            }
        });
    }

    //FullScreenUtilities.setWindowCanFullScreen(window, true);
    private void enableOSXFullscreen(Window window) {
        try {
            Class util = Class.forName("com.apple.eawt.FullScreenUtilities");
            Class params[] = new Class[]{Window.class, Boolean.TYPE};
            Method method = util.getMethod("setWindowCanFullScreen", params);
            method.invoke(util, window, true);
        } catch (ClassNotFoundException | NoSuchMethodException |
                SecurityException | IllegalAccessException |
                IllegalArgumentException | InvocationTargetException exp) {
            exp.printStackTrace(System.err);
        }
    }

    //Application.getApplication().requestToggleFullScreen(window);
    private void toggleOSXFullscreen(Window window) {
        try {
            Class application = Class.forName("com.apple.eawt.Application");
            Method getApplication = application.getMethod("getApplication");
            Object instance = getApplication.invoke(application);
            Method method = application.getMethod("requestToggleFullScreen", Window.class);
            method.invoke(instance, window);
        } catch (ClassNotFoundException | NoSuchMethodException |
                SecurityException | IllegalAccessException |
                IllegalArgumentException | InvocationTargetException exp) {
            exp.printStackTrace(System.err);
        }
    }

    //Application.getApplication().setQuitStrategy(QuitStrategy.CLOSE_ALL_WINDOWS);
    private void enableOSXQuitStrategy() {
        try {
            Class application = Class.forName("com.apple.eawt.Application");
            Method getApplication = application.getMethod("getApplication");
            Object instance = getApplication.invoke(application);
            Class strategy = Class.forName("com.apple.eawt.QuitStrategy");
            Enum closeAllWindows = Enum.valueOf(strategy, "CLOSE_ALL_WINDOWS");
            Method method = application.getMethod("setQuitStrategy", strategy);
            method.invoke(instance, closeAllWindows);
        } catch (ClassNotFoundException | NoSuchMethodException |
                SecurityException | IllegalAccessException |
                IllegalArgumentException | InvocationTargetException exp) {
            exp.printStackTrace(System.err);
        }
    }

    public static void main(String[] args) {
        EventQueue.invokeLater(new FullScreenTest()::display);
    }
}

As suggested here, Mac OS X users may have different user expectations for full screen applications. An alternative approach, shown here, relies on com.apple.eawt classes that "provide a simple way to implement native features to fine tune Java applications on Mac OS X." The FullScreenUtilities method setWindowCanFullScreen() enables the feature, and the Application method requestToggleFullScreen() changes the setting dynamically. Note how the expand icon differs among versions.

Mac OS 10.9, Mavericks:

10.9

Mac OS 10.10, Yosemite:

10.10

Mac OS X 10.11, El Capitan:

enter image description here

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.EventQueue;
import java.awt.Window;
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import javax.swing.AbstractAction;
import javax.swing.Action;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.KeyStroke;

/**
 * @see https://stackoverflow.com/a/30308671/230513
 * @see https://stackoverflow.com/questions/7456227
 * @see https://stackoverflow.com/q/13064607/230513
 * @see https://stackoverflow.com/q/30089804/230513
 * @see https://stackoverflow.com/q/25270465/230513
 * @see http://hg.openjdk.java.net/jdk8/jdk8/jdk/file/687fd7c7986d/src/macosx/classes/com/apple/
 */
public class FullScreenTest extends JPanel {

    private static final String NAME = "Mac OS X Full Screen Test";
    private static final String TOGGLE = "Toggle Full Screen";
    private final JFrame f = new JFrame(NAME);
    private final Action exit = new AbstractAction(TOGGLE) {

        @Override
        public void actionPerformed(ActionEvent e) {
            toggleOSXFullscreen(f);
        }
    };
    private final JButton b = new JButton(exit);

    public FullScreenTest() {
        this.add(b);
        f.getRootPane().setDefaultButton(b);
        this.getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_Q, 0), TOGGLE);
        this.getActionMap().put(TOGGLE, exit);
        this.addMouseMotionListener(new MouseAdapter() {

            @Override
            public void mouseMoved(MouseEvent e) {
                FullScreenTest.this.setToolTipText(
                        "(" + e.getX() + "," + e.getY() + ")");
            }
        });
    }

    private void display() {
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.setBackground(Color.darkGray);
        f.add(this);
        f.add(new JLabel(NAME, JLabel.CENTER), BorderLayout.SOUTH);
        f.pack();
        f.setLocationRelativeTo(null);
        f.setVisible(true);
        if (System.getProperty("os.name").startsWith("Mac OS X")) {
            enableOSXFullscreen(f);
            toggleOSXFullscreen(f);
            enableOSXQuitStrategy();
        }
        f.addWindowListener(new WindowAdapter() {

            @Override
            public void windowClosing(WindowEvent e) {
                System.out.println(e);
            }
        });
    }

    //FullScreenUtilities.setWindowCanFullScreen(window, true);
    private void enableOSXFullscreen(Window window) {
        try {
            Class util = Class.forName("com.apple.eawt.FullScreenUtilities");
            Class params[] = new Class[]{Window.class, Boolean.TYPE};
            Method method = util.getMethod("setWindowCanFullScreen", params);
            method.invoke(util, window, true);
        } catch (ClassNotFoundException | NoSuchMethodException |
                SecurityException | IllegalAccessException |
                IllegalArgumentException | InvocationTargetException exp) {
            exp.printStackTrace(System.err);
        }
    }

    //Application.getApplication().requestToggleFullScreen(window);
    private void toggleOSXFullscreen(Window window) {
        try {
            Class application = Class.forName("com.apple.eawt.Application");
            Method getApplication = application.getMethod("getApplication");
            Object instance = getApplication.invoke(application);
            Method method = application.getMethod("requestToggleFullScreen", Window.class);
            method.invoke(instance, window);
        } catch (ClassNotFoundException | NoSuchMethodException |
                SecurityException | IllegalAccessException |
                IllegalArgumentException | InvocationTargetException exp) {
            exp.printStackTrace(System.err);
        }
    }

    //Application.getApplication().setQuitStrategy(QuitStrategy.CLOSE_ALL_WINDOWS);
    private void enableOSXQuitStrategy() {
        try {
            Class application = Class.forName("com.apple.eawt.Application");
            Method getApplication = application.getMethod("getApplication");
            Object instance = getApplication.invoke(application);
            Class strategy = Class.forName("com.apple.eawt.QuitStrategy");
            Enum closeAllWindows = Enum.valueOf(strategy, "CLOSE_ALL_WINDOWS");
            Method method = application.getMethod("setQuitStrategy", strategy);
            method.invoke(instance, closeAllWindows);
        } catch (ClassNotFoundException | NoSuchMethodException |
                SecurityException | IllegalAccessException |
                IllegalArgumentException | InvocationTargetException exp) {
            exp.printStackTrace(System.err);
        }
    }

    public static void main(String[] args) {
        EventQueue.invokeLater(new FullScreenTest()::display);
    }
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文