#ifndef XCB_RESOURCE_HH #define XCB_RESOURCE_HH #include "xcb_connection.hh" #include #include namespace xcb { namespace internal { struct WndDeleter { void operator() (xcb_connection_t* conn, xcb_window_t wnd) const { xcb_destroy_window(conn, wnd); } }; struct GCDeleter { void operator() (xcb_connection_t* conn, xcb_gcontext_t gc) const { xcb_free_gc(conn, gc); } }; struct FontDeleter { void operator() (xcb_connection_t* conn, xcb_font_t font) const { xcb_close_font(conn, font); } }; } // namespace internal template class xcb_resource { public: explicit xcb_resource(shared_conn conn) : conn_(conn), id_(xcb_generate_id(conn_.get())) {} constexpr xcb_resource() : id_(XCB_NONE) {} xcb_resource(xcb_resource const& res) = delete; xcb_resource(xcb_resource&& res) : conn_(res.conn_), id_(res.release()) { } ~xcb_resource() { reset(); } xcb_resource& operator=(xcb_resource const& res) = delete; xcb_resource& operator=(xcb_resource&& res) { reset(); conn_ = res.conn_; id_ = res.release(); return *this; } T id() const { return id_; } void reset() { if (id_ == XCB_NONE) return; deleter_(conn_.get(), id_); id_ = XCB_NONE; } T release() { auto ret = id_; id_ = XCB_NONE; conn_.reset(); return ret; } private: shared_conn conn_; T id_; Deleter const deleter_{}; }; typedef std::unique_ptr> unique_wnd; typedef std::shared_ptr> shared_wnd; unique_wnd make_unique_wnd(shared_conn conn); shared_wnd make_shared_wnd(shared_conn conn); typedef std::unique_ptr> unique_gc; typedef std::shared_ptr> shared_gc; unique_gc make_unique_gc(shared_conn conn); shared_gc make_shared_gc(shared_conn conn); typedef std::unique_ptr> unique_font; typedef std::shared_ptr> shared_font; unique_font make_unique_font(shared_conn conn); shared_font make_shared_font(shared_conn conn); } // namespace xcb #endif // XCB_RESOURCE_HH