core: add interface wrappers and display refactor
authorU. Artie Eoff <ullysses.a.eoff@intel.com>
Fri, 25 Jan 2013 00:23:50 +0000 (16:23 -0800)
committerU. Artie Eoff <ullysses.a.eoff@intel.com>
Fri, 25 Jan 2013 00:23:50 +0000 (16:23 -0800)
Signed-off-by: U. Artie Eoff <ullysses.a.eoff@intel.com>
18 files changed:
src/core/Makefile.am
src/core/compositor.cpp [new file with mode: 0644]
src/core/compositor.h [new file with mode: 0644]
src/core/display.cpp [new file with mode: 0644]
src/core/display.h
src/core/harness.cpp
src/core/harness.h
src/core/pointer.cpp [new file with mode: 0644]
src/core/pointer.h [new file with mode: 0644]
src/core/seat.cpp [new file with mode: 0644]
src/core/seat.h [new file with mode: 0644]
src/core/shell.cpp [new file with mode: 0644]
src/core/shell.h [new file with mode: 0644]
src/core/surface.cpp [new file with mode: 0644]
src/core/surface.h [new file with mode: 0644]
src/core/test_bind_interface.cpp
src/core/test_cursor.cpp
src/core/test_data.cpp

index 70fb260..bfbd162 100644 (file)
@@ -2,10 +2,16 @@ INCLUDES = -I$(top_srcdir)/src
 
 lib_LTLIBRARIES = libwfits-core.la
 
-libwfits_core_la_SOURCES = \
-       harness.cpp \
-       test_bind_interface.cpp \
-       test_cursor.cpp \
+libwfits_core_la_SOURCES =                                             \
+       display.cpp                                                     \
+       compositor.cpp                                                  \
+       shell.cpp                                                       \
+       seat.cpp                                                        \
+       pointer.cpp                                                     \
+       surface.cpp                                                     \
+       harness.cpp                                                     \
+       test_bind_interface.cpp                                         \
+       test_cursor.cpp                                                 \
        test_data.cpp
 
 libwfits_core_la_LIBADD = \
diff --git a/src/core/compositor.cpp b/src/core/compositor.cpp
new file mode 100644 (file)
index 0000000..93f5c6c
--- /dev/null
@@ -0,0 +1,17 @@
+#include "compositor.h"
+
+Compositor::Compositor(const Display& display)
+       : display_(display)
+       , wl_compositor_(
+               display.bind<wl_compositor>(
+                       "wl_compositor", &wl_compositor_interface))
+{
+       ASSERT(wl_compositor_ != NULL);
+
+       wl_compositor_set_user_data(*this, this);
+}
+
+/*virtual*/ Compositor::~Compositor()
+{
+       wl_compositor_destroy(*this);
+}
diff --git a/src/core/compositor.h b/src/core/compositor.h
new file mode 100644 (file)
index 0000000..3d14c2e
--- /dev/null
@@ -0,0 +1,21 @@
+#ifndef __WFITS_CORE_COMPOSITOR_H__
+#define __WFITS_CORE_COMPOSITOR_H__
+
+#include "display.h"
+
+class Compositor
+{
+public:
+       Compositor(const Display&);
+
+       virtual ~Compositor();
+
+       operator wl_compositor*() const { return wl_compositor_; }
+       const Display& display() const { return display_; }
+
+private:
+       const Display&  display_;
+       wl_compositor   *wl_compositor_;
+};
+
+#endif
diff --git a/src/core/display.cpp b/src/core/display.cpp
new file mode 100644 (file)
index 0000000..629f91e
--- /dev/null
@@ -0,0 +1,48 @@
+#include "display.h"
+
+Display::Display()
+       : wl_display_(wl_display_connect(0))
+       , wl_registry_(NULL)
+       , globals_()
+{
+       ASSERT(wl_display_ != NULL);
+
+       wl_registry_ = wl_display_get_registry(*this);
+
+       wl_display_set_user_data(*this, this);
+       
+       ASSERT(wl_registry_ != NULL);
+
+       static const struct wl_registry_listener listener = {global};
+
+       wl_registry_add_listener(wl_registry_, &listener, this);
+
+       dispatch();
+}
+
+/*virtual*/ Display::~Display()
+{
+       wl_registry_destroy(wl_registry_);
+       wl_display_disconnect(*this);
+}
+
+void Display::roundtrip() const
+{
+       ASSERT(wl_display_roundtrip(*this) >= 0);
+}
+
+void Display::dispatch() const
+{
+       ASSERT(wl_display_dispatch(*this) >= 0);
+}
+
+/*static*/ void Display::global(
+       void *data, struct wl_registry *wl_registry, uint32_t id,
+       const char* interface, uint32_t version)
+{
+       Display* display = static_cast<Display*>(data);
+
+       ASSERT(display->wl_registry_ == wl_registry);
+
+       display->globals_[std::string(interface)] = GlobalInfo(id, version);
+}
index 682527c..21e1396 100644 (file)
@@ -1,27 +1,46 @@
 #ifndef __WFITS_CORE_DISPLAY_H__
 #define __WFITS_CORE_DISPLAY_H__
 
+#include <map>
 #include <wayland-client.h>
 #include "common/test.h"
 
 class Display
 {
+       typedef std::pair<uint32_t, uint32_t> GlobalInfo;
+       typedef std::map<std::string, GlobalInfo> Globals;
 public:
-       Display()
-               : display_(wl_display_connect(0))
-       {
-               FAIL_IF(display_ == NULL);
-       }
+       Display();
 
-       virtual ~Display()
+       virtual ~Display();
+
+       template <typename T>
+       T* bind(
+               const std::string& interface,
+               const struct wl_interface *wl_interface) const
        {
-               wl_display_disconnect(*this);
+               const Globals::const_iterator match(globals_.find(interface));
+
+               ASSERT(match != globals_.end());
+
+               return static_cast<T*>(
+                       wl_registry_bind(
+                               wl_registry_, match->second.first, wl_interface,
+                               match->second.second));
        }
 
-       operator wl_display*() { return display_; }
+       void roundtrip() const;
+       void dispatch() const;
+
+       operator wl_display*() const { return wl_display_; }
 
 private:
-       wl_display* display_;
+       static void global(
+               void*, struct wl_registry*, uint32_t, const char*, uint32_t);
+
+       wl_display      *wl_display_;
+       wl_registry     *wl_registry_;
+       Globals         globals_;
 };
 
 #endif
index 1e76727..c0e5451 100644 (file)
@@ -2,22 +2,15 @@
 #include "harness.h"
 
 CoreTestHarness::CoreTestHarness()
-       : Display::Display()
-       , registry_(0)
+       : display_()
+       , tests_()
 {
-       registry_ = wl_display_get_registry(*this);
-
-       static const struct wl_registry_listener listener = {
-               &CoreTestHarness::globalListener
-       };
-
-       wl_registry_add_listener(registry_, &listener, this);
-       FAIL_IF_EQUAL(registry_, NULL);
+       return;
 }
 
 CoreTestHarness::~CoreTestHarness()
 {
-       wl_registry_destroy(*this);
+       return;
 }
 
 void CoreTestHarness::queueTest(Test test)
@@ -27,29 +20,18 @@ void CoreTestHarness::queueTest(Test test)
 
 void CoreTestHarness::run()
 {
-       // trigger client global announcements
-       wl_display_dispatch(*this);
-
        setup();
 
        while (not tests_.empty())
        {
                tests_.front()(); // call test
                tests_.pop_front(); // remove test
+               display().roundtrip();
        }
 
        teardown();
 }
 
-/*static*/
-void CoreTestHarness::globalListener(
-       void *data, struct wl_registry *registry, uint32_t id, const char* iface, uint32_t version)
-{
-       CoreTestHarness* harness = static_cast<CoreTestHarness*>(data);
-       FAIL_UNLESS_EQUAL(registry, *harness);
-       harness->handleGlobal(id, std::string(iface), version);
-}
-
 class SimpleTest : public CoreTestHarness
 {
 public:
@@ -60,16 +42,11 @@ public:
                return;
        }
 
-       void handleGlobal(uint32_t, const std::string&, uint32_t)
-       {
-               return;
-       }
-       
        void setup()
        {
                queueTest(boost::bind(&SimpleTest::test, boost::ref(*this)));
        }
-       
+
        void test()
        {
                if (++tested < 10)
@@ -77,12 +54,12 @@ public:
                        queueTest(boost::bind(&SimpleTest::test, boost::ref(*this)));
                }
        }
-       
+
        void teardown()
        {
                FAIL_UNLESS_EQUAL(tested, 10);
        }
-       
+
        unsigned tested;
 };
 
index 12adad7..216b362 100644 (file)
@@ -5,9 +5,10 @@
 #include <boost/bind.hpp>
 #include <deque>
 #include <string>
+
 #include "display.h"
 
-class CoreTestHarness : public Display
+class CoreTestHarness
 {
 public:
        typedef boost::function<void()> Test;
@@ -22,12 +23,6 @@ public:
 
        /**
         * Optionally override this to do any special
-        * interface binding and/or setup.
-        **/
-       virtual void handleGlobal(uint32_t, const std::string&, uint32_t) { };
-       
-       /**
-        * Optionally override this to do any special
         * setup before processing Tests.
         * i.e. you can queue all your tests from here.
         **/
@@ -39,13 +34,11 @@ public:
         **/
        virtual void teardown() { };
 
-       operator wl_registry*() { return registry_; }
+       const Display& display() const { return display_; }
 
 private:
-       static void globalListener(void*, struct wl_registry*, uint32_t, const char*, uint32_t);
-
-       wl_registry*    registry_;
-       Tests           tests_;
+       Display display_;
+       Tests   tests_;
 };
 
 #define WFITS_CORE_HARNESS_TEST_CASE(HarnessClass, suite) \
diff --git a/src/core/pointer.cpp b/src/core/pointer.cpp
new file mode 100644 (file)
index 0000000..70a076d
--- /dev/null
@@ -0,0 +1,103 @@
+#include "surface.h"
+#include "pointer.h"
+
+Pointer::Pointer(const Seat& seat)
+       : seat_(seat)
+       , focus_(NULL)
+       , x_(-1)
+       , y_(-1)
+       , button_(0)
+       , buttonState_(0)
+       , axis_(0)
+       , axisValue_(0.f)
+       , wl_pointer_(NULL)
+{
+       ASSERT(seat.capabilities() & WL_SEAT_CAPABILITY_POINTER);
+
+       wl_pointer_ = wl_seat_get_pointer(seat);
+
+       ASSERT(wl_pointer_ != NULL);
+
+       wl_pointer_set_user_data(*this, this);
+
+       static const wl_pointer_listener listener = {
+               enter, leave, motion, button, axis};
+
+       wl_pointer_add_listener(*this, &listener, this);
+}
+
+/*virtual*/ Pointer::~Pointer()
+{
+       wl_pointer_destroy(*this);
+}
+
+bool Pointer::hasFocus(const Surface* surface)
+{
+       return focus_ == surface;
+}
+
+/*static*/ void Pointer::enter(
+       void *data, wl_pointer *wl_pointer, uint32_t serial,
+       wl_surface *wl_surface, wl_fixed_t x, wl_fixed_t y)
+{
+       Pointer* pointer = static_cast<Pointer*>(data);
+       ASSERT(wl_pointer == *pointer);
+
+       std::cout << "Pointer::enter(): " << wl_fixed_to_int(x) << " "
+               << wl_fixed_to_int(y) << std::endl;
+       
+       pointer->focus_ = static_cast<Surface*>(
+               wl_surface_get_user_data(wl_surface));
+       pointer->x_ = wl_fixed_to_int(x);
+       pointer->y_ = wl_fixed_to_int(y);
+}
+
+/*static*/ void Pointer::leave(
+       void *data, wl_pointer *wl_pointer, uint32_t serial,
+       wl_surface *wl_surface)
+{
+       Pointer* pointer = static_cast<Pointer*>(data);
+       ASSERT(wl_pointer == *pointer);
+
+       std::cout << "Pointer::leave(): " << std::endl;
+       
+       pointer->focus_ = NULL;
+       pointer->x_ = -1;
+       pointer->y_ = -1;
+}
+
+/*static*/ void Pointer::motion(
+       void *data, wl_pointer *wl_pointer, uint32_t time,
+       wl_fixed_t x, wl_fixed_t y)
+{
+       Pointer* pointer = static_cast<Pointer*>(data);
+       ASSERT(wl_pointer == *pointer);
+
+       std::cout << "Pointer::motion(): " << wl_fixed_to_int(x) << " "
+               << wl_fixed_to_int(y) << std::endl;
+
+       pointer->x_ = wl_fixed_to_int(x);
+       pointer->y_ = wl_fixed_to_int(y);
+}
+
+/*static*/ void Pointer::button(
+       void *data, wl_pointer *wl_pointer, uint32_t serial,
+       uint32_t time, uint32_t button, uint32_t state)
+{
+       Pointer* pointer = static_cast<Pointer*>(data);
+       ASSERT(wl_pointer == *pointer);
+
+       pointer->button_ = button;
+       pointer->buttonState_ = state;
+}
+
+/*static*/ void Pointer::axis(
+       void *data, wl_pointer *wl_pointer, uint32_t time,
+       uint32_t axis, wl_fixed_t value)
+{
+       Pointer* pointer = static_cast<Pointer*>(data);
+       ASSERT(wl_pointer == *pointer);
+
+       pointer->axis_ = axis;
+       pointer->axisValue_ = wl_fixed_to_double(value);
+}
diff --git a/src/core/pointer.h b/src/core/pointer.h
new file mode 100644 (file)
index 0000000..f6d707f
--- /dev/null
@@ -0,0 +1,43 @@
+#ifndef __WFITS_CORE_POINTER_H__
+#define __WFITS_CORE_POINTER_H__
+
+#include "seat.h"
+
+class Surface;
+
+class Pointer
+{
+public:
+       Pointer(const Seat&);
+
+       virtual ~Pointer();
+
+       operator wl_pointer*() const { return wl_pointer_; }
+       const Seat& seat() const { return seat_; }
+
+       bool hasFocus(const Surface*);
+
+private:
+       static void enter(
+               void*, wl_pointer*, uint32_t, wl_surface*, wl_fixed_t, wl_fixed_t);
+       static void leave(
+               void*, wl_pointer*, uint32_t, wl_surface*);
+       static void motion(
+               void*, wl_pointer*, uint32_t, wl_fixed_t, wl_fixed_t);
+       static void button(
+               void*, wl_pointer*, uint32_t, uint32_t, uint32_t, uint32_t);
+       static void axis(
+               void*, wl_pointer*, uint32_t, uint32_t, wl_fixed_t);
+
+       const Seat&     seat_;
+       Surface*        focus_;
+       int32_t         x_;
+       int32_t         y_;
+       uint32_t        button_;
+       uint32_t        buttonState_;
+       uint32_t        axis_;
+       uint32_t        axisValue_;
+       wl_pointer*     wl_pointer_;
+};
+
+#endif
diff --git a/src/core/seat.cpp b/src/core/seat.cpp
new file mode 100644 (file)
index 0000000..e55167d
--- /dev/null
@@ -0,0 +1,30 @@
+#include "seat.h"
+
+Seat::Seat(const Display& display)
+       : display_(display)
+       , wl_seat_(display.bind<wl_seat>("wl_seat", &wl_seat_interface))
+       , capabilities_(0)
+{
+       ASSERT(wl_seat_ != NULL);
+
+       wl_seat_set_user_data(*this, this);
+
+       static const wl_seat_listener listener = {capabilities};
+       wl_seat_add_listener(*this, &listener, this);
+
+       display.roundtrip();
+}
+
+/*virtual*/ Seat::~Seat()
+{
+       wl_seat_destroy(*this);
+}
+
+/*static*/ void Seat::capabilities(void *data, wl_seat *wl_seat, uint32_t caps)
+{
+       Seat* seat = static_cast<Seat*>(data);
+
+       ASSERT(wl_seat == *seat);
+
+       seat->capabilities_ = caps;
+}
diff --git a/src/core/seat.h b/src/core/seat.h
new file mode 100644 (file)
index 0000000..817b7fc
--- /dev/null
@@ -0,0 +1,25 @@
+#ifndef __WFITS_CORE_SEAT_H__
+#define __WFITS_CORE_SEAT_H__
+
+#include "display.h"
+
+class Seat
+{
+public:
+       Seat(const Display&);
+
+       virtual ~Seat();
+
+       operator wl_seat*() const { return wl_seat_; }
+       const Display& display() const { return display_; }
+       uint32_t capabilities() const { return capabilities_; }
+
+private:
+       static void capabilities(void*, wl_seat*, uint32_t);
+       
+       const Display&          display_;
+       wl_seat*                wl_seat_;
+       uint32_t                capabilities_;
+};
+
+#endif
diff --git a/src/core/shell.cpp b/src/core/shell.cpp
new file mode 100644 (file)
index 0000000..a25496d
--- /dev/null
@@ -0,0 +1,19 @@
+#include "shell.h"
+
+Shell::Shell(const Display& display)
+       : display_(display)
+       , wl_shell_(
+               display.bind<wl_shell>(
+                       "wl_shell", &wl_shell_interface))
+{
+       ASSERT(wl_shell_ != NULL);
+
+       wl_shell_set_user_data(*this, this);
+
+       ASSERT(wl_shell_get_user_data(*this) == this);
+}
+
+/*virtual*/ Shell::~Shell()
+{
+       wl_shell_destroy(*this);
+}
diff --git a/src/core/shell.h b/src/core/shell.h
new file mode 100644 (file)
index 0000000..c73bfed
--- /dev/null
@@ -0,0 +1,21 @@
+#ifndef __WFITS_CORE_SHELL_H__
+#define __WFITS_CORE_SHELL_H__
+
+#include "display.h"
+
+class Shell
+{
+public:
+       Shell(const Display&);
+
+       virtual ~Shell();
+
+       operator wl_shell*() const { return wl_shell_; }
+       const Display& display() const { return display_; }
+
+private:
+       const Display&  display_;
+       wl_shell        *wl_shell_;
+};
+
+#endif
diff --git a/src/core/surface.cpp b/src/core/surface.cpp
new file mode 100644 (file)
index 0000000..8af69d1
--- /dev/null
@@ -0,0 +1,58 @@
+#include "surface.h"
+
+Surface::Surface(const Compositor& compositor)
+       : compositor_(compositor)
+       , wl_surface_(
+               wl_compositor_create_surface(compositor))
+{
+       ASSERT(wl_surface_ != NULL);
+
+       wl_surface_set_user_data(*this, this);
+
+       static const wl_surface_listener listener = {enter, leave};
+
+       wl_surface_add_listener(*this, &listener, this);
+
+       compositor.display().roundtrip();
+}
+
+/*virtual*/ Surface::~Surface()
+{
+       wl_surface_destroy(*this);
+}
+
+static void handleDone(void *data, wl_callback *callback, uint32_t time)
+{
+       bool *done = static_cast<bool*>(data);
+       *done = true;
+       wl_callback_destroy(callback);
+}
+
+static const struct wl_callback_listener doneListener = {handleDone};
+
+void Surface::commit() const
+{
+       bool            done(false);
+       wl_callback*    callback(wl_surface_frame(*this));
+
+       wl_callback_add_listener(callback, &doneListener, &done);
+       wl_surface_commit(*this);
+
+       while (not done) {
+               compositor().display().dispatch();
+       }
+}
+
+/*static*/ void Surface::enter(
+       void *data, wl_surface *wl_surface, wl_output *wl_output)
+{
+       Surface* surface = static_cast<Surface*>(data);
+       ASSERT(wl_surface == *surface);
+}
+
+/*static*/ void Surface::leave(
+       void *data, wl_surface *wl_surface, wl_output *wl_output)
+{
+       Surface* surface = static_cast<Surface*>(data);
+       ASSERT(wl_surface == *surface);
+}
diff --git a/src/core/surface.h b/src/core/surface.h
new file mode 100644 (file)
index 0000000..234796f
--- /dev/null
@@ -0,0 +1,26 @@
+#ifndef __WFITS_CORE_SURFACE_H__
+#define __WFITS_CORE_SURFACE_H__
+
+#include "compositor.h"
+
+class Surface
+{
+public:
+       Surface(const Compositor&);
+
+       virtual ~Surface();
+
+       operator wl_surface*() const { return wl_surface_; }
+       const Compositor& compositor() const { return compositor_; }
+
+       void commit() const;
+
+private:
+       static void enter(void*, wl_surface*, wl_output*);
+       static void leave(void*, wl_surface*, wl_output*);
+
+       const Compositor&       compositor_;
+       wl_surface              *wl_surface_;
+};
+
+#endif
index b127f45..59745f5 100644 (file)
@@ -1,4 +1,3 @@
-
 #include "harness.h"
 
 template <typename O, const wl_interface& interface, const std::string& str_interface>
@@ -12,16 +11,9 @@ public:
                return;
        }
 
-       void handleGlobal(uint32_t id, const std::string& iface, uint32_t)
+       void setup()
        {
-               if (iface == str_interface)
-               {
-                       object_ = static_cast<O*>(
-                               wl_registry_bind(
-                                       *this, id, &interface, 1
-                               )
-                       );
-               }
+               object_ = display().template bind<O>(str_interface, &interface);
        }
        
        void teardown()
@@ -44,3 +36,6 @@ BIND_TEST(wl_output)
 BIND_TEST(wl_seat)
 BIND_TEST(wl_shell)
 BIND_TEST(wl_data_device_manager)
+// BIND_TEST(wfits_input)
+// BIND_TEST(wfits_query)
+
index 0122eb4..7e7ec29 100644 (file)
@@ -17,18 +17,9 @@ class ThemeLoadTest : public CoreTestHarness
 public:
        ThemeLoadTest()
                : CoreTestHarness::CoreTestHarness()
-               , shm_(0)
+               , shm_(display().bind<wl_shm>("wl_shm", &wl_shm_interface))
        {
-               return;
-       }
-
-       void handleGlobal(uint32_t id, const std::string& iface, uint32_t version)
-       {
-               if (iface == "wl_shm")
-               {
-                       shm_ = static_cast<wl_shm*>(wl_registry_bind(*this, id, &wl_shm_interface, 1));
-                       FAIL_IF_EQUAL(shm_, NULL);
-               }
+               ASSERT(shm_ != NULL);
        }
 
        void setup()
index fe20786..ef94575 100644 (file)
@@ -49,14 +49,12 @@ protected:
        class data_ ## name : public DataTest<name> \
        { \
        public: \
-               DATA_SETTER_GETTER(name) \
-               void handleGlobal(uint32_t id, const std::string& iface, uint32_t version) \
+               data_ ## name() \
+                       : DataTest<name>::DataTest() \
                { \
-                       if (iface == #name) \
-                       { \
-                               obj_ = static_cast<name*>(wl_registry_bind(*this, id, & name ## _interface, 1)); \
-                       } \
+                       obj_ = display().bind<name>(#name, & name ## _interface); \
                } \
+               DATA_SETTER_GETTER(name) \
        }; \
        WFITS_CORE_HARNESS_TEST_CASE(data_ ## name, "DataInterface")