Some wayland cleanup
This commit is contained in:
parent
7ce29ce8ae
commit
25b1966c0e
10 changed files with 267 additions and 252 deletions
17
README.md
17
README.md
|
@ -30,6 +30,23 @@ sudo apt-get install libasound2-dev
|
|||
sudo apt-get install libpng-dev
|
||||
```
|
||||
|
||||
#### Window rendering
|
||||
|
||||
```bash
|
||||
sudo apt-get install libwayland-dev wayland-protocols
|
||||
```
|
||||
|
||||
We need to generate suitable xdg shell c code for wayland:
|
||||
|
||||
```bash
|
||||
mkdir $WORK_DIR
|
||||
cd $WORK_DIR
|
||||
wayland-scanner private-code < /usr/share/wayland-protocols/stable/xdg-shell/xdg-shell.xml > xdg-shell-protocol.cpp
|
||||
wayland-scanner client-header < /usr/share/wayland-protocols/stable/xdg-shell/xdg-shell.xml > xdg-shell-client-protocol.h
|
||||
export WAYLAND_EXTENSION_DIR=$WORK_DIR
|
||||
```
|
||||
|
||||
In `xdg-shell-protocol.cpp` - we need access to `xdg_wm_base_interface` so export it also `extern const struct wl_interface xdg_wm_base_interface;` as per similar interface structs.
|
||||
|
||||
# Build from Source
|
||||
|
||||
|
|
|
@ -22,34 +22,29 @@ if(UNIX)
|
|||
message(STATUS "x11 development headers not found - skipping support")
|
||||
endif()
|
||||
|
||||
find_path(WAYLAND_CLIENT_INCLUDE_DIR NAMES wayland-client.h)
|
||||
if (NOT ${WAYLAND_CLIENT_INCLUDE_DIR-NOTFOUND})
|
||||
list(APPEND WAYLAND_INCLUDE_DIRS ${WAYLAND_CLIENT_INCLUDE_DIR})
|
||||
|
||||
find_path(WAYLAND_EXTENSIONS_INCLUDE_DIR NAMES xdg-shell-client-protocol.h
|
||||
HINTS ENV WAYLAND_EXTENSION_DIR
|
||||
)
|
||||
if(NOT ${WAYLAND_EXTENSIONS_INCLUDE_DIR-NOTFOUND})
|
||||
find_library(
|
||||
WAYLAND_CLIENT_LIBRARY
|
||||
NAMES wayland-client libwayland-client
|
||||
)
|
||||
|
||||
list(APPEND WAYLAND_INCLUDE_DIRS ${WAYLAND_EXTENSIONS_INCLUDE_DIR})
|
||||
|
||||
list(APPEND platform_INCLUDES
|
||||
ui_interfaces/wayland/WaylandWindowInterface.cpp
|
||||
ui_interfaces/wayland/WaylandSurface.cpp
|
||||
ui_interfaces/wayland/WaylandBuffer.cpp
|
||||
${WAYLAND_EXTENSIONS_INCLUDE_DIR}/xdg-shell-protocol.cpp
|
||||
)
|
||||
set(_HAS_WAYLAND ON)
|
||||
else()
|
||||
message(STATUS "Wayland Extensions Header not found - not building Wayland support")
|
||||
endif()
|
||||
else()
|
||||
message(STATUS "Wayland Client Header not found - not building Wayland support")
|
||||
endif()
|
||||
find_path(WAYLAND_CLIENT_INCLUDE_DIR NAMES wayland-client.h)
|
||||
#if (NOT ${WAYLAND_CLIENT_INCLUDE_DIR-NOTFOUND})
|
||||
list(APPEND WAYLAND_INCLUDE_DIRS ${WAYLAND_CLIENT_INCLUDE_DIR})
|
||||
|
||||
find_path(WAYLAND_EXTENSIONS_INCLUDE_DIR NAMES xdg-shell-client-protocol.h HINTS ENV WAYLAND_EXTENSION_DIR)
|
||||
|
||||
#if(NOT ${WAYLAND_EXTENSIONS_INCLUDE_DIR-NOTFOUND})
|
||||
find_library(WAYLAND_CLIENT_LIBRARY NAMES wayland-client libwayland-client)
|
||||
|
||||
list(APPEND WAYLAND_INCLUDE_DIRS ${WAYLAND_EXTENSIONS_INCLUDE_DIR})
|
||||
list(APPEND platform_INCLUDES
|
||||
ui_interfaces/wayland/WaylandWindowInterface.cpp
|
||||
ui_interfaces/wayland/WaylandSurface.cpp
|
||||
ui_interfaces/wayland/WaylandBuffer.cpp
|
||||
${WAYLAND_EXTENSIONS_INCLUDE_DIR}/xdg-shell-protocol.cpp
|
||||
)
|
||||
set(_HAS_WAYLAND ON)
|
||||
#else()
|
||||
#message(STATUS "Wayland Extensions Header not found - not building Wayland support")
|
||||
#endif()
|
||||
#else()
|
||||
#message(STATUS "Wayland Client Header not found - not building Wayland support")
|
||||
#endif()
|
||||
|
||||
else()
|
||||
list(APPEND platform_INCLUDES
|
||||
|
@ -87,6 +82,7 @@ target_include_directories(windows PUBLIC
|
|||
)
|
||||
|
||||
target_link_libraries(windows PUBLIC ${platform_LIBS} core geometry graphics ui_elements ${WAYLAND_CLIENT_LIBRARY})
|
||||
target_compile_options(windows PRIVATE -Wno-attributes) # From xdg shell autogen code
|
||||
|
||||
set_property(TARGET windows PROPERTY FOLDER src)
|
||||
set_target_properties( windows PROPERTIES WINDOWS_EXPORT_ALL_SYMBOLS ON )
|
||||
|
|
|
@ -11,10 +11,6 @@
|
|||
class WindowManager
|
||||
{
|
||||
|
||||
private:
|
||||
|
||||
std::vector<WindowUPtr> mWindows;
|
||||
|
||||
public:
|
||||
|
||||
WindowManager();
|
||||
|
@ -33,6 +29,8 @@ public:
|
|||
|
||||
void OnKeyboardEvent(const KeyboardEvent* event);
|
||||
|
||||
private:
|
||||
std::vector<WindowUPtr> mWindows;
|
||||
};
|
||||
|
||||
using WindowManagerUPtr = std::unique_ptr<WindowManager>;
|
||||
|
|
|
@ -1,25 +1,21 @@
|
|||
#include "WaylandBuffer.h"
|
||||
|
||||
#include "FileLogger.h"
|
||||
|
||||
#include <sys/mman.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include <iostream>
|
||||
|
||||
void WaylandBuffer::setSharedMemory(wl_shm* shared_memory)
|
||||
{
|
||||
mWlSharedMemory = shared_memory;
|
||||
}
|
||||
|
||||
void WaylandBuffer::initializeSharedBuffer(int size)
|
||||
{
|
||||
mSharedMemory = std::make_unique<SharedMemory>();
|
||||
mSharedMemory->allocate("/wl_shm-XXXXXX", size);
|
||||
mSharedMemory = std::make_unique<SharedMemory>();
|
||||
mSharedMemory->allocate("/wl_shm-XXXXXX", size);
|
||||
|
||||
if (!mSharedMemory->isValid())
|
||||
{
|
||||
return;
|
||||
}
|
||||
mPoolData = static_cast<uint8_t*>(mmap(nullptr, size, PROT_READ | PROT_WRITE, MAP_SHARED, mSharedMemory->getFileDescriptor(), 0));
|
||||
if (!mSharedMemory->isValid())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
mPoolData = static_cast<uint8_t*>(mmap(nullptr, size, PROT_READ | PROT_WRITE, MAP_SHARED, mSharedMemory->getFileDescriptor(), 0));
|
||||
if (mPoolData == MAP_FAILED)
|
||||
{
|
||||
close(mSharedMemory->getFileDescriptor());
|
||||
|
@ -27,51 +23,56 @@ void WaylandBuffer::initializeSharedBuffer(int size)
|
|||
}
|
||||
}
|
||||
|
||||
void WaylandBuffer::setSharedMemory(wl_shm* shared_memory)
|
||||
{
|
||||
mWlSharedMemory = shared_memory;
|
||||
}
|
||||
|
||||
void WaylandBuffer::setUpPool(int size, int width, int height, int stride)
|
||||
{
|
||||
if (!mSharedMemory->isValid())
|
||||
{
|
||||
std::cout << "Failed to allocate shared memory" << std::endl;
|
||||
return;
|
||||
}
|
||||
if (!mSharedMemory->isValid())
|
||||
{
|
||||
MLOG_ERROR("Failed to allocate shared memory.");
|
||||
return;
|
||||
}
|
||||
|
||||
if (!mPoolData)
|
||||
{
|
||||
std::cout << "Failed to mmap pool" << std::endl;
|
||||
return;
|
||||
}
|
||||
if (!mPoolData)
|
||||
{
|
||||
MLOG_ERROR("Failed to allocate shared memory.");
|
||||
return;
|
||||
}
|
||||
|
||||
auto pool = wl_shm_create_pool(mWlSharedMemory, mSharedMemory->getFileDescriptor(), size);
|
||||
auto pool = wl_shm_create_pool(mWlSharedMemory, mSharedMemory->getFileDescriptor(), size);
|
||||
|
||||
int index = 0;
|
||||
// int offset = height * stride * index; // Two buffers, offset to starting point of second
|
||||
int offset = 0;
|
||||
int index = 0;
|
||||
// int offset = height * stride * index; // Two buffers, offset to starting point of second
|
||||
int offset = 0;
|
||||
|
||||
mWorkingBuffer = wl_shm_pool_create_buffer(pool, offset, width, height, stride, WL_SHM_FORMAT_XRGB8888);
|
||||
mWorkingBuffer = wl_shm_pool_create_buffer(pool, offset, width, height, stride, WL_SHM_FORMAT_XRGB8888);
|
||||
|
||||
wl_shm_pool_destroy(pool);
|
||||
close(mSharedMemory->getFileDescriptor());
|
||||
wl_shm_pool_destroy(pool);
|
||||
close(mSharedMemory->getFileDescriptor());
|
||||
}
|
||||
|
||||
void WaylandBuffer::tearDownPool(int size)
|
||||
{
|
||||
munmap(mPoolData, size);
|
||||
munmap(mPoolData, size);
|
||||
|
||||
auto wl_buffer_release = [](void *data, struct wl_buffer *wl_buffer)
|
||||
{
|
||||
wl_buffer_destroy(wl_buffer);
|
||||
};
|
||||
mBufferListener.release = wl_buffer_release;
|
||||
auto wl_buffer_release = [](void *data, struct wl_buffer *wl_buffer)
|
||||
{
|
||||
wl_buffer_destroy(wl_buffer);
|
||||
};
|
||||
mBufferListener.release = wl_buffer_release;
|
||||
|
||||
wl_buffer_add_listener(mWorkingBuffer, &mBufferListener, nullptr);
|
||||
wl_buffer_add_listener(mWorkingBuffer, &mBufferListener, nullptr);
|
||||
}
|
||||
|
||||
uint8_t* WaylandBuffer::getPoolData()
|
||||
{
|
||||
return mPoolData;
|
||||
return mPoolData;
|
||||
}
|
||||
|
||||
wl_buffer* WaylandBuffer::getWorkingBuffer()
|
||||
{
|
||||
return mWorkingBuffer;
|
||||
return mWorkingBuffer;
|
||||
}
|
||||
|
|
|
@ -10,26 +10,24 @@ class WaylandBuffer
|
|||
{
|
||||
public:
|
||||
|
||||
WaylandBuffer() = default;
|
||||
WaylandBuffer() = default;
|
||||
void initializeSharedBuffer(int size);
|
||||
|
||||
void setSharedMemory(wl_shm* shared_memory);
|
||||
uint8_t* getPoolData();
|
||||
wl_buffer* getWorkingBuffer();
|
||||
|
||||
void initializeSharedBuffer(int size);
|
||||
void setUpPool(int size, int width, int height, int stride);
|
||||
void setSharedMemory(wl_shm* shared_memory);
|
||||
|
||||
uint8_t* getPoolData();
|
||||
wl_buffer* getWorkingBuffer();
|
||||
|
||||
void setUpPool(int size, int width, int height, int stride);
|
||||
|
||||
void tearDownPool(int size);
|
||||
void tearDownPool(int size);
|
||||
|
||||
private:
|
||||
wl_shm* mWlSharedMemory{nullptr};
|
||||
wl_shm* mWlSharedMemory{nullptr};
|
||||
|
||||
std::unique_ptr<SharedMemory> mSharedMemory;
|
||||
uint8_t* mPoolData{nullptr};
|
||||
wl_shm_pool* mPool{nullptr};
|
||||
std::unique_ptr<SharedMemory> mSharedMemory;
|
||||
uint8_t* mPoolData{nullptr};
|
||||
wl_shm_pool* mPool{nullptr};
|
||||
|
||||
wl_buffer* mWorkingBuffer{nullptr};
|
||||
wl_buffer_listener mBufferListener;
|
||||
wl_buffer* mWorkingBuffer{nullptr};
|
||||
wl_buffer_listener mBufferListener;
|
||||
};
|
||||
|
|
|
@ -1,11 +1,7 @@
|
|||
#include "WaylandSurface.h"
|
||||
|
||||
#include <iostream>
|
||||
#include <sys/mman.h>
|
||||
#include <unistd.h>
|
||||
|
||||
WaylandSurface::WaylandSurface(mt::Window* window)
|
||||
: mWindow(window)
|
||||
: mWindow(window)
|
||||
{
|
||||
|
||||
}
|
||||
|
@ -17,21 +13,21 @@ WaylandSurface::~WaylandSurface()
|
|||
|
||||
void WaylandSurface::initialize(wl_compositor* compositor, xdg_wm_base* xdg_wm_base, std::shared_ptr<WaylandBuffer> buffer)
|
||||
{
|
||||
mBuffer = buffer;
|
||||
mBuffer = buffer;
|
||||
|
||||
mSurface = wl_compositor_create_surface(compositor);
|
||||
mXdgSurface = xdg_wm_base_get_xdg_surface(xdg_wm_base, mSurface);
|
||||
mSurface = wl_compositor_create_surface(compositor);
|
||||
mXdgSurface = xdg_wm_base_get_xdg_surface(xdg_wm_base, mSurface);
|
||||
|
||||
auto xdg_surface_configure = [](void *data, struct xdg_surface *xdg_surface, uint32_t serial)
|
||||
{
|
||||
auto thisClass = static_cast<WaylandSurface*>(data);
|
||||
thisClass->onConfigure(xdg_surface, serial);
|
||||
};
|
||||
mXdgSurfaceListener.configure = xdg_surface_configure;
|
||||
auto xdg_surface_configure = [](void *data, struct xdg_surface *xdg_surface, uint32_t serial)
|
||||
{
|
||||
auto thisClass = static_cast<WaylandSurface*>(data);
|
||||
thisClass->onConfigure(xdg_surface, serial);
|
||||
};
|
||||
mXdgSurfaceListener.configure = xdg_surface_configure;
|
||||
|
||||
xdg_surface_add_listener(mXdgSurface, &mXdgSurfaceListener, this);
|
||||
xdg_surface_add_listener(mXdgSurface, &mXdgSurfaceListener, this);
|
||||
|
||||
mXdgTopLevel = xdg_surface_get_toplevel(mXdgSurface);
|
||||
mXdgTopLevel = xdg_surface_get_toplevel(mXdgSurface);
|
||||
xdg_toplevel_set_title(mXdgTopLevel, "Example client");
|
||||
|
||||
wl_surface_commit(mSurface);
|
||||
|
@ -49,43 +45,43 @@ void WaylandSurface::onConfigure(xdg_surface *xdg_surface, uint32_t serial)
|
|||
|
||||
wl_buffer* WaylandSurface::drawFrame()
|
||||
{
|
||||
const auto width = mWindow->GetWidth();
|
||||
const auto height = mWindow->GetHeight();
|
||||
const auto width = mWindow->GetWidth();
|
||||
const auto height = mWindow->GetHeight();
|
||||
|
||||
const int bitDepth = 4;
|
||||
const int bitDepth = 4;
|
||||
|
||||
const int stride = width * bitDepth;
|
||||
//const int numBuffers = 2; // i.e. front/back
|
||||
const int numBuffers = 1;
|
||||
const int shm_pool_size = height * stride * numBuffers;
|
||||
const int stride = width * bitDepth;
|
||||
//const int numBuffers = 2; // i.e. front/back
|
||||
const int numBuffers = 1;
|
||||
const int shm_pool_size = height * stride * numBuffers;
|
||||
|
||||
mBuffer->initializeSharedBuffer(shm_pool_size);
|
||||
mBuffer->setUpPool(shm_pool_size, width, height, stride);
|
||||
mBuffer->initializeSharedBuffer(shm_pool_size);
|
||||
mBuffer->setUpPool(shm_pool_size, width, height, stride);
|
||||
|
||||
int offset = 0;
|
||||
drawCheckerboard(width, height, offset);
|
||||
int offset = 0;
|
||||
drawCheckerboard(width, height, offset);
|
||||
|
||||
mBuffer->tearDownPool(shm_pool_size);
|
||||
mBuffer->tearDownPool(shm_pool_size);
|
||||
|
||||
return mBuffer->getWorkingBuffer();
|
||||
return mBuffer->getWorkingBuffer();
|
||||
}
|
||||
|
||||
void WaylandSurface::drawCheckerboard(int width, int height, int offset)
|
||||
{
|
||||
uint32_t *pixels = (uint32_t *)&(mBuffer->getPoolData())[offset];
|
||||
for (int y = 0; y < height; ++y)
|
||||
{
|
||||
for (int x = 0; x < width; ++x)
|
||||
{
|
||||
if ((x + y / 8 * 8) % 16 < 8)
|
||||
{
|
||||
pixels[y * width + x] = 0xFF666666;
|
||||
}
|
||||
else
|
||||
{
|
||||
pixels[y * width + x] = 0xFFEEEEEE;
|
||||
}
|
||||
}
|
||||
}
|
||||
uint32_t *pixels = (uint32_t *)&(mBuffer->getPoolData())[offset];
|
||||
for (int y = 0; y < height; ++y)
|
||||
{
|
||||
for (int x = 0; x < width; ++x)
|
||||
{
|
||||
if ((x + y / 8 * 8) % 16 < 8)
|
||||
{
|
||||
pixels[y * width + x] = 0xFF666666;
|
||||
}
|
||||
else
|
||||
{
|
||||
pixels[y * width + x] = 0xFFEEEEEE;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -15,30 +15,28 @@ class WaylandSurface
|
|||
{
|
||||
|
||||
public:
|
||||
WaylandSurface(mt::Window* window);
|
||||
|
||||
WaylandSurface(mt::Window* window);
|
||||
~WaylandSurface();
|
||||
|
||||
~WaylandSurface();
|
||||
void initialize(wl_compositor* compositor, xdg_wm_base* xdg_wm_base, std::shared_ptr<WaylandBuffer> buffer);
|
||||
|
||||
void initialize(wl_compositor* compositor, xdg_wm_base* xdg_wm_base, std::shared_ptr<WaylandBuffer> buffer);
|
||||
void onConfigure(xdg_surface *xdg_surface, uint32_t serial);
|
||||
|
||||
void onConfigure(xdg_surface *xdg_surface, uint32_t serial);
|
||||
wl_buffer* drawFrame();
|
||||
|
||||
wl_buffer* drawFrame();
|
||||
|
||||
void drawCheckerboard(int width, int height, int offset);
|
||||
void drawCheckerboard(int width, int height, int offset);
|
||||
|
||||
private:
|
||||
mt::Window* mWindow{nullptr};
|
||||
|
||||
mt::Window* mWindow{nullptr};
|
||||
wl_surface* mSurface{nullptr};
|
||||
xdg_surface* mXdgSurface{nullptr};
|
||||
xdg_surface_listener mXdgSurfaceListener{nullptr};
|
||||
|
||||
wl_surface* mSurface{nullptr};
|
||||
xdg_surface* mXdgSurface{nullptr};
|
||||
xdg_surface_listener mXdgSurfaceListener{nullptr};
|
||||
xdg_toplevel* mXdgTopLevel{nullptr};
|
||||
|
||||
xdg_toplevel* mXdgTopLevel{nullptr};
|
||||
|
||||
std::shared_ptr<WaylandBuffer> mBuffer;
|
||||
std::shared_ptr<WaylandBuffer> mBuffer;
|
||||
};
|
||||
|
||||
using WaylandSurfacePtr = std::unique_ptr<WaylandSurface>;
|
||||
|
|
|
@ -1,39 +1,46 @@
|
|||
#include "WaylandWindowInterface.h"
|
||||
|
||||
#include "FileLogger.h"
|
||||
#include "WaylandSurface.h"
|
||||
#include "WaylandBuffer.h"
|
||||
|
||||
#include <cstring>
|
||||
#include <sstream>
|
||||
|
||||
void WaylandWindowInterface::registryHandleGlobalCallback(void *data, struct wl_registry *registry,
|
||||
uint32_t name, const char *interface, uint32_t version)
|
||||
{
|
||||
auto thisClass = static_cast<WaylandWindowInterface*>(data);
|
||||
|
||||
std::stringstream sstrm;
|
||||
sstrm << "interface: " << interface << " version " << version << " name " << name;
|
||||
MLOG_INFO(sstrm.str());
|
||||
|
||||
if (strcmp(interface, wl_compositor_interface.name) == 0)
|
||||
{
|
||||
thisClass->setCompositor(static_cast<wl_compositor*>(wl_registry_bind(registry, name, &wl_compositor_interface, 4)));
|
||||
}
|
||||
else if (strcmp(interface, wl_shm_interface.name) == 0)
|
||||
{
|
||||
thisClass->setSharedMemory(static_cast<wl_shm*>(wl_registry_bind(registry, name, &wl_shm_interface, 1)));
|
||||
}
|
||||
else if (strcmp(interface, xdg_wm_base_interface.name) == 0)
|
||||
{
|
||||
thisClass->setXdgBase(static_cast<xdg_wm_base*>(wl_registry_bind(registry, name, &xdg_wm_base_interface, 1)));
|
||||
}
|
||||
}
|
||||
|
||||
void WaylandWindowInterface::registryHandleGlobalRemoveCallback(void *data, struct wl_registry *registry, uint32_t name)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
|
||||
WaylandWindowInterface::WaylandWindowInterface()
|
||||
: mBuffer(std::make_shared<WaylandBuffer>())
|
||||
: mBuffer(std::make_shared<WaylandBuffer>())
|
||||
{
|
||||
auto registry_handle_global_func = [](void *data, struct wl_registry *registry,
|
||||
uint32_t name, const char *interface, uint32_t version)
|
||||
{
|
||||
auto thisClass = static_cast<WaylandWindowInterface*>(data);
|
||||
|
||||
printf("interface: '%s', version: %d, name: %d\n", interface, version, name);
|
||||
|
||||
if (strcmp(interface, wl_compositor_interface.name) == 0)
|
||||
{
|
||||
thisClass->setCompositor(static_cast<wl_compositor*>(wl_registry_bind(registry, name, &wl_compositor_interface, 4)));
|
||||
}
|
||||
else if (strcmp(interface, wl_shm_interface.name) == 0)
|
||||
{
|
||||
thisClass->setSharedMemory(static_cast<wl_shm*>(wl_registry_bind(registry, name, &wl_shm_interface, 1)));
|
||||
}
|
||||
else if (strcmp(interface, xdg_wm_base_interface.name) == 0)
|
||||
{
|
||||
thisClass->setXdgBase(static_cast<xdg_wm_base*>(wl_registry_bind(registry, name, &xdg_wm_base_interface, 1)));
|
||||
}
|
||||
};
|
||||
|
||||
auto registry_handle_global_remove_func = [](void *data, struct wl_registry *registry,
|
||||
uint32_t name)
|
||||
{
|
||||
// This space deliberately left blank;
|
||||
};
|
||||
|
||||
mRegistryListener.global = registry_handle_global_func;
|
||||
mRegistryListener.global_remove = registry_handle_global_remove_func;
|
||||
mRegistryListener.global = registryHandleGlobalCallback;
|
||||
mRegistryListener.global_remove = registryHandleGlobalRemoveCallback;
|
||||
}
|
||||
|
||||
WaylandWindowInterface::~WaylandWindowInterface()
|
||||
|
@ -41,56 +48,58 @@ WaylandWindowInterface::~WaylandWindowInterface()
|
|||
|
||||
}
|
||||
|
||||
void WaylandWindowInterface::setXdgBase(xdg_wm_base* xdg_base)
|
||||
void WaylandWindowInterface::connect()
|
||||
{
|
||||
mXdgBase = xdg_base;
|
||||
auto xdg_ping_handler = [](void *data, struct xdg_wm_base *xdg_wm_base, uint32_t serial)
|
||||
{
|
||||
auto thisClass = static_cast<WaylandWindowInterface*>(data);
|
||||
thisClass->doXdgPong(serial);
|
||||
};
|
||||
mXdgBaseListener.ping = xdg_ping_handler;
|
||||
xdg_wm_base_add_listener(mXdgBase, &mXdgBaseListener, this);
|
||||
mDisplay = wl_display_connect(nullptr);
|
||||
|
||||
if (!mDisplay)
|
||||
{
|
||||
MLOG_ERROR("Display connect error");
|
||||
return;
|
||||
}
|
||||
|
||||
auto registry = wl_display_get_registry(mDisplay);
|
||||
if (!registry)
|
||||
{
|
||||
MLOG_ERROR("Failed to get registry");
|
||||
return;
|
||||
}
|
||||
|
||||
wl_registry_add_listener(registry, &mRegistryListener, this);
|
||||
wl_display_roundtrip(mDisplay);
|
||||
}
|
||||
|
||||
void WaylandWindowInterface::doXdgPong(uint32_t serial)
|
||||
void WaylandWindowInterface::setXdgBase(xdg_wm_base* xdg_base)
|
||||
{
|
||||
xdg_wm_base_pong(mXdgBase, serial);
|
||||
mXdgBase = xdg_base;
|
||||
auto xdg_ping_handler = [](void *data, struct xdg_wm_base *xdg_wm_base, uint32_t serial)
|
||||
{
|
||||
auto thisClass = static_cast<WaylandWindowInterface*>(data);
|
||||
thisClass->doXdgPong(serial);
|
||||
};
|
||||
mXdgBaseListener.ping = xdg_ping_handler;
|
||||
xdg_wm_base_add_listener(mXdgBase, &mXdgBaseListener, this);
|
||||
}
|
||||
|
||||
void WaylandWindowInterface::setCompositor(wl_compositor* compositor)
|
||||
{
|
||||
mCompositor = compositor;
|
||||
mCompositor = compositor;
|
||||
}
|
||||
|
||||
void WaylandWindowInterface::setSharedMemory(wl_shm* shared_memory)
|
||||
{
|
||||
mBuffer->setSharedMemory(shared_memory);
|
||||
mBuffer->setSharedMemory(shared_memory);
|
||||
}
|
||||
|
||||
void WaylandWindowInterface::connect()
|
||||
void WaylandWindowInterface::doXdgPong(uint32_t serial)
|
||||
{
|
||||
mDisplay = wl_display_connect(nullptr);
|
||||
|
||||
if (!mDisplay)
|
||||
{
|
||||
std::cout << "Display connect error" << std::endl;
|
||||
}
|
||||
|
||||
auto registry = wl_display_get_registry(mDisplay);
|
||||
if (!registry)
|
||||
{
|
||||
std::cout << "Failed to get registry" << std::endl;
|
||||
}
|
||||
|
||||
wl_registry_add_listener(registry, &mRegistryListener, this);
|
||||
wl_display_roundtrip(mDisplay);
|
||||
xdg_wm_base_pong(mXdgBase, serial);
|
||||
}
|
||||
|
||||
void WaylandWindowInterface::addWindow(mt::Window* window)
|
||||
{
|
||||
auto surface = std::make_unique<WaylandSurface>(window);
|
||||
mSurfaces.push_back(std::move(surface));
|
||||
auto surface = std::make_unique<WaylandSurface>(window);
|
||||
mSurfaces.push_back(std::move(surface));
|
||||
}
|
||||
|
||||
void WaylandWindowInterface::mapWindow(mt::Window* window)
|
||||
|
@ -100,15 +109,16 @@ void WaylandWindowInterface::mapWindow(mt::Window* window)
|
|||
|
||||
void WaylandWindowInterface::disconnect()
|
||||
{
|
||||
if (mDisplay)
|
||||
{
|
||||
wl_display_disconnect(mDisplay);
|
||||
}
|
||||
if (mDisplay)
|
||||
{
|
||||
wl_display_disconnect(mDisplay);
|
||||
}
|
||||
}
|
||||
|
||||
void WaylandWindowInterface::run()
|
||||
{
|
||||
while (wl_display_dispatch(mDisplay) != -1) {
|
||||
/* This space deliberately left blank */
|
||||
}
|
||||
while (wl_display_dispatch(mDisplay) != -1)
|
||||
{
|
||||
/* This space deliberately left blank */
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,56 +1,56 @@
|
|||
#pragma once
|
||||
|
||||
#include "wayland-client.h"
|
||||
#include "xdg-shell-client-protocol.h"
|
||||
|
||||
#include "Window.h"
|
||||
#include "SharedMemory.h"
|
||||
|
||||
#include "WaylandSurface.h"
|
||||
#include "WaylandBuffer.h"
|
||||
#include "wayland-client.h"
|
||||
#include "xdg-shell-client-protocol.h"
|
||||
|
||||
#include <iostream>
|
||||
#include <vector>
|
||||
#include <memory>
|
||||
|
||||
class WaylandSurface;
|
||||
class WaylandBuffer;
|
||||
|
||||
class WaylandWindowInterface
|
||||
{
|
||||
|
||||
public:
|
||||
|
||||
WaylandWindowInterface();
|
||||
WaylandWindowInterface();
|
||||
|
||||
~WaylandWindowInterface();
|
||||
~WaylandWindowInterface();
|
||||
|
||||
void setXdgBase(xdg_wm_base* xdg_base);
|
||||
void connect();
|
||||
|
||||
void doXdgPong(uint32_t serial);
|
||||
void disconnect();
|
||||
|
||||
void setCompositor(wl_compositor* compositor);
|
||||
void run();
|
||||
|
||||
void setSharedMemory(wl_shm* shared_memory);
|
||||
void addWindow(mt::Window* window);
|
||||
|
||||
void connect();
|
||||
|
||||
void disconnect();
|
||||
|
||||
void run();
|
||||
|
||||
void addWindow(mt::Window* window);
|
||||
|
||||
void mapWindow(mt::Window* window);
|
||||
void mapWindow(mt::Window* window);
|
||||
|
||||
private:
|
||||
static void registryHandleGlobalCallback(void *data, struct wl_registry *registry, uint32_t name, const char *interface, uint32_t version);
|
||||
static void registryHandleGlobalRemoveCallback(void *data, struct wl_registry *registry, uint32_t name);
|
||||
|
||||
std::vector<std::unique_ptr<WaylandSurface> > mSurfaces;
|
||||
void doXdgPong(uint32_t serial);
|
||||
|
||||
wl_display* mDisplay{nullptr};
|
||||
wl_compositor* mCompositor{nullptr};
|
||||
wl_registry_listener mRegistryListener;
|
||||
void setCompositor(wl_compositor* compositor);
|
||||
|
||||
xdg_wm_base* mXdgBase{nullptr};
|
||||
xdg_wm_base_listener mXdgBaseListener;
|
||||
void setSharedMemory(wl_shm* shared_memory);
|
||||
|
||||
std::shared_ptr<WaylandBuffer> mBuffer;
|
||||
void setXdgBase(xdg_wm_base* xdg_base);
|
||||
|
||||
wl_display* mDisplay{nullptr};
|
||||
wl_compositor* mCompositor{nullptr};
|
||||
wl_registry_listener mRegistryListener;
|
||||
|
||||
xdg_wm_base* mXdgBase{nullptr};
|
||||
xdg_wm_base_listener mXdgBaseListener;
|
||||
|
||||
std::vector<std::unique_ptr<WaylandSurface> > mSurfaces;
|
||||
std::shared_ptr<WaylandBuffer> mBuffer;
|
||||
|
||||
};
|
||||
|
|
|
@ -1,23 +1,24 @@
|
|||
#include "WaylandWindowInterface.h"
|
||||
|
||||
#include "Window.h"
|
||||
|
||||
|
||||
#include "FileLogger.h"
|
||||
|
||||
int main()
|
||||
{
|
||||
WaylandWindowInterface window_interface;
|
||||
window_interface.connect();
|
||||
FileLogger::GetInstance().Open();
|
||||
|
||||
auto window = mt::Window::Create();
|
||||
window->SetSize(800, 600);
|
||||
WaylandWindowInterface window_interface;
|
||||
window_interface.connect();
|
||||
|
||||
window_interface.addWindow(window.get());
|
||||
auto window = mt::Window::Create();
|
||||
window->SetSize(800, 600);
|
||||
|
||||
window_interface.mapWindow(window.get());
|
||||
window_interface.addWindow(window.get());
|
||||
|
||||
window_interface.run();
|
||||
window_interface.mapWindow(window.get());
|
||||
|
||||
window_interface.disconnect();
|
||||
return 0;
|
||||
window_interface.run();
|
||||
|
||||
window_interface.disconnect();
|
||||
return 0;
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue