Package com.ardor3d.framework.jogl

Source Code of com.ardor3d.framework.jogl.JoglCanvas

/**
* Copyright (c) 2008-2010 Ardor Labs, Inc.
*
* This file is part of Ardor3D.
*
* Ardor3D is free software: you can redistribute it and/or modify it
* under the terms of its license which may be found in the accompanying
* LICENSE file or at <http://www.ardor3d.com/LICENSE>.
*/

package com.ardor3d.framework.jogl;

import java.awt.Dimension;
import java.awt.DisplayMode;
import java.awt.Frame;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.Toolkit;
import java.awt.event.FocusListener;
import java.awt.event.KeyListener;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
import java.awt.event.MouseWheelListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.util.concurrent.CountDownLatch;
import java.util.logging.Level;
import java.util.logging.Logger;

import javax.media.opengl.GLContext;
import javax.media.opengl.GLException;

import com.ardor3d.annotation.MainThread;
import com.ardor3d.framework.CanvasRenderer;
import com.ardor3d.framework.DisplaySettings;
import com.ardor3d.framework.NativeCanvas;
import com.ardor3d.image.Image;
import com.ardor3d.renderer.jogl.JoglPbufferTextureRenderer;

/**
* A canvas implementation for use with native JOGL windows.
*/
public class JoglCanvas extends Frame implements NativeCanvas {

    private static final long serialVersionUID = 1L;

    private static final Logger logger = Logger.getLogger(JoglCanvas.class.getName());

    private final DisplaySettings _settings;
    private boolean _inited = false;
    private boolean _isClosing = false;

    private JoglAwtCanvas _glCanvas;

    public JoglCanvas(final JoglCanvasRenderer canvasRenderer, final DisplaySettings settings) {
        _settings = settings;

        // Create the OpenGL canvas
        _glCanvas = new JoglAwtCanvas(_settings, canvasRenderer);

        // Default is not-resizeable. If you turn on resizeable, know what you are doing.
        setResizable(false);
    }

    @Override
    public void addKeyListener(final KeyListener l) {
        _glCanvas.addKeyListener(l);
    }

    @Override
    public void addMouseListener(final MouseListener l) {
        _glCanvas.addMouseListener(l);
    }

    @Override
    public void addMouseMotionListener(final MouseMotionListener l) {
        _glCanvas.addMouseMotionListener(l);
    }

    @Override
    public void addMouseWheelListener(final MouseWheelListener l) {
        _glCanvas.addMouseWheelListener(l);
    }

    @Override
    public void addFocusListener(final FocusListener l) {
        _glCanvas.addFocusListener(l);
    }

    @MainThread
    public void init() {
        privateInit();
    }

    @MainThread
    protected void privateInit() {
        if (_inited) {
            return;
        }

        // FIXME: remove need for directly setting _parentContext.
        JoglPbufferTextureRenderer._parentContext = _glCanvas.getContext();

        this.add(_glCanvas);

        final boolean isDisplayModeModified;
        final GraphicsDevice gd = GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice();
        // Get the current display mode
        final DisplayMode previousDisplayMode = gd.getDisplayMode();
        // Handle full screen mode if requested.
        if (_settings.isFullScreen()) {
            setUndecorated(true);
            // Check if the full-screen mode is supported by the OS
            boolean isFullScreenSupported = gd.isFullScreenSupported();
            if (isFullScreenSupported) {
                gd.setFullScreenWindow(this);
                // Check if display mode changes are supported by the OS
                if (gd.isDisplayChangeSupported()) {
                    // Get all available display modes
                    final DisplayMode[] displayModes = gd.getDisplayModes();
                    DisplayMode multiBitsDepthSupportedDisplayMode = null;
                    DisplayMode refreshRateUnknownDisplayMode = null;
                    DisplayMode multiBitsDepthSupportedAndRefreshRateUnknownDisplayMode = null;
                    DisplayMode matchingDisplayMode = null;
                    DisplayMode currentDisplayMode;
                    // Look for the display mode that matches with our parameters
                    // Look for some display modes that are close to these parameters
                    // and that could be used as substitutes
                    // On some machines, the refresh rate is unknown and/or multi bit
                    // depths are supported. If you try to force a particular refresh
                    // rate or a bit depth, you might find no available display mode
                    // that matches exactly with your parameters
                    for (int i = 0; i < displayModes.length && matchingDisplayMode == null; i++) {
                        currentDisplayMode = displayModes[i];
                        if (currentDisplayMode.getWidth() == _settings.getWidth()
                                && currentDisplayMode.getHeight() == _settings.getHeight()) {
                            if (currentDisplayMode.getBitDepth() == _settings.getColorDepth()) {
                                if (currentDisplayMode.getRefreshRate() == _settings.getFrequency()) {
                                    matchingDisplayMode = currentDisplayMode;
                                } else if (currentDisplayMode.getRefreshRate() == DisplayMode.REFRESH_RATE_UNKNOWN) {
                                    refreshRateUnknownDisplayMode = currentDisplayMode;
                                }
                            } else if (currentDisplayMode.getBitDepth() == DisplayMode.BIT_DEPTH_MULTI) {
                                if (currentDisplayMode.getRefreshRate() == _settings.getFrequency()) {
                                    multiBitsDepthSupportedDisplayMode = currentDisplayMode;
                                } else if (currentDisplayMode.getRefreshRate() == DisplayMode.REFRESH_RATE_UNKNOWN) {
                                    multiBitsDepthSupportedAndRefreshRateUnknownDisplayMode = currentDisplayMode;
                                }
                            }
                        }
                    }
                    DisplayMode nextDisplayMode = null;
                    if (matchingDisplayMode != null) {
                        nextDisplayMode = matchingDisplayMode;
                    } else if (multiBitsDepthSupportedDisplayMode != null) {
                        nextDisplayMode = multiBitsDepthSupportedDisplayMode;
                    } else if (refreshRateUnknownDisplayMode != null) {
                        nextDisplayMode = refreshRateUnknownDisplayMode;
                    } else if (multiBitsDepthSupportedAndRefreshRateUnknownDisplayMode != null) {
                        nextDisplayMode = multiBitsDepthSupportedAndRefreshRateUnknownDisplayMode;
                    } else {
                        isFullScreenSupported = false;
                    }
                    // If we have found a display mode that approximatively matches
                    // with the input parameters, use it
                    if (nextDisplayMode != null) {
                        gd.setDisplayMode(nextDisplayMode);
                        isDisplayModeModified = true;
                    } else {
                        isDisplayModeModified = false;
                    }
                } else {
                    isDisplayModeModified = false;
                    // Resize the canvas if the display mode cannot be changed
                    // and the screen size is not equal to the canvas size
                    final Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
                    if (screenSize.width != _settings.getWidth() || screenSize.height != _settings.getHeight()) {
                        _glCanvas.setSize(screenSize);
                    }
                }
            } else {
                isDisplayModeModified = false;
            }

            // Software windowed full-screen mode
            if (!isFullScreenSupported) {
                final Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
                // Resize the canvas
                _glCanvas.setSize(screenSize);
                // Resize the frame so that it occupies the whole screen
                this.setSize(screenSize);
                // Set its location at the top left corner
                this.setLocation(0, 0);
            }
        }
        // Otherwise, center the window on the screen.
        else {
            isDisplayModeModified = false;
            pack();

            int x, y;
            x = (Toolkit.getDefaultToolkit().getScreenSize().width - _settings.getWidth()) / 2;
            y = (Toolkit.getDefaultToolkit().getScreenSize().height - _settings.getHeight()) / 2;
            this.setLocation(x, y);
        }

        addWindowListener(new WindowAdapter() {
            @Override
            public void windowClosing(final WindowEvent e) {
                _isClosing = true;
                // If required, restore the previous display mode
                if (isDisplayModeModified) {
                    gd.setDisplayMode(previousDisplayMode);
                }
                // If required, get back to the windowed mode
                if (gd.getFullScreenWindow() == JoglCanvas.this) {
                    gd.setFullScreenWindow(null);
                }
            }
        });

        // Make the window visible to realize the OpenGL surface.
        setVisible(true);

        _glCanvas.init(); // true - do swap in renderer.
        _inited = true;
    }

    public void draw(final CountDownLatch latch) {
        if (!_inited) {
            privateInit();
        }

        _glCanvas.draw(latch);
    }

    public CanvasRenderer getCanvasRenderer() {
        return _glCanvas.getCanvasRenderer();
    }

    public void close() {
        try {
            if (GLContext.getCurrent() != null) {
                // Release the OpenGL resources.
                GLContext.getCurrent().release();
            }
        } catch (final GLException releaseFailure) {
            logger.log(Level.WARNING, "Failed to release OpenGL Context: " + _glCanvas, releaseFailure);
        } finally {
            _glCanvas = null;
        }

        // Dispose of any window resources.
        dispose();
    }

    @Override
    public boolean isActive() {
        return hasFocus();
    }

    public boolean isClosing() {
        return _isClosing;
    }

    public void moveWindowTo(final int locX, final int locY) {
        setLocation(locX, locY);
    }

    public void setIcon(final Image[] iconImages) {
        // FIXME not implemented
    }

    public void setVSyncEnabled(final boolean enabled) {
        _glCanvas.setVSyncEnabled(enabled);
    }
}
TOP

Related Classes of com.ardor3d.framework.jogl.JoglCanvas

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.