/*************************************************************************** * Copyright (C) 2004 by Raphael Langerhorst * * raphael-langerhorst@gmx.at * * * * Permission is hereby granted, free of charge, to any person obtaining * * a copy of this software and associated documentation files (the * * "Software"), to deal in the Software without restriction, including * * without limitation the rights to use, copy, modify, merge, publish, * * distribute, sublicense, and/or sell copies of the Software, and to * * permit persons to whom the Software is furnished to do so, subject to * * the following conditions: * * * * The above copyright notice and this permission notice shall be * * included in all copies or substantial portions of the Software. * * * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.* * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR * * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, * * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR * * OTHER DEALINGS IN THE SOFTWARE. * ***************************************************************************/ #ifndef OPENGLFRAMEH #define OPENGLFRAMEH //G includes #include #include #include #include #include //Qt includes #include #include #include #include #include //this belongs to the client engine namespace GCE { /** * \class CViewProperties GOpenGLFrame.h * \brief Holds information that is relevant for camera settings * @author Raphael Langerhorst * @todo Move this class into GGOpenGLFrame as it needs not really be independent. */ class CViewProperties { public: CViewProperties() : ViewPosition(0,0,-1), ViewTarget(0,0,0), ViewUp(0,1,0), fov(90), NearClippingPlane(0.01), FarClippingPlane(10), width(768), height(1024), CameraElement(0) { } GCS::GVector3 ViewPosition; GCS::GVector3 ViewTarget; GCS::GVector3 ViewUp; double fov; double NearClippingPlane; double FarClippingPlane; int width, height; /** * Holds the ID of the element for which the * view properties apply since this modifies * the view transformation. * @note If CameraElement.getID() returns 0 then * there is no parent transformation. */ GCS::GElementID CameraElement; void update() { glViewport(0,0,width,height); glMatrixMode(GL_PROJECTION); glLoadIdentity(); gluPerspective(fov,(double)width/(double)height,NearClippingPlane,FarClippingPlane); glMatrixMode(GL_MODELVIEW); glLoadIdentity(); } }; /** * \class GGOpenGLFrame GGOpenGLFrame.h * \brief A frame that can draw GOpenGLForm objects. * @author Raphael Langerhorst * * @todo The client interface could use MUCH improvement, its currently a very basic implementation. * This class represents the 3D interface. It allows for hierarchical rendering * of elements, specifically elements that use GOpenGLForm. */ class GOpenGLFrame : public QGLWidget, public QMutex { Q_OBJECT private: const GWE::GweController* Gwe; QValueList TopElements; /** * Used to know for which elements the respective server name should be shown. * It's determined at the beginning of each render cycle and stored here. */ GCS::GElementID CameraParent; /** * Stores the time for the last rendering periods. * This is used for frames per second calculations. * On each FPS update the list is cleared. */ QValueList RenderingPeriods; /** * The calculated fps value. */ double FramesPerSecond; /** * Time since last fps update. This is summed up in each * rendering cycle, if it reaches 1 second, the FPS value * is updated. The unit is milliseconds. */ double TimeSinceFpsUpdate; /** * Used to measure rendering periods. */ QTime FpsTimer; protected: void renderElement(const GCS::GElement* element); protected: /** * Transforms the matrix on the stack according to given form. * Position, rotation and scale (ellipsoid) are taken into account. */ void transform(const GCS::GForm* form) const; /** * Renders given form * @param RGBA an array with 4 float values, red, green, blue and alpha */ void render(const GCS::GForm* form, float* RGBA) const; /** * Started as singleshot timer after each redraw, * connected to update() */ QTimer RedrawTimer; bool StopRendering; /** * How many milliseconds to wait after finishing drawing * before redrawing. */ int RedrawSleepTime_ms; public: CViewProperties ViewProperties; GOpenGLFrame(const GWE::GweController* gwe, QWidget* parent = 0, const char* name = 0); ~GOpenGLFrame() {} public slots: /** * starts a thread that constantly sends paint events to this OpenGL frame * to ensure repainting; * a value of 20 means a framerate of 50 fps under optimum conditions; */ virtual void startRendering(int sleep_ms_between_updates_min = 20); virtual void stopRendering(); virtual void initializeGL(); virtual void resizeGL(int w, int h); virtual void paintGL(); virtual void addTopElement(const GCS::GElementID& element); virtual void removeTopElement(const GCS::GElementID& element); signals: /** * Emitted just before starting the rendering cycle, * no transformation,... done before emitting this signal. */ void beforeRendering(); /** * Emitted after rendering, all content is rendered. */ void afterRendering(); }; } #endif