Skip to content

Commit

Permalink
Wire up tearing protocol callbacks
Browse files Browse the repository at this point in the history
  • Loading branch information
serebit committed Mar 10, 2024
1 parent 3f14a19 commit 8d54654
Show file tree
Hide file tree
Showing 8 changed files with 113 additions and 4 deletions.
8 changes: 8 additions & 0 deletions meson.build
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,14 @@ cursor_shape_protocol = custom_target(
build_by_default: false,
)

tearing_control_protocol = custom_target(
'tearing_control_v1_protocol_h',
input: join_paths(wayland_protocol_dir, 'staging', 'tearing-control', 'tearing-control-v1.xml'),
output: 'tearing-control-v1-protocol.h',
command: [wayland_scanner, 'server-header', '@INPUT@', '@OUTPUT@'],
build_by_default: false,
)

xdg_shell_protocol = custom_target(
'xdg_shell_server_h',
input: join_paths(wayland_protocol_dir, 'stable', 'xdg-shell', 'xdg-shell.xml'),
Expand Down
4 changes: 3 additions & 1 deletion src/meson.build
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ magpie_sources = [
'foreign_toplevel.cpp',
'output.cpp',
'server.cpp',
'tearing.cpp',
'xwayland.cpp',
'input/constraint.cpp',
'input/cursor.cpp',
Expand All @@ -15,10 +16,11 @@ magpie_sources = [
'surface/xwayland_view.cpp',
content_type_protocol,
cursor_shape_protocol,
xdg_shell_protocol,
tearing_control_protocol,
wlr_layer_shell_protocol,
wlr_output_power_management_protocol,
wlr_pointer_constraints_protocol,
xdg_shell_protocol,
]

exe = executable(
Expand Down
4 changes: 4 additions & 0 deletions src/server.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,8 @@
#include <wlr/util/log.h>
#include "wlr-wrap-end.hpp"

#include <tearing.hpp>

void Server::focus_view(View* view, wlr_surface* surface) {
const wlr_surface* prev_surface = seat->wlr->keyboard_state.focused_surface;
if (prev_surface == surface && surface != nullptr) {
Expand Down Expand Up @@ -454,4 +456,6 @@ Server::Server() : listeners(*this) {
}

content_type_manager = wlr_content_type_manager_v1_create(display, 1);

tearing_manager = new TearingManager(*this);
}
5 changes: 3 additions & 2 deletions src/server.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ class Server {
wl_listener output_layout_change = {};
wl_listener output_manager_apply = {};
wl_listener output_power_manager_set_mode = {};
wl_listener tearing_manager_new_object = {};
explicit Listeners(Server& parent) noexcept : parent(parent) {}
};

Expand All @@ -59,6 +60,8 @@ class Server {
wlr_compositor* compositor;

XWayland* xwayland;
Seat* seat;
TearingManager* tearing_manager;

wlr_scene* scene;
wlr_scene_output_layout* scene_layout;
Expand All @@ -72,8 +75,6 @@ class Server {

wlr_layer_shell_v1* layer_shell;

Seat* seat;

std::list<View*> views;
View* focused_view = nullptr;
View* grabbed_view = nullptr;
Expand Down
2 changes: 2 additions & 0 deletions src/surface/surface.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,14 @@

#include "wlr-wrap-start.hpp"
#include <wlr/types/wlr_scene.h>
#include <wlr/types/wlr_tearing_control_v1.h>
#include "wlr-wrap-end.hpp"

enum SurfaceType { MAGPIE_SURFACE_TYPE_VIEW, MAGPIE_SURFACE_TYPE_LAYER, MAGPIE_SURFACE_TYPE_POPUP };

struct Surface {
wlr_scene_node* scene_node = nullptr;
wp_tearing_control_v1_presentation_hint tearing_hint = WP_TEARING_CONTROL_V1_PRESENTATION_HINT_VSYNC;

virtual ~Surface() noexcept = default;

Expand Down
39 changes: 39 additions & 0 deletions src/tearing.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
#include "tearing.hpp"

#include "server.hpp"

#include <surface/surface.hpp>

void tearing_manager_new_object_notify(wl_listener* listener, void* data) {
TearingManager& tearing_manager = magpie_container_of(listener, tearing_manager, new_object);
auto& tearing_object_wlr = *static_cast<wlr_tearing_control_v1*>(data);

tearing_manager.tearing_objects.push_back(std::make_unique<TearingObject>(tearing_manager, tearing_object_wlr));
}

void tearing_object_set_hint_notify(wl_listener* listener, void*) {
TearingObject& tearing_object = magpie_container_of(listener, tearing_object, set_hint);

auto* surface = static_cast<Surface*>(tearing_object.wlr.surface->data);
surface->tearing_hint = static_cast<wp_tearing_control_v1_presentation_hint>(tearing_object.wlr.hint);
}

void tearing_object_destroy_notify(wl_listener* listener, void*) {
TearingObject& tearing_object = magpie_container_of(listener, tearing_object, destroy);
std::erase_if(tearing_object.parent.tearing_objects, [&](const auto& other) { return other.get() == &tearing_object; });
}

TearingManager::TearingManager(Server& server) noexcept : listeners(*this), server(server) {
wlr = wlr_tearing_control_manager_v1_create(server.display, 1);

listeners.new_object.notify = tearing_manager_new_object_notify;
wl_signal_add(&wlr->events.new_object, &listeners.new_object);
}

TearingObject::TearingObject(TearingManager& parent, wlr_tearing_control_v1& wlr) noexcept
: listeners(*this), parent(parent), wlr(wlr) {
listeners.destroy.notify = tearing_object_destroy_notify;
wl_signal_add(&wlr.events.destroy, &listeners.destroy);
listeners.set_hint.notify = tearing_object_set_hint_notify;
wl_signal_add(&wlr.events.set_hint, &listeners.set_hint);
}
52 changes: 52 additions & 0 deletions src/tearing.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
#ifndef MAGPIE_TEARING_HPP
#define MAGPIE_TEARING_HPP

#include "types.hpp"

#include <functional>
#include <list>
#include <memory>

#include "wlr-wrap-start.hpp"
#include <wlr/types/wlr_tearing_control_v1.h>
#include "wlr-wrap-end.hpp"

class TearingObject {
public:
struct Listeners {
std::reference_wrapper<TearingObject> parent;
wl_listener set_hint = {};
wl_listener destroy = {};
explicit Listeners(TearingObject& parent) noexcept : parent(parent) {}
};

private:
Listeners listeners;

public:
TearingManager& parent;
wlr_tearing_control_v1& wlr;

explicit TearingObject(TearingManager& parent, wlr_tearing_control_v1& wlr) noexcept;
};

class TearingManager {
public:
struct Listeners {
std::reference_wrapper<TearingManager> parent;
wl_listener new_object = {};
explicit Listeners(TearingManager& parent) noexcept : parent(parent) {}
};

private:
Listeners listeners;

public:
Server& server;
wlr_tearing_control_manager_v1* wlr;
std::list<std::unique_ptr<TearingObject>> tearing_objects;

explicit TearingManager(Server& server) noexcept;
};

#endif
3 changes: 2 additions & 1 deletion src/types.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,9 @@
#define MAGPIE_TYPES_HPP

class Server;
class XWayland;
class Output;
class TearingManager;
class XWayland;

class Seat;
class Keyboard;
Expand Down

0 comments on commit 8d54654

Please sign in to comment.