#pragma once /* Implementations for: - wl_compositor - wl_surface - wl_region - wl_callback */ #include #include #include #include "../WaylandProtocol.hpp" #include "wayland.hpp" #include "../../helpers/signal/Signal.hpp" #include "../../helpers/math/Math.hpp" #include "../types/Buffer.hpp" #include "../types/SurfaceRole.hpp" class CWLOutputResource; class CMonitor; class CWLSurface; class CWLSurfaceResource; class CWLSubsurfaceResource; class CViewportResource; class CDRMSyncobjSurfaceResource; class CWLCallbackResource { public: CWLCallbackResource(SP resource_); bool good(); void send(timespec* now); private: SP resource; }; class CWLRegionResource { public: CWLRegionResource(SP resource_); static SP fromResource(wl_resource* res); bool good(); CRegion region; WP self; private: SP resource; }; class CWLSurfaceResource { public: CWLSurfaceResource(SP resource_); ~CWLSurfaceResource(); static SP fromResource(wl_resource* res); bool good(); wl_client* client(); void enter(SP monitor); void leave(SP monitor); void sendPreferredTransform(wl_output_transform t); void sendPreferredScale(int32_t scale); void frame(timespec* now); uint32_t id(); void map(); void unmap(); void error(int code, const std::string& str); SP getResource(); CBox extends(); void resetRole(); Vector2D sourceSize(); struct { CSignal precommit; CSignal commit; CSignal map; CSignal unmap; CSignal newSubsurface; CSignal destroy; } events; struct SState { CRegion opaque, input = CBox{{}, {INT32_MAX, INT32_MAX}}, damage, bufferDamage = CBox{{}, {INT32_MAX, INT32_MAX}} /* initial damage */; wl_output_transform transform = WL_OUTPUT_TRANSFORM_NORMAL; int scale = 1; SP buffer; SP texture; Vector2D offset; Vector2D size; struct { bool hasDestination = false; bool hasSource = false; Vector2D destination; CBox source; } viewport; bool rejected = false; // void reset() { damage.clear(); bufferDamage.clear(); transform = WL_OUTPUT_TRANSFORM_NORMAL; scale = 1; offset = {}; size = {}; } } current, pending; std::vector> callbacks; WP self; WP hlSurface; std::vector> enteredOutputs; bool mapped = false; std::vector> subsurfaces; WP role; WP viewportResource; WP syncobj; // may not be present void breadthfirst(std::function, const Vector2D&, void*)> fn, void* data); CRegion accumulateCurrentBufferDamage(); void presentFeedback(timespec* when, CMonitor* pMonitor, bool needsExplicitSync = false); void lockPendingState(); void unlockPendingState(); // returns a pair: found surface (null if not found) and surface local coords. // localCoords param is relative to 0,0 of this surface std::pair, Vector2D> at(const Vector2D& localCoords, bool allowsInput = false); private: SP resource; wl_client* pClient = nullptr; int stateLocks = 0; void destroy(); void releaseBuffers(bool onlyCurrent = true); void commitPendingState(); void bfHelper(std::vector> nodes, std::function, const Vector2D&, void*)> fn, void* data); }; class CWLCompositorResource { public: CWLCompositorResource(SP resource_); bool good(); private: SP resource; }; class CWLCompositorProtocol : public IWaylandProtocol { public: CWLCompositorProtocol(const wl_interface* iface, const int& ver, const std::string& name); virtual void bindManager(wl_client* client, void* data, uint32_t ver, uint32_t id); struct { CSignal newSurface; // SP } events; private: void destroyResource(CWLCompositorResource* resource); void destroyResource(CWLSurfaceResource* resource); void destroyResource(CWLRegionResource* resource); // std::vector> m_vManagers; std::vector> m_vSurfaces; std::vector> m_vRegions; friend class CWLSurfaceResource; friend class CWLCompositorResource; friend class CWLRegionResource; friend class CWLCallbackResource; }; namespace PROTO { inline UP compositor; };