Browse Source

Merge branch 'master' into compatibility

Vladimír Vondruš 14 years ago
parent
commit
cc6a4302a1
  1. 3
      modules/FindMagnum.cmake
  2. 1
      src/CMakeLists.txt
  3. 56
      src/Contexts/EglContext.cpp
  4. 87
      src/Contexts/EglContext.h
  5. 2
      src/Contexts/Sdl2Context.h
  6. 1
      src/Math/CMakeLists.txt
  7. 77
      src/Math/Swizzle.h
  8. 2
      src/Math/Test/CMakeLists.txt
  9. 62
      src/Math/Test/SwizzleTest.cpp
  10. 34
      src/Math/Test/SwizzleTest.h
  11. 4
      src/Math/Vector.h
  12. 2
      src/Math/Vector3.h
  13. 6
      src/Math/Vector4.h

3
modules/FindMagnum.cmake

@ -147,6 +147,9 @@ foreach(component ${Magnum_FIND_COMPONENTS})
find_path(_MAGNUM_${_COMPONENT}_INCLUDE_DIR
NAMES ${_MAGNUM_${_COMPONENT}_INCLUDE_PATH_NAMES}
PATHS ${MAGNUM_INCLUDE_DIR}/${_MAGNUM_${_COMPONENT}_INCLUDE_PATH_SUFFIX})
# Don't expose this variable to end users
mark_as_advanced(FORCE _MAGNUM_${_COMPONENT}_INCLUDE_DIR)
endif()
# Decide if the library was found

1
src/CMakeLists.txt

@ -67,7 +67,6 @@ set(Magnum_HEADERS
Query.h
Renderbuffer.h
Scene.h
Set.h
Shader.h
SizeTraits.h
Texture.h

56
src/Contexts/EglContext.cpp

@ -17,6 +17,9 @@
#define None 0L // redef Xlib nonsense
/* Mask for X events */
#define INPUT_MASK KeyPressMask|KeyReleaseMask|ButtonPressMask|ButtonReleaseMask|StructureNotifyMask
using namespace std;
namespace Magnum { namespace Contexts {
@ -73,13 +76,17 @@ EglContext::EglContext(int&, char**, const string& title, const Math::Vector2<GL
XSetWindowAttributes attr;
attr.background_pixel = 0;
attr.border_pixel = 0;
attr.colormap = XCreateColormap( xDisplay, root, visInfo->visual, AllocNone);
attr.event_mask = StructureNotifyMask|ExposureMask|KeyPressMask;
attr.colormap = XCreateColormap(xDisplay, root, visInfo->visual, AllocNone);
attr.event_mask = 0;
unsigned long mask = CWBackPixel|CWBorderPixel|CWColormap|CWEventMask;
xWindow = XCreateWindow(xDisplay, root, 20, 20, size.x(), size.y(), 0, visInfo->depth, InputOutput, visInfo->visual, mask, &attr);
XSetStandardProperties(xDisplay, xWindow, title.c_str(), 0, None, 0, 0, 0);
XFree(visInfo);
/* Be notified about closing the window */
deleteWindow = XInternAtom(xDisplay, "WM_DELETE_WINDOW", True);
XSetWMProtocols(xDisplay, xWindow, &deleteWindow, 1);
/* Create context and window surface */
static const EGLint contextAttributes[] = {
#ifdef MAGNUM_TARGET_GLES
@ -98,8 +105,10 @@ EglContext::EglContext(int&, char**, const string& title, const Math::Vector2<GL
exit(1);
}
/* Show window and set OpenGL context as current */
XMapWindow(xDisplay, xWindow);
/* Capture exposure, keyboard and mouse button events */
XSelectInput(xDisplay, xWindow, INPUT_MASK);
/* Set OpenGL context as current */
eglMakeCurrent(display, surface, surface, context);
/** @bug Fixme: GLEW initialization fails (thinks that the context is not created) */
@ -125,12 +134,49 @@ EglContext::~EglContext() {
}
int EglContext::exec() {
/* Show window */
XMapWindow(xDisplay, xWindow);
/* Call viewportEvent for the first time */
viewportEvent(viewportSize);
while(true) {
XEvent event;
/* Closed window */
if(XCheckTypedWindowEvent(xDisplay, xWindow, ClientMessage, &event) &&
Atom(event.xclient.data.l[0]) == deleteWindow) {
return 0;
}
while(XCheckWindowEvent(xDisplay, xWindow, INPUT_MASK, &event)) {
switch(event.type) {
/* Window resizing */
case ConfigureNotify: {
Math::Vector2<int> size(event.xconfigure.width, event.xconfigure.height);
if(size != viewportSize) {
viewportSize = size;
viewportEvent(size);
}
} break;
/* Key/mouse events */
case KeyPress:
keyPressEvent(static_cast<Key>(XLookupKeysym(&event.xkey, 0)), {event.xkey.x, event.xkey.y});
break;
case KeyRelease:
keyReleaseEvent(static_cast<Key>(XLookupKeysym(&event.xkey, 0)), {event.xkey.x, event.xkey.y});
break;
case ButtonPress:
mousePressEvent(static_cast<MouseButton>(event.xbutton.button), {event.xbutton.x, event.xbutton.y});
break;
case ButtonRelease:
mouseReleaseEvent(static_cast<MouseButton>(event.xbutton.button), {event.xbutton.x, event.xbutton.y});
break;
}
}
/** @todo Handle at least window closing and resizing */
eglMakeCurrent(display, surface, surface, context);
drawEvent();
}

87
src/Contexts/EglContext.h

@ -62,6 +62,8 @@ class EglContext: public AbstractContext {
int exec();
/** @{ @name Drawing functions */
protected:
/** @copydoc GlutContext::viewportEvent() */
virtual void viewportEvent(const Math::Vector2<GLsizei>& size) = 0;
@ -72,9 +74,88 @@ class EglContext: public AbstractContext {
/** @copydoc GlutContext::swapBuffers() */
inline void swapBuffers() { eglSwapBuffers(display, surface); }
/*@}*/
/** @{ @name Keyboard handling */
public:
/** @brief Key */
enum class Key: KeySym {
Up = XK_Up, /**< Up arrow */
Down = XK_Down, /**< Down arrow */
Left = XK_Left, /**< Left arrow */
Right = XK_Right, /**< Right arrow */
F1 = XK_F1, /**< F1 */
F2 = XK_F2, /**< F2 */
F3 = XK_F3, /**< F3 */
F4 = XK_F4, /**< F4 */
F5 = XK_F5, /**< F5 */
F6 = XK_F6, /**< F6 */
F7 = XK_F7, /**< F7 */
F8 = XK_F8, /**< F8 */
F9 = XK_F9, /**< F9 */
F10 = XK_F10, /**< F10 */
F11 = XK_F11, /**< F11 */
F12 = XK_F12, /**< F12 */
Home = XK_Home, /**< Home */
End = XK_End, /**< End */
PageUp = XK_Page_Up, /**< Page up */
PageDown = XK_Page_Down /**< Page down */
};
protected:
/**
* @brief Key press event
* @param key Key pressed
* @param position Cursor position
*
* Called when an key is pressed. Default implementation does nothing.
*/
virtual void keyPressEvent(Key key, const Math::Vector2<int>& position) = 0;
/**
* @brief Key press event
* @param key Key released
* @param position Cursor position
*
* Called when an key is released. Default implementation does nothing.
*/
virtual void keyReleaseEvent(Key key, const Math::Vector2<int>& position) = 0;
/*@}*/
/** @{ @name Mouse handling */
public:
/** @brief Mouse button */
enum class MouseButton: unsigned int {
Left = Button1, /**< Left button */
Middle = Button2, /**< Middle button */
Right = Button3, /**< Right button */
WheelUp = Button4, /**< Wheel up */
WheelDown = Button5 /**< Wheel down */
};
protected:
/**
* @brief Mouse press event
*
* Called when mouse button is pressed. Default implementation does
* nothing.
*/
virtual void mousePressEvent(MouseButton button, const Math::Vector2<int>& position);
/**
* @brief Mouse release event
*
* Called when mouse button is released. Default implementation does
* nothing.
*/
virtual void mouseReleaseEvent(MouseButton button, const Math::Vector2<int>& position);
private:
Display* xDisplay;
Window xWindow;
Atom deleteWindow;
EGLDisplay display;
EGLSurface surface;
@ -84,6 +165,12 @@ class EglContext: public AbstractContext {
Math::Vector2<GLsizei> viewportSize;
};
inline void EglContext::keyPressEvent(EglContext::Key, const Math::Vector2<int>&) {}
inline void EglContext::keyReleaseEvent(EglContext::Key, const Math::Vector2<int>&) {}
inline void EglContext::mousePressEvent(EglContext::MouseButton, const Math::Vector2<int>&) {}
inline void EglContext::mouseReleaseEvent(EglContext::MouseButton, const Math::Vector2<int>&) {}
}}
#endif

2
src/Contexts/Sdl2Context.h

@ -100,7 +100,7 @@ class Sdl2Context: public AbstractContext {
/**
* @brief Key release event
* @param key Key release
* @param key Key released
*/
virtual void keyReleaseEvent(Key key);

1
src/Math/CMakeLists.txt

@ -6,6 +6,7 @@ set(MagnumMath_HEADERS
Matrix.h
Matrix3.h
Matrix4.h
Swizzle.h
Vector.h
Vector2.h
Vector3.h

77
src/Math/Swizzle.h

@ -0,0 +1,77 @@
#ifndef Magnum_Math_Swizzle_h
#define Magnum_Math_Swizzle_h
/*
Copyright © 2010, 2011, 2012 Vladimír Vondruš <mosra@centrum.cz>
This file is part of Magnum.
Magnum is free software: you can redistribute it and/or modify
it under the terms of the GNU Lesser General Public License version 3
only, as published by the Free Software Foundation.
Magnum 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 Lesser General Public License version 3 for more details.
*/
/** @file
* @brief Function Magnum::Math::swizzle()
*/
#include "Vector4.h"
namespace Magnum { namespace Math {
#ifndef DOXYGEN_GENERATING_OUTPUT
namespace Implementation {
template<size_t size, size_t position> struct GetPosition {
static_assert(size > position, "Swizzle parameter out of range of base vector");
inline constexpr static size_t value() { return position; }
};
template<size_t size, char component> struct GetComponent {};
template<size_t size> struct GetComponent<size, 'x'>: public GetPosition<size, 0> {};
template<size_t size> struct GetComponent<size, 'y'>: public GetPosition<size, 1> {};
template<size_t size> struct GetComponent<size, 'z'>: public GetPosition<size, 2> {};
template<size_t size> struct GetComponent<size, 'w'>: public GetPosition<size, 3> {};
template<size_t size> struct GetComponent<size, 'r'>: public GetPosition<size, 0> {};
template<size_t size> struct GetComponent<size, 'g'>: public GetPosition<size, 1> {};
template<size_t size> struct GetComponent<size, 'b'>: public GetPosition<size, 2> {};
template<size_t size> struct GetComponent<size, 'a'>: public GetPosition<size, 3> {};
template<size_t size, class T> struct TypeForSize {
typedef Vector<size, T> Type;
};
template<class T> struct TypeForSize<2, T> { typedef Vector2<T> Type; };
template<class T> struct TypeForSize<3, T> { typedef Vector3<T> Type; };
template<class T> struct TypeForSize<4, T> { typedef Vector4<T> Type; };
}
#endif
/**
@brief Swizzle Vector components
Creates new vector from given components. Example:
@code
Vector4<int> original(1, 2, 3, 4);
auto vec = swizzle<'a', 'b', 'b', 'g', 'r', 'r'>(original);
// vec == { 4, 3, 3, 2, 1, 1 }
@endcode
You can use letters `x`, `y`, `z`, `w` and `r`, `g`, `b`, `a`. Count of
elements is unlimited, but must be at least one. If the resulting vector is
two, three or four-component, corresponding Vector2, Vector3 or Vector4
specialization is returned.
@see Vector4::xyz(), Vector4::rgb(), Vector4::xy(), Vector3::xy()
*/
template<char ...components, size_t size, class T> inline constexpr typename Implementation::TypeForSize<sizeof...(components), T>::Type swizzle(const Vector<size, T>& vector) {
return {vector[Implementation::GetComponent<size, components>::value()]...};
}
}}
#endif

2
src/Math/Test/CMakeLists.txt

@ -5,6 +5,8 @@ corrade_add_test2(MathVector2Test Vector2Test.cpp)
corrade_add_test2(MathVector3Test Vector3Test.cpp)
corrade_add_test2(MathVector4Test Vector4Test.cpp)
corrade_add_test2(MathSwizzleTest SwizzleTest.cpp)
corrade_add_test2(MathMatrixTest MatrixTest.cpp)
corrade_add_test2(MathMatrix3Test Matrix3Test.cpp)
corrade_add_test2(MathMatrix4Test Matrix4Test.cpp)

62
src/Math/Test/SwizzleTest.cpp

@ -0,0 +1,62 @@
/*
Copyright © 2010, 2011, 2012 Vladimír Vondruš <mosra@centrum.cz>
This file is part of Magnum.
Magnum is free software: you can redistribute it and/or modify
it under the terms of the GNU Lesser General Public License version 3
only, as published by the Free Software Foundation.
Magnum 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 Lesser General Public License version 3 for more details.
*/
#include "SwizzleTest.h"
#include "Swizzle.h"
using namespace std;
CORRADE_TEST_MAIN(Magnum::Math::Test::SwizzleTest)
namespace Magnum { namespace Math { namespace Test {
typedef Math::Vector2<int> Vector2;
typedef Math::Vector3<int> Vector3;
typedef Math::Vector4<int> Vector4;
template<size_t size> using Vector = Math::Vector<size, int>;
SwizzleTest::SwizzleTest() {
addTests(&SwizzleTest::xyzw,
&SwizzleTest::rgba,
&SwizzleTest::type,
&SwizzleTest::defaultType);
}
void SwizzleTest::xyzw() {
Vector4 orig(2, 4, 5, 7);
CORRADE_COMPARE((swizzle<'z', 'x', 'w', 'y'>(orig)), Vector4(5, 2, 7, 4));
}
void SwizzleTest::rgba() {
Vector4 orig(2, 4, 5, 7);
CORRADE_COMPARE((swizzle<'b', 'r', 'a', 'g'>(orig)), Vector4(5, 2, 7, 4));
}
void SwizzleTest::type() {
Vector4 orig;
CORRADE_VERIFY((is_same<decltype(swizzle<'y', 'a'>(orig)), Vector2>::value));
CORRADE_VERIFY((is_same<decltype(swizzle<'y', 'z', 'a'>(orig)), Vector3>::value));
CORRADE_VERIFY((is_same<decltype(swizzle<'y', 'a', 'y', 'x'>(orig)), Vector4>::value));
}
void SwizzleTest::defaultType() {
Vector4 orig(1, 2, 3, 4);
CORRADE_COMPARE(swizzle<'b'>(orig), Vector<1>(3));
CORRADE_COMPARE((swizzle<'b', 'r', 'a', 'g', 'z', 'y', 'x'>(orig)), Vector<7>(3, 1, 4, 2, 3, 2, 1));
}
}}}

34
src/Math/Test/SwizzleTest.h

@ -0,0 +1,34 @@
#ifndef Magnum_Math_Test_SwizzleTest_h
#define Magnum_Math_Test_SwizzleTest_h
/*
Copyright © 2010, 2011, 2012 Vladimír Vondruš <mosra@centrum.cz>
This file is part of Magnum.
Magnum is free software: you can redistribute it and/or modify
it under the terms of the GNU Lesser General Public License version 3
only, as published by the Free Software Foundation.
Magnum 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 Lesser General Public License version 3 for more details.
*/
#include <TestSuite/Tester.h>
namespace Magnum { namespace Math { namespace Test {
class SwizzleTest: public Corrade::TestSuite::Tester<SwizzleTest> {
public:
SwizzleTest();
void xyzw();
void rgba();
void type();
void defaultType();
};
}}}
#endif

4
src/Math/Vector.h

@ -103,7 +103,11 @@ template<size_t size, class T> class Vector {
* @brief Constructor
* @param value Value for all fields
*/
#ifndef DOXYGEN_GENERATING_OUTPUT
template<class U> inline explicit Vector(typename std::enable_if<std::is_same<T, U>::value && size != 1, U>::type value) {
#else
inline explicit Vector(T value) {
#endif
for(size_t i = 0; i != size; ++i)
_data[i] = value;
}

2
src/Math/Vector3.h

@ -81,6 +81,8 @@ template<class T> class Vector3: public Vector<3, T> {
/**
* @brief XY part of the vector
* @return First two components of the vector
*
* @see swizzle()
*/
inline constexpr Vector2<T> xy() const { return Vector2<T>::from(Vector<3, T>::data()); }

6
src/Math/Vector4.h

@ -70,12 +70,16 @@ template<class T> class Vector4: public Vector<4, T> {
/**
* @brief XYZ part of the vector
* @return First three components of the vector
*
* @see swizzle()
*/
inline constexpr Vector3<T> xyz() const { return Vector3<T>::from(Vector<4, T>::data()); }
/**
* @brief XY part of the vector
* @return First two components of the vector
*
* @see swizzle()
*/
inline constexpr Vector2<T> xy() const { return Vector2<T>::from(Vector<4, T>::data()); }
@ -92,6 +96,8 @@ template<class T> class Vector4: public Vector<4, T> {
/**
* @brief RGB part of the vector
* @return First three components of the vector
*
* @see swizzle()
*/
inline constexpr Vector3<T> rgb() const { return xyz(); }

Loading…
Cancel
Save