Compare commits
12 Commits
3e0dc851c4
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
| b228ef13c4 | |||
| f7150056c4 | |||
| bb7632d53f | |||
| 862eaa205a | |||
| 61f8b2fa66 | |||
| e376c57cda | |||
| 561aaecc3f | |||
| 4886e71452 | |||
| 710b896a84 | |||
| 8c2fea9edf | |||
| 85bb292a31 | |||
| 20f105f56c |
@@ -348,6 +348,10 @@ namespace LibGUI
|
||||
if (m_window_focus_event_callback)
|
||||
m_window_focus_event_callback(TRY_OR_BREAK(EventPacket::WindowFocusEvent::deserialize(packet_data.span())).event);
|
||||
break;
|
||||
case PacketType::WindowFullscreenEvent:
|
||||
if (m_window_fullscreen_event_callback)
|
||||
m_window_fullscreen_event_callback(TRY_OR_BREAK(EventPacket::WindowFullscreenEvent::deserialize(packet_data.span())).event);
|
||||
break;
|
||||
case PacketType::KeyEvent:
|
||||
if (m_key_event_callback)
|
||||
m_key_event_callback(TRY_OR_BREAK(EventPacket::KeyEvent::deserialize(packet_data.span())).event);
|
||||
|
||||
@@ -7,7 +7,6 @@
|
||||
#include <LibInput/KeyEvent.h>
|
||||
#include <LibInput/MouseEvent.h>
|
||||
|
||||
#include <cstdint>
|
||||
#include <sys/socket.h>
|
||||
|
||||
#define FOR_EACH_0(macro)
|
||||
@@ -219,6 +218,7 @@ namespace LibGUI
|
||||
ResizeWindowEvent,
|
||||
WindowShownEvent,
|
||||
WindowFocusEvent,
|
||||
WindowFullscreenEvent,
|
||||
KeyEvent,
|
||||
MouseButtonEvent,
|
||||
MouseMoveEvent,
|
||||
@@ -345,6 +345,14 @@ namespace LibGUI
|
||||
event_t, event
|
||||
);
|
||||
|
||||
DEFINE_PACKET_EXTRA(
|
||||
WindowFullscreenEvent,
|
||||
struct event_t {
|
||||
bool fullscreen;
|
||||
},
|
||||
event_t, event
|
||||
);
|
||||
|
||||
DEFINE_PACKET_EXTRA(
|
||||
KeyEvent,
|
||||
using event_t = LibInput::KeyEvent,
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
|
||||
#include <BAN/StringView.h>
|
||||
|
||||
#include <cstdint>
|
||||
#include <stdint.h>
|
||||
|
||||
namespace LibFont { class Font; }
|
||||
|
||||
@@ -68,15 +68,16 @@ namespace LibGUI
|
||||
void wait_events();
|
||||
void poll_events();
|
||||
|
||||
void set_socket_error_callback(BAN::Function<void()> callback) { m_socket_error_callback = callback; }
|
||||
void set_close_window_event_callback(BAN::Function<void()> callback) { m_close_window_event_callback = callback; }
|
||||
void set_resize_window_event_callback(BAN::Function<void()> callback) { m_resize_window_event_callback = callback; }
|
||||
void set_key_event_callback(BAN::Function<void(EventPacket::KeyEvent::event_t)> callback) { m_key_event_callback = callback; }
|
||||
void set_mouse_button_event_callback(BAN::Function<void(EventPacket::MouseButtonEvent::event_t)> callback) { m_mouse_button_event_callback = callback; }
|
||||
void set_mouse_move_event_callback(BAN::Function<void(EventPacket::MouseMoveEvent::event_t)> callback) { m_mouse_move_event_callback = callback; }
|
||||
void set_mouse_scroll_event_callback(BAN::Function<void(EventPacket::MouseScrollEvent::event_t)> callback) { m_mouse_scroll_event_callback = callback; }
|
||||
void set_window_shown_event_callback(BAN::Function<void(EventPacket::WindowShownEvent::event_t)> callback) { m_window_shown_event_callback = callback; }
|
||||
void set_window_focus_event_callback(BAN::Function<void(EventPacket::WindowFocusEvent::event_t)> callback) { m_window_focus_event_callback = callback; }
|
||||
void set_socket_error_callback(BAN::Function<void()> callback) { m_socket_error_callback = callback; }
|
||||
void set_close_window_event_callback(BAN::Function<void()> callback) { m_close_window_event_callback = callback; }
|
||||
void set_resize_window_event_callback(BAN::Function<void()> callback) { m_resize_window_event_callback = callback; }
|
||||
void set_key_event_callback(BAN::Function<void(EventPacket::KeyEvent::event_t)> callback) { m_key_event_callback = callback; }
|
||||
void set_mouse_button_event_callback(BAN::Function<void(EventPacket::MouseButtonEvent::event_t)> callback) { m_mouse_button_event_callback = callback; }
|
||||
void set_mouse_move_event_callback(BAN::Function<void(EventPacket::MouseMoveEvent::event_t)> callback) { m_mouse_move_event_callback = callback; }
|
||||
void set_mouse_scroll_event_callback(BAN::Function<void(EventPacket::MouseScrollEvent::event_t)> callback) { m_mouse_scroll_event_callback = callback; }
|
||||
void set_window_shown_event_callback(BAN::Function<void(EventPacket::WindowShownEvent::event_t)> callback) { m_window_shown_event_callback = callback; }
|
||||
void set_window_focus_event_callback(BAN::Function<void(EventPacket::WindowFocusEvent::event_t)> callback) { m_window_focus_event_callback = callback; }
|
||||
void set_window_fullscreen_event_callback(BAN::Function<void(EventPacket::WindowFullscreenEvent::event_t)> callback) { m_window_fullscreen_event_callback = callback; }
|
||||
|
||||
int server_fd() const { return m_server_fd; }
|
||||
|
||||
@@ -107,15 +108,16 @@ namespace LibGUI
|
||||
Texture m_texture;
|
||||
BAN::RefPtr<Widget::Widget> m_root_widget;
|
||||
|
||||
BAN::Function<void()> m_socket_error_callback;
|
||||
BAN::Function<void()> m_close_window_event_callback;
|
||||
BAN::Function<void()> m_resize_window_event_callback;
|
||||
BAN::Function<void(EventPacket::WindowShownEvent::event_t)> m_window_shown_event_callback;
|
||||
BAN::Function<void(EventPacket::WindowFocusEvent::event_t)> m_window_focus_event_callback;
|
||||
BAN::Function<void(EventPacket::KeyEvent::event_t)> m_key_event_callback;
|
||||
BAN::Function<void(EventPacket::MouseButtonEvent::event_t)> m_mouse_button_event_callback;
|
||||
BAN::Function<void(EventPacket::MouseMoveEvent::event_t)> m_mouse_move_event_callback;
|
||||
BAN::Function<void(EventPacket::MouseScrollEvent::event_t)> m_mouse_scroll_event_callback;
|
||||
BAN::Function<void()> m_socket_error_callback;
|
||||
BAN::Function<void()> m_close_window_event_callback;
|
||||
BAN::Function<void()> m_resize_window_event_callback;
|
||||
BAN::Function<void(EventPacket::WindowShownEvent::event_t)> m_window_shown_event_callback;
|
||||
BAN::Function<void(EventPacket::WindowFocusEvent::event_t)> m_window_focus_event_callback;
|
||||
BAN::Function<void(EventPacket::WindowFullscreenEvent::event_t)> m_window_fullscreen_event_callback;
|
||||
BAN::Function<void(EventPacket::KeyEvent::event_t)> m_key_event_callback;
|
||||
BAN::Function<void(EventPacket::MouseButtonEvent::event_t)> m_mouse_button_event_callback;
|
||||
BAN::Function<void(EventPacket::MouseMoveEvent::event_t)> m_mouse_move_event_callback;
|
||||
BAN::Function<void(EventPacket::MouseScrollEvent::event_t)> m_mouse_scroll_event_callback;
|
||||
|
||||
friend class BAN::UniqPtr<Window>;
|
||||
};
|
||||
|
||||
@@ -94,7 +94,7 @@ void WindowServer::on_window_create(int fd, const LibGUI::WindowPacket::WindowCr
|
||||
|
||||
window_popper.disable();
|
||||
|
||||
if (packet.attributes.shown && packet.attributes.focusable)
|
||||
if (packet.attributes.shown && packet.attributes.focusable && m_state == State::Normal)
|
||||
set_focused_window(window);
|
||||
else if (m_client_windows.size() > 1)
|
||||
BAN::swap(m_client_windows[m_client_windows.size() - 1], m_client_windows[m_client_windows.size() - 2]);
|
||||
@@ -177,9 +177,15 @@ void WindowServer::on_window_set_attributes(int fd, const LibGUI::WindowPacket::
|
||||
|
||||
if ((!packet.attributes.focusable || !packet.attributes.shown) && m_focused_window == target_window)
|
||||
{
|
||||
if (m_state == State::Fullscreen && m_focused_window->get_attributes().resizable)
|
||||
{
|
||||
if (!resize_window(m_focused_window, m_non_full_screen_rect.width, m_non_full_screen_rect.height))
|
||||
return;
|
||||
m_focused_window->set_position({ m_non_full_screen_rect.x, m_non_full_screen_rect.y });
|
||||
}
|
||||
|
||||
m_focused_window = nullptr;
|
||||
if (m_state == State::Moving || m_state == State::Resizing)
|
||||
m_state = State::Normal;
|
||||
m_state = State::Normal;
|
||||
for (size_t i = m_client_windows.size(); i > 0; i--)
|
||||
{
|
||||
auto& window = m_client_windows[i - 1];
|
||||
@@ -202,7 +208,7 @@ void WindowServer::on_window_set_attributes(int fd, const LibGUI::WindowPacket::
|
||||
if (auto ret = event_packet.send_serialized(target_window->client_fd()); ret.is_error())
|
||||
dwarnln("could not send window shown event: {}", ret.error());
|
||||
|
||||
if (packet.attributes.focusable && packet.attributes.shown)
|
||||
if (packet.attributes.focusable && packet.attributes.shown && m_state == State::Normal)
|
||||
set_focused_window(target_window);
|
||||
}
|
||||
|
||||
@@ -302,6 +308,13 @@ void WindowServer::on_window_set_fullscreen(int fd, const LibGUI::WindowPacket::
|
||||
return;
|
||||
m_focused_window->set_position({ m_non_full_screen_rect.x, m_non_full_screen_rect.y });
|
||||
}
|
||||
|
||||
auto event_packet = LibGUI::EventPacket::WindowFullscreenEvent {
|
||||
.event = { .fullscreen = false }
|
||||
};
|
||||
if (auto ret = event_packet.send_serialized(m_focused_window->client_fd()); ret.is_error())
|
||||
dwarnln("could not send window fullscreen event: {}", ret.error());
|
||||
|
||||
m_state = State::Normal;
|
||||
invalidate(m_framebuffer.area());
|
||||
return;
|
||||
@@ -331,6 +344,12 @@ void WindowServer::on_window_set_fullscreen(int fd, const LibGUI::WindowPacket::
|
||||
m_non_full_screen_rect = old_area;
|
||||
}
|
||||
|
||||
auto event_packet = LibGUI::EventPacket::WindowFullscreenEvent {
|
||||
.event = { .fullscreen = true }
|
||||
};
|
||||
if (auto ret = event_packet.send_serialized(target_window->client_fd()); ret.is_error())
|
||||
dwarnln("could not send window fullscreen event: {}", ret.error());
|
||||
|
||||
m_state = State::Fullscreen;
|
||||
set_focused_window(target_window);
|
||||
invalidate(m_framebuffer.area());
|
||||
@@ -486,6 +505,12 @@ void WindowServer::on_key_event(LibInput::KeyEvent event)
|
||||
m_state = State::Fullscreen;
|
||||
}
|
||||
|
||||
auto event_packet = LibGUI::EventPacket::WindowFullscreenEvent {
|
||||
.event = { .fullscreen = (m_state == State::Fullscreen) }
|
||||
};
|
||||
if (auto ret = event_packet.send_serialized(m_focused_window->client_fd()); ret.is_error())
|
||||
dwarnln("could not send window fullscreen event: {}", ret.error());
|
||||
|
||||
invalidate(m_framebuffer.area());
|
||||
return;
|
||||
}
|
||||
|
||||
609
xbanan/Base.cpp
609
xbanan/Base.cpp
File diff suppressed because it is too large
Load Diff
@@ -33,6 +33,12 @@ banan_link_library(xbanan libdeflate)
|
||||
banan_link_library(xbanan libgui)
|
||||
banan_link_library(xbanan libinput)
|
||||
|
||||
target_compile_options(xbanan PRIVATE -Wall -Wextra -Wno-sign-compare -Wno-missing-field-initializers)
|
||||
target_compile_options(xbanan PRIVATE -Wall -Wextra)
|
||||
target_compile_options(xbanan PRIVATE
|
||||
-Wno-sign-compare
|
||||
-Wno-missing-field-initializers
|
||||
-Wno-unused-variable
|
||||
-Wno-unused-but-set-variable
|
||||
)
|
||||
|
||||
install(TARGETS xbanan OPTIONAL)
|
||||
|
||||
@@ -62,12 +62,12 @@ struct Object
|
||||
{
|
||||
bool mapped { false };
|
||||
bool focused { false };
|
||||
bool fullscreen { false };
|
||||
uint8_t depth { 0 };
|
||||
int32_t x { 0 };
|
||||
int32_t y { 0 };
|
||||
int32_t cursor_x { -1 };
|
||||
int32_t cursor_y { -1 };
|
||||
uint32_t event_mask { 0 };
|
||||
WINDOW parent;
|
||||
CURSOR cursor;
|
||||
CARD16 c_class;
|
||||
@@ -77,6 +77,8 @@ struct Object
|
||||
LibGUI::Texture
|
||||
> window;
|
||||
|
||||
BAN::HashMap<Client*, uint32_t> event_masks;
|
||||
|
||||
BAN::HashMap<ATOM, Property> properties;
|
||||
|
||||
LibGUI::Texture& texture()
|
||||
@@ -96,6 +98,9 @@ struct Object
|
||||
return window.get<BAN::UniqPtr<LibGUI::Window>>()->texture();
|
||||
ASSERT_NOT_REACHED();
|
||||
}
|
||||
|
||||
uint32_t full_event_mask() const;
|
||||
BAN::ErrorOr<void> send_event(xEvent event, uint32_t event_mask);
|
||||
};
|
||||
|
||||
struct Pixmap
|
||||
|
||||
@@ -207,7 +207,7 @@ BAN::ErrorOr<void> fill_poly(Client& client_info, BAN::ConstByteSpan packet)
|
||||
dprintln(" gc: {}", request.gc);
|
||||
dprintln(" shape: {}", request.shape);
|
||||
dprintln(" coordMode: {}", request.coordMode);
|
||||
|
||||
|
||||
auto [out_data_u32, out_w, out_h, _] = TRY(get_drawable_info(client_info, request.drawable, X_FillPoly));
|
||||
|
||||
const auto& gc = TRY_REF(get_gc(client_info, request.gc, X_FillPoly));
|
||||
@@ -268,7 +268,7 @@ BAN::ErrorOr<void> fill_poly(Client& client_info, BAN::ConstByteSpan packet)
|
||||
}
|
||||
|
||||
if (g_objects[request.drawable]->type == Object::Type::Window)
|
||||
invalidate_window(request.drawable, min_x, min_y, max_x - min_x + 1, max_y - min_y + 1);
|
||||
invalidate_window(request.drawable, min_x, min_y, max_x - min_x + 1, max_y - min_y + 1);
|
||||
|
||||
return {};
|
||||
}
|
||||
@@ -347,7 +347,7 @@ BAN::ErrorOr<void> poly_fill_arc(Client& client_info, BAN::ConstByteSpan packet)
|
||||
|
||||
const int32_t min_x = BAN::Math::max<int32_t>(0, arc.x);
|
||||
const int32_t min_y = BAN::Math::max<int32_t>(0, arc.y);
|
||||
|
||||
|
||||
const int32_t max_x = BAN::Math::min<int32_t>(out_w, arc.x + arc.width);
|
||||
const int32_t max_y = BAN::Math::min<int32_t>(out_h, arc.y + arc.height);
|
||||
|
||||
|
||||
@@ -144,7 +144,7 @@ BAN::ErrorOr<void> extension_glx(Client& client_info, BAN::ConstByteSpan packet)
|
||||
delete &TRY_REF(get_glx_context(request.context));
|
||||
client_info.objects.remove(request.context);
|
||||
g_objects.remove(request.context);
|
||||
|
||||
|
||||
break;
|
||||
}
|
||||
case X_GLXIsDirect:
|
||||
@@ -253,7 +253,7 @@ BAN::ErrorOr<void> extension_glx(Client& client_info, BAN::ConstByteSpan packet)
|
||||
.n = static_cast<CARD16>(string.size()),
|
||||
};
|
||||
TRY(encode(client_info.output_buffer, reply));
|
||||
|
||||
|
||||
TRY(encode(client_info.output_buffer, string));
|
||||
for (size_t i = 0; (string.size() + i) % 4; i++)
|
||||
TRY(encode(client_info.output_buffer, '\0'));
|
||||
@@ -289,7 +289,7 @@ BAN::ErrorOr<void> extension_glx(Client& client_info, BAN::ConstByteSpan packet)
|
||||
.numAttribs = attribs,
|
||||
};
|
||||
TRY(encode(client_info.output_buffer, reply));
|
||||
|
||||
|
||||
TRY(encode(client_info.output_buffer, g_fb_configs));
|
||||
|
||||
break;
|
||||
|
||||
@@ -10,7 +10,7 @@ static BAN::ErrorOr<void> extension_randr(Client& client_info, BAN::ConstByteSpa
|
||||
{
|
||||
static CARD32 crtc_id = 5;
|
||||
static CARD32 output_id = 6;
|
||||
static CARD32 mode_id = 7;
|
||||
static CARD32 mode_id = 7;
|
||||
static CARD32 timestamp = time(nullptr);
|
||||
|
||||
static xRenderTransform transform {
|
||||
|
||||
@@ -455,7 +455,7 @@ static void initialize_fonts()
|
||||
|
||||
auto it = s_available_fonts.find(BAN::String(name));
|
||||
if (it == s_available_fonts.end())
|
||||
continue;
|
||||
continue;
|
||||
|
||||
MUST(s_available_fonts.insert(BAN::String(alias), it->value));
|
||||
}
|
||||
@@ -756,7 +756,7 @@ static void write_text(WriteTextInfo& info)
|
||||
for (size_t i = 0; i < info.string_len; i++)
|
||||
{
|
||||
const uint16_t codepoint = info.wide ? (info.string[i * 2] << 8) | info.string[i * 2 + 1] : info.string[i];
|
||||
|
||||
|
||||
auto glyph_index = info.font->find_glyph(codepoint);
|
||||
if (!glyph_index.has_value())
|
||||
continue;
|
||||
|
||||
@@ -159,9 +159,9 @@ static constexpr uint32_t my_key_to_x_keysym(LibInput::Key key)
|
||||
case Key::Half:
|
||||
return XK_onehalf;
|
||||
case Key::OpenParenthesis:
|
||||
return ')';
|
||||
case Key::CloseParenthesis:
|
||||
return '(';
|
||||
case Key::CloseParenthesis:
|
||||
return ')';
|
||||
case Key::OpenSquareBracket:
|
||||
return '[';
|
||||
case Key::CloseSquareBracket:
|
||||
|
||||
@@ -180,8 +180,8 @@ int main()
|
||||
}
|
||||
|
||||
#define APPEND_ATOM(name) do { \
|
||||
MUST(g_atoms_id_to_name.insert(name, #name##_sv)); \
|
||||
MUST(g_atoms_name_to_id.insert(#name##_sv, name)); \
|
||||
MUST(g_atoms_id_to_name.insert(name, #name##_sv.substring(3))); \
|
||||
MUST(g_atoms_name_to_id.insert(#name##_sv.substring(3), name)); \
|
||||
} while (0)
|
||||
APPEND_ATOM(XA_PRIMARY);
|
||||
APPEND_ATOM(XA_SECONDARY);
|
||||
@@ -253,6 +253,17 @@ int main()
|
||||
APPEND_ATOM(XA_WM_TRANSIENT_FOR);
|
||||
#undef APPEND_ATOM
|
||||
|
||||
#define APPEND_ATOM_CUSTOM(name) do { \
|
||||
const CARD32 atom = g_atom_value++; \
|
||||
MUST(g_atoms_id_to_name.insert(atom, #name##_sv)); \
|
||||
MUST(g_atoms_name_to_id.insert(#name##_sv, atom)); \
|
||||
} while (0)
|
||||
APPEND_ATOM_CUSTOM(WM_PROTOCOLS);
|
||||
APPEND_ATOM_CUSTOM(WM_DELETE_WINDOW);
|
||||
APPEND_ATOM_CUSTOM(_NET_WM_STATE);
|
||||
APPEND_ATOM_CUSTOM(_NET_WM_STATE_FULLSCREEN);
|
||||
#undef APPEND_ATOM_CUSTOM
|
||||
|
||||
MUST(initialize_keymap());
|
||||
|
||||
printf("xbanan started\n");
|
||||
@@ -266,6 +277,16 @@ int main()
|
||||
|
||||
dprintln("client {} disconnected", client_fd);
|
||||
|
||||
// FIXME: store selected events on client so we dont
|
||||
// have to loop over all objects
|
||||
for (auto& [_, object] : g_objects)
|
||||
{
|
||||
if (object->type != Object::Type::Window)
|
||||
continue;
|
||||
auto& window = object->object.get<Object::Window>();
|
||||
window.event_masks.remove(&client_info);
|
||||
}
|
||||
|
||||
for (auto id : client_info.objects)
|
||||
{
|
||||
auto it = g_objects.find(id);
|
||||
@@ -321,7 +342,9 @@ int main()
|
||||
MUST(BAN::UniqPtr<Object>::create(Object {
|
||||
.type = Object::Type::Window,
|
||||
.object = Object::Window {
|
||||
.event_mask = 0,
|
||||
.mapped = true,
|
||||
.depth = g_root.rootDepth,
|
||||
.parent = None,
|
||||
.c_class = InputOutput,
|
||||
.window = {},
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user