You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
310 lines
8.4 KiB
310 lines
8.4 KiB
#pragma once
|
|
|
|
#include "ofBaseApp.h"
|
|
|
|
#include "ofAppBaseWindow.h"
|
|
#include "ofThread.h"
|
|
#include "ofImage.h"
|
|
#include "ofBaseTypes.h"
|
|
#include "ofEvents.h"
|
|
#include "ofConstants.h"
|
|
#include "ofTypes.h"
|
|
|
|
// include includes for both native and X11 possibilities
|
|
#include <libudev.h>
|
|
#include <stdbool.h>
|
|
#include <stdio.h> // sprintf
|
|
#include <stdlib.h> // malloc
|
|
#include <math.h>
|
|
#include <fcntl.h> // open fcntl
|
|
#include <unistd.h> // read close
|
|
#include <linux/joystick.h>
|
|
|
|
#include "linux/kd.h" // keyboard stuff...
|
|
#include "termios.h"
|
|
#include "sys/ioctl.h"
|
|
|
|
#include <dirent.h> // scandir
|
|
#include <string.h> // strlen
|
|
|
|
// x11
|
|
#include <X11/Xlib.h>
|
|
#include <X11/Xutil.h>
|
|
|
|
#include <queue>
|
|
#include <map>
|
|
|
|
#include <EGL/egl.h>
|
|
|
|
// TODO: this shold be passed in with the other window settings, like window alpha, etc.
|
|
enum ofAppEGLWindowType {
|
|
OF_APP_WINDOW_AUTO,
|
|
OF_APP_WINDOW_NATIVE,
|
|
OF_APP_WINDOW_X11
|
|
};
|
|
|
|
struct ofAppEGLWindowMouseArgs {
|
|
string deviceName;
|
|
int fildes; // File Descriptor
|
|
int absXMin;
|
|
int absXMax;
|
|
int absYMin;
|
|
int absYMax;
|
|
float scaleX;
|
|
float scaleY;
|
|
};
|
|
|
|
typedef std::map<EGLint,EGLint> ofEGLAttributeList;
|
|
typedef std::map<EGLint,EGLint>::iterator ofEGLAttributeListIterator;
|
|
|
|
class ofAppEGLWindow : public ofAppBaseGLESWindow, public ofThread {
|
|
public:
|
|
|
|
struct Settings;
|
|
|
|
ofAppEGLWindow();
|
|
virtual ~ofAppEGLWindow();
|
|
|
|
static void loop(){};
|
|
static bool doesLoop(){ return false; }
|
|
static bool allowsMultiWindow(){ return false; }
|
|
static bool needsPolling(){ return true; }
|
|
static void pollEvents();
|
|
|
|
using ofAppBaseGLESWindow::setup;
|
|
void setup(const Settings & settings);
|
|
void setup(const ofGLESWindowSettings & settings);
|
|
|
|
void update();
|
|
void draw();
|
|
void close();
|
|
void makeCurrent();
|
|
void swapBuffers();
|
|
void startRender();
|
|
void finishRender();
|
|
|
|
ofCoreEvents & events();
|
|
std::shared_ptr<ofBaseRenderer> & renderer();
|
|
|
|
void setThreadTimeout(long timeOut){ threadTimeout = timeOut; }
|
|
|
|
virtual void hideCursor();
|
|
virtual void showCursor();
|
|
|
|
virtual void setWindowPosition(int x, int y);
|
|
virtual void setWindowShape(int w, int h);
|
|
|
|
virtual glm::vec2 getWindowPosition();
|
|
virtual glm::vec2 getWindowSize();
|
|
virtual glm::vec2 getScreenSize();
|
|
|
|
virtual void setOrientation(ofOrientation orientation);
|
|
virtual ofOrientation getOrientation();
|
|
virtual bool doesHWOrientation();
|
|
|
|
//this is used by ofGetWidth and now determines the window width based on orientation
|
|
virtual int getWidth();
|
|
virtual int getHeight();
|
|
|
|
virtual void setWindowTitle(std::string title); // TODO const correct
|
|
|
|
virtual ofWindowMode getWindowMode();
|
|
|
|
virtual void setFullscreen(bool fullscreen);
|
|
virtual void toggleFullscreen();
|
|
|
|
virtual void enableSetupScreen();
|
|
virtual void disableSetupScreen();
|
|
|
|
virtual void setVerticalSync(bool enabled);
|
|
|
|
struct Settings: public ofGLESWindowSettings {
|
|
public:
|
|
ofAppEGLWindowType eglWindowPreference; // what window type is preferred?
|
|
EGLint eglWindowOpacity; // 0-255 window alpha value
|
|
|
|
ofEGLAttributeList frameBufferAttributes;
|
|
// surface creation
|
|
ofEGLAttributeList windowSurfaceAttributes;
|
|
|
|
ofColor initialClearColor;
|
|
|
|
int screenNum;
|
|
int layer;
|
|
|
|
Settings();
|
|
Settings(const ofGLESWindowSettings & settings);
|
|
};
|
|
|
|
EGLDisplay getEglDisplay() const;
|
|
EGLSurface getEglSurface() const;
|
|
EGLContext getEglContext() const;
|
|
|
|
#ifndef TARGET_RASPBERRY_PI
|
|
Display* getX11Display();
|
|
Window getX11Window();
|
|
#endif
|
|
|
|
EGLConfig getEglConfig() const;
|
|
|
|
EGLint getEglVersionMajor () const;
|
|
EGLint getEglVersionMinor() const;
|
|
|
|
|
|
protected:
|
|
void setWindowRect(const ofRectangle& requestedWindowRect);
|
|
|
|
|
|
// bool create
|
|
|
|
virtual void setupPeripherals();
|
|
|
|
virtual ofRectangle getScreenRect();
|
|
|
|
int getWindowWidth();
|
|
int getWindowHeight();
|
|
|
|
ofWindowMode windowMode;
|
|
bool bNewScreenMode; ///< \brief This indicates if a (new) window rectangle has to be adjusted.
|
|
int buttonInUse; ///< \brief Mouse button currently in use.
|
|
bool bEnableSetupScreen; ///< \brief This indicates the need/intent to draw a setup screen.
|
|
bool bShowCursor; ///< \brief Indicate the visibility of the (mouse) cursor.
|
|
|
|
std::string eglDisplayString;
|
|
int nFramesSinceWindowResized; ///< \brief The number of frames passed/shown since the window got resized.
|
|
ofOrientation orientation;
|
|
|
|
|
|
void threadedFunction();
|
|
std::queue<ofMouseEventArgs> mouseEvents;
|
|
std::queue<ofKeyEventArgs> keyEvents;
|
|
void checkEvents();
|
|
ofImage mouseCursor;
|
|
|
|
// TODO: getters and setters? OR automatically set based on
|
|
// OS or screen size? Should be changed when screen is resized?
|
|
float mouseScaleX; ///< \brief Amount by which to mouse movements along the X axis.
|
|
float mouseScaleY; ///< \brief Amount by which to mouse movements along the Y axis.
|
|
|
|
|
|
// float getMouseScaleX() const;
|
|
// void setMouseScaleX(float x);
|
|
// float getMouseScaleY() const;
|
|
// void setMouseScaleY(float y);
|
|
|
|
// For absolute input devices that send ABS_X and ABS_Y events, we want to store
|
|
// information about the min and max axis values.
|
|
int mouseAbsXMin;
|
|
int mouseAbsXMax;
|
|
int mouseAbsYMin;
|
|
int mouseAbsYMax;
|
|
|
|
// TODO: a list of all valid and open mouse devices
|
|
// Store open mouse device file descriptors
|
|
vector<ofAppEGLWindowMouseArgs> mice;
|
|
|
|
bool hasMouse() { return mouseDetected; }
|
|
bool hasKeyboard() { return keyboardDetected; }
|
|
|
|
|
|
//------------------------------------------------------------
|
|
// EGL
|
|
//------------------------------------------------------------
|
|
|
|
bool createSurface();
|
|
bool destroySurface();
|
|
|
|
// bool resizeSurface();
|
|
|
|
EGLDisplay eglDisplay; // EGL display connection
|
|
EGLSurface eglSurface;
|
|
EGLContext eglContext;
|
|
|
|
EGLConfig eglConfig;
|
|
|
|
EGLint eglVersionMajor;
|
|
EGLint eglVersionMinor;
|
|
|
|
//------------------------------------------------------------
|
|
// PLATFORM SPECIFIC WINDOWING
|
|
//------------------------------------------------------------
|
|
|
|
//------------------------------------------------------------
|
|
// WINDOWING
|
|
//------------------------------------------------------------
|
|
// EGL window
|
|
ofRectangle nonFullscreenWindowRect; // the rectangle describing the non-fullscreen window
|
|
ofRectangle currentWindowRect; // the rectangle describing the current device
|
|
|
|
bool createWindow(const ofRectangle& requestedWindowRect);
|
|
bool destroyWindow();
|
|
|
|
bool isUsingX11; ///< \brief Indicate the use of the X Window System.
|
|
|
|
bool isWindowInited; ///< \brief Indicate that the window is (properly) initialized.
|
|
bool isSurfaceInited; ///< \brief Indicate that the surface is (properly) initialized.
|
|
|
|
void initNative();
|
|
void exitNative();
|
|
|
|
EGLNativeWindowType getNativeWindow();
|
|
EGLNativeDisplayType getNativeDisplay();
|
|
|
|
#ifdef TARGET_RASPBERRY_PI
|
|
void initRPiNative();
|
|
void exitRPiNative();
|
|
|
|
EGL_DISPMANX_WINDOW_T dispman_native_window; // rpi
|
|
|
|
DISPMANX_UPDATE_HANDLE_T dispman_update;
|
|
DISPMANX_ELEMENT_HANDLE_T dispman_element;
|
|
DISPMANX_DISPLAY_HANDLE_T dispman_display;
|
|
|
|
DISPMANX_CLAMP_T dispman_clamp;
|
|
DISPMANX_TRANSFORM_T dispman_transform;
|
|
VC_DISPMANX_ALPHA_T dispman_alpha;
|
|
|
|
bool createRPiNativeWindow(const ofRectangle& requestedWindowRect);
|
|
|
|
#else
|
|
// if you are not raspberry pi, you will not be able to
|
|
// create a window without using x11.
|
|
#endif
|
|
|
|
Display* x11Display; ///< \brief Indicate which X11 display is in use (currently).
|
|
Screen* x11Screen; ///< \brief Indicate which X11 screen is in use (currently).
|
|
Window x11Window;
|
|
long x11ScreenNum; ///< \brief The number of the X11 screen is in use (currently).
|
|
bool createX11NativeWindow(const ofRectangle& requestedWindowRect);
|
|
|
|
//------------------------------------------------------------
|
|
// EVENTS
|
|
//------------------------------------------------------------
|
|
void setupNativeEvents();
|
|
void destroyNativeEvents();
|
|
|
|
void setupNativeUDev();
|
|
void destroyNativeUDev();
|
|
|
|
void setupNativeMouse();
|
|
void setupNativeKeyboard();
|
|
|
|
void destroyNativeMouse();
|
|
void destroyNativeKeyboard();
|
|
|
|
void readNativeMouseEvents();
|
|
void readNativeKeyboardEvents();
|
|
void readNativeUDevEvents();
|
|
|
|
static void handleX11Event(const XEvent& event);
|
|
|
|
private:
|
|
Settings settings;
|
|
int glesVersion; ///< \brief Indicate the version of OpenGL for Embedded Systems.
|
|
bool keyboardDetected;
|
|
bool mouseDetected;
|
|
long threadTimeout;
|
|
ofCoreEvents coreEvents;
|
|
std::shared_ptr<ofBaseRenderer> currentRenderer;
|
|
static ofAppEGLWindow * instance;
|
|
};
|
|
|