summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndreas Kling <kling@serenityos.org>2020-07-24 01:03:24 +0200
committerAndreas Kling <kling@serenityos.org>2020-07-24 01:03:24 +0200
commita655cf5b414ba10a0bf5046a313771711fcceb64 (patch)
tree2b77b6d295e61c698e43702e859489be4942d828
parent3f45e9ab1ef560eb606ae03a18d6435b718d9982 (diff)
downloadserenity-a655cf5b414ba10a0bf5046a313771711fcceb64.zip
LibGUI: Break up Window::event() into many smaller functions
This function was unbearably huge. Handle each event type in its own function instead so you can see what's going on.
-rw-r--r--Libraries/LibGUI/Forward.h7
-rw-r--r--Libraries/LibGUI/Window.cpp338
-rw-r--r--Libraries/LibGUI/Window.h12
3 files changed, 202 insertions, 155 deletions
diff --git a/Libraries/LibGUI/Forward.h b/Libraries/LibGUI/Forward.h
index 43bbd7a217..55c1b166e2 100644
--- a/Libraries/LibGUI/Forward.h
+++ b/Libraries/LibGUI/Forward.h
@@ -38,6 +38,8 @@ class BoxLayout;
class Button;
class CheckBox;
class Command;
+class DragEvent;
+class DropEvent;
class FileSystemModel;
class Frame;
class GroupBox;
@@ -56,10 +58,12 @@ class Model;
class ModelEditingDelegate;
class ModelIndex;
class MouseEvent;
+class MultiPaintEvent;
class MultiView;
class PaintEvent;
class Painter;
class ResizeCorner;
+class ResizeEvent;
class ScrollBar;
class Slider;
class SortingProxyModel;
@@ -75,9 +79,10 @@ class TextDocument;
class TextDocumentLine;
class TextDocumentUndoCommand;
class TextEditor;
-class TreeView;
+class ThemeChangeEvent;
class ToolBar;
class ToolBarContainer;
+class TreeView;
class Variant;
class VerticalBoxLayout;
class VerticalSlider;
diff --git a/Libraries/LibGUI/Window.cpp b/Libraries/LibGUI/Window.cpp
index ce7685451b..30d4473de6 100644
--- a/Libraries/LibGUI/Window.cpp
+++ b/Libraries/LibGUI/Window.cpp
@@ -227,186 +227,217 @@ void Window::set_override_cursor(const Gfx::Bitmap& cursor)
WindowServerConnection::the().send_sync<Messages::WindowServer::SetWindowCustomOverrideCursor>(m_window_id, m_custom_cursor->to_shareable_bitmap(WindowServerConnection::the().server_pid()));
}
-void Window::event(Core::Event& event)
+void Window::handle_drop_event(DropEvent& event)
{
- if (event.type() == Event::Drop) {
- auto& drop_event = static_cast<DropEvent&>(event);
- if (!m_main_widget)
- return;
- auto result = m_main_widget->hit_test(drop_event.position());
- auto local_event = make<DropEvent>(result.local_position, drop_event.text(), drop_event.mime_data());
- ASSERT(result.widget);
- return result.widget->dispatch_event(*local_event, this);
- }
+ if (!m_main_widget)
+ return;
+ auto result = m_main_widget->hit_test(event.position());
+ auto local_event = make<DropEvent>(result.local_position, event.text(), event.mime_data());
+ ASSERT(result.widget);
+ return result.widget->dispatch_event(*local_event, this);
+}
- if (event.type() == Event::MouseUp || event.type() == Event::MouseDown || event.type() == Event::MouseDoubleClick || event.type() == Event::MouseMove || event.type() == Event::MouseWheel) {
- auto& mouse_event = static_cast<MouseEvent&>(event);
- if (m_global_cursor_tracking_widget) {
- auto window_relative_rect = m_global_cursor_tracking_widget->window_relative_rect();
- Gfx::IntPoint local_point { mouse_event.x() - window_relative_rect.x(), mouse_event.y() - window_relative_rect.y() };
- auto local_event = make<MouseEvent>((Event::Type)event.type(), local_point, mouse_event.buttons(), mouse_event.button(), mouse_event.modifiers(), mouse_event.wheel_delta());
- m_global_cursor_tracking_widget->dispatch_event(*local_event, this);
- return;
- }
- if (m_automatic_cursor_tracking_widget) {
- auto window_relative_rect = m_automatic_cursor_tracking_widget->window_relative_rect();
- Gfx::IntPoint local_point { mouse_event.x() - window_relative_rect.x(), mouse_event.y() - window_relative_rect.y() };
- auto local_event = make<MouseEvent>((Event::Type)event.type(), local_point, mouse_event.buttons(), mouse_event.button(), mouse_event.modifiers(), mouse_event.wheel_delta());
- m_automatic_cursor_tracking_widget->dispatch_event(*local_event, this);
- if (mouse_event.buttons() == 0)
- m_automatic_cursor_tracking_widget = nullptr;
- return;
- }
- if (!m_main_widget)
- return;
- auto result = m_main_widget->hit_test(mouse_event.position());
- auto local_event = make<MouseEvent>((Event::Type)event.type(), result.local_position, mouse_event.buttons(), mouse_event.button(), mouse_event.modifiers(), mouse_event.wheel_delta());
- ASSERT(result.widget);
- set_hovered_widget(result.widget);
- if (mouse_event.buttons() != 0 && !m_automatic_cursor_tracking_widget)
- m_automatic_cursor_tracking_widget = result.widget->make_weak_ptr();
- if (result.widget != m_global_cursor_tracking_widget.ptr())
- return result.widget->dispatch_event(*local_event, this);
+void Window::handle_mouse_event(MouseEvent& event)
+{
+ if (m_global_cursor_tracking_widget) {
+ auto window_relative_rect = m_global_cursor_tracking_widget->window_relative_rect();
+ Gfx::IntPoint local_point { event.x() - window_relative_rect.x(), event.y() - window_relative_rect.y() };
+ auto local_event = make<MouseEvent>((Event::Type)event.type(), local_point, event.buttons(), event.button(), event.modifiers(), event.wheel_delta());
+ m_global_cursor_tracking_widget->dispatch_event(*local_event, this);
return;
}
+ if (m_automatic_cursor_tracking_widget) {
+ auto window_relative_rect = m_automatic_cursor_tracking_widget->window_relative_rect();
+ Gfx::IntPoint local_point { event.x() - window_relative_rect.x(), event.y() - window_relative_rect.y() };
+ auto local_event = make<MouseEvent>((Event::Type)event.type(), local_point, event.buttons(), event.button(), event.modifiers(), event.wheel_delta());
+ m_automatic_cursor_tracking_widget->dispatch_event(*local_event, this);
+ if (event.buttons() == 0)
+ m_automatic_cursor_tracking_widget = nullptr;
+ return;
+ }
+ if (!m_main_widget)
+ return;
+ auto result = m_main_widget->hit_test(event.position());
+ auto local_event = make<MouseEvent>((Event::Type)event.type(), result.local_position, event.buttons(), event.button(), event.modifiers(), event.wheel_delta());
+ ASSERT(result.widget);
+ set_hovered_widget(result.widget);
+ if (event.buttons() != 0 && !m_automatic_cursor_tracking_widget)
+ m_automatic_cursor_tracking_widget = result.widget->make_weak_ptr();
+ if (result.widget != m_global_cursor_tracking_widget.ptr())
+ return result.widget->dispatch_event(*local_event, this);
+ return;
+}
- if (event.type() == Event::MultiPaint) {
- if (!is_visible())
- return;
- if (!m_main_widget)
- return;
- auto& paint_event = static_cast<MultiPaintEvent&>(event);
- auto rects = paint_event.rects();
- ASSERT(!rects.is_empty());
- if (m_back_bitmap && m_back_bitmap->size() != paint_event.window_size()) {
- // Eagerly discard the backing store if we learn from this paint event that it needs to be bigger.
- // Otherwise we would have to wait for a resize event to tell us. This way we don't waste the
- // effort on painting into an undersized bitmap that will be thrown away anyway.
- m_back_bitmap = nullptr;
- }
- bool created_new_backing_store = !m_back_bitmap;
- if (!m_back_bitmap) {
- m_back_bitmap = create_backing_bitmap(paint_event.window_size());
+void Window::handle_multi_paint_event(MultiPaintEvent& event)
+{
+ if (!is_visible())
+ return;
+ if (!m_main_widget)
+ return;
+ auto rects = event.rects();
+ ASSERT(!rects.is_empty());
+ if (m_back_bitmap && m_back_bitmap->size() != event.window_size()) {
+ // Eagerly discard the backing store if we learn from this paint event that it needs to be bigger.
+ // Otherwise we would have to wait for a resize event to tell us. This way we don't waste the
+ // effort on painting into an undersized bitmap that will be thrown away anyway.
+ m_back_bitmap = nullptr;
+ }
+ bool created_new_backing_store = !m_back_bitmap;
+ if (!m_back_bitmap) {
+ m_back_bitmap = create_backing_bitmap(event.window_size());
+ ASSERT(m_back_bitmap);
+ } else if (m_double_buffering_enabled) {
+ bool still_has_pixels = m_back_bitmap->shared_buffer()->set_nonvolatile();
+ if (!still_has_pixels) {
+ m_back_bitmap = create_backing_bitmap(event.window_size());
ASSERT(m_back_bitmap);
- } else if (m_double_buffering_enabled) {
- bool still_has_pixels = m_back_bitmap->shared_buffer()->set_nonvolatile();
- if (!still_has_pixels) {
- m_back_bitmap = create_backing_bitmap(paint_event.window_size());
- ASSERT(m_back_bitmap);
- created_new_backing_store = true;
- }
+ created_new_backing_store = true;
}
+ }
- auto rect = rects.first();
- if (rect.is_empty() || created_new_backing_store) {
- rects.clear();
- rects.append({ {}, paint_event.window_size() });
- }
+ auto rect = rects.first();
+ if (rect.is_empty() || created_new_backing_store) {
+ rects.clear();
+ rects.append({ {}, event.window_size() });
+ }
- for (auto& rect : rects) {
- PaintEvent paint_event(rect);
- m_main_widget->dispatch_event(paint_event, this);
- }
+ for (auto& rect : rects) {
+ PaintEvent paint_event(rect);
+ m_main_widget->dispatch_event(paint_event, this);
+ }
- if (m_double_buffering_enabled)
- flip(rects);
- else if (created_new_backing_store)
- set_current_backing_bitmap(*m_back_bitmap, true);
+ if (m_double_buffering_enabled)
+ flip(rects);
+ else if (created_new_backing_store)
+ set_current_backing_bitmap(*m_back_bitmap, true);
- if (is_visible()) {
- Vector<Gfx::IntRect> rects_to_send;
- for (auto& r : rects)
- rects_to_send.append(r);
- WindowServerConnection::the().post_message(Messages::WindowServer::DidFinishPainting(m_window_id, rects_to_send));
- }
- return;
+ if (is_visible()) {
+ Vector<Gfx::IntRect> rects_to_send;
+ for (auto& r : rects)
+ rects_to_send.append(r);
+ WindowServerConnection::the().post_message(Messages::WindowServer::DidFinishPainting(m_window_id, rects_to_send));
}
+}
- if (event.type() == Event::KeyUp || event.type() == Event::KeyDown) {
- if (m_focused_widget)
- return m_focused_widget->dispatch_event(event, this);
- if (m_main_widget)
- return m_main_widget->dispatch_event(event, this);
- return;
- }
+void Window::handle_key_event(KeyEvent& event)
+{
+ if (m_focused_widget)
+ return m_focused_widget->dispatch_event(event, this);
+ if (m_main_widget)
+ return m_main_widget->dispatch_event(event, this);
+}
- if (event.type() == Event::WindowBecameActive || event.type() == Event::WindowBecameInactive) {
- m_is_active = event.type() == Event::WindowBecameActive;
- if (on_activity_change)
- on_activity_change(m_is_active);
- if (m_main_widget)
- m_main_widget->dispatch_event(event, this);
- if (m_focused_widget)
- m_focused_widget->update();
- return;
+void Window::handle_resize_event(ResizeEvent& event)
+{
+ auto new_size = event.size();
+ if (m_back_bitmap && m_back_bitmap->size() != new_size)
+ m_back_bitmap = nullptr;
+ if (!m_pending_paint_event_rects.is_empty()) {
+ m_pending_paint_event_rects.clear_with_capacity();
+ m_pending_paint_event_rects.append({ {}, new_size });
}
+ m_rect_when_windowless = { {}, new_size };
+ m_main_widget->set_relative_rect({ {}, new_size });
+}
- if (event.type() == Event::WindowInputEntered || event.type() == Event::WindowInputLeft) {
- m_is_active_input = event.type() == Event::WindowInputEntered;
- if (on_active_input_change)
- on_active_input_change(m_is_active_input);
- if (m_main_widget)
- m_main_widget->dispatch_event(event, this);
- if (m_focused_widget)
- m_focused_widget->update();
- return;
- }
+void Window::handle_input_entered_or_left_event(Core::Event& event)
+{
+ m_is_active_input = event.type() == Event::WindowInputEntered;
+ if (on_active_input_change)
+ on_active_input_change(m_is_active_input);
+ if (m_main_widget)
+ m_main_widget->dispatch_event(event, this);
+ if (m_focused_widget)
+ m_focused_widget->update();
+}
- if (event.type() == Event::WindowCloseRequest) {
- if (on_close_request) {
- if (on_close_request() == Window::CloseRequestDecision::StayOpen)
- return;
- }
- close();
- return;
+void Window::handle_became_active_or_inactive_event(Core::Event& event)
+{
+ m_is_active = event.type() == Event::WindowBecameActive;
+ if (on_activity_change)
+ on_activity_change(m_is_active);
+ if (m_main_widget)
+ m_main_widget->dispatch_event(event, this);
+ if (m_focused_widget)
+ m_focused_widget->update();
+}
+
+void Window::handle_close_request()
+{
+ if (on_close_request) {
+ if (on_close_request() == Window::CloseRequestDecision::StayOpen)
+ return;
}
+ close();
+}
- if (event.type() == Event::WindowLeft) {
- set_hovered_widget(nullptr);
+void Window::handle_theme_change_event(ThemeChangeEvent& event)
+{
+ if (!m_main_widget)
return;
- }
+ auto dispatch_theme_change = [&](auto& widget, auto recursive) {
+ widget.dispatch_event(event, this);
+ widget.for_each_child_widget([&](auto& widget) -> IterationDecision {
+ widget.dispatch_event(event, this);
+ recursive(widget, recursive);
+ return IterationDecision::Continue;
+ });
+ };
+ dispatch_theme_change(*m_main_widget.ptr(), dispatch_theme_change);
+}
- if (event.type() == Event::Resize) {
- auto new_size = static_cast<ResizeEvent&>(event).size();
- if (m_back_bitmap && m_back_bitmap->size() != new_size)
- m_back_bitmap = nullptr;
- if (!m_pending_paint_event_rects.is_empty()) {
- m_pending_paint_event_rects.clear_with_capacity();
- m_pending_paint_event_rects.append({ {}, new_size });
- }
- m_rect_when_windowless = { {}, new_size };
- m_main_widget->set_relative_rect({ {}, new_size });
+void Window::handle_drag_move_event(DragEvent& event)
+{
+ if (!m_main_widget)
return;
- }
+ auto result = m_main_widget->hit_test(event.position());
+ auto local_event = make<DragEvent>(static_cast<Event::Type>(event.type()), result.local_position, event.data_type());
+ ASSERT(result.widget);
+ return result.widget->dispatch_event(*local_event, this);
+}
+
+void Window::handle_left_event()
+{
+ set_hovered_widget(nullptr);
+}
+
+void Window::event(Core::Event& event)
+{
+ if (event.type() == Event::Drop)
+ return handle_drop_event(static_cast<DropEvent&>(event));
+
+ if (event.type() == Event::MouseUp || event.type() == Event::MouseDown || event.type() == Event::MouseDoubleClick || event.type() == Event::MouseMove || event.type() == Event::MouseWheel)
+ return handle_mouse_event(static_cast<MouseEvent&>(event));
+
+ if (event.type() == Event::MultiPaint)
+ return handle_multi_paint_event(static_cast<MultiPaintEvent&>(event));
+
+ if (event.type() == Event::KeyUp || event.type() == Event::KeyDown)
+ return handle_key_event(static_cast<KeyEvent&>(event));
+
+ if (event.type() == Event::WindowBecameActive || event.type() == Event::WindowBecameInactive)
+ return handle_became_active_or_inactive_event(event);
+
+ if (event.type() == Event::WindowInputEntered || event.type() == Event::WindowInputLeft)
+ return handle_input_entered_or_left_event(event);
+
+ if (event.type() == Event::WindowCloseRequest)
+ return handle_close_request();
+
+ if (event.type() == Event::WindowLeft)
+ return handle_left_event();
+
+ if (event.type() == Event::Resize)
+ return handle_resize_event(static_cast<ResizeEvent&>(event));
if (event.type() > Event::__Begin_WM_Events && event.type() < Event::__End_WM_Events)
return wm_event(static_cast<WMEvent&>(event));
- if (event.type() == Event::DragMove) {
- if (!m_main_widget)
- return;
- auto& drag_event = static_cast<DragEvent&>(event);
- auto result = m_main_widget->hit_test(drag_event.position());
- auto local_event = make<DragEvent>(static_cast<Event::Type>(drag_event.type()), result.local_position, drag_event.data_type());
- ASSERT(result.widget);
- return result.widget->dispatch_event(*local_event, this);
- }
+ if (event.type() == Event::DragMove)
+ return handle_drag_move_event(static_cast<DragEvent&>(event));
- if (event.type() == Event::ThemeChange) {
- if (!m_main_widget)
- return;
- auto theme_event = static_cast<ThemeChangeEvent&>(event);
- auto dispatch_theme_change = [&](auto& widget, auto recursive) {
- widget.dispatch_event(theme_event, this);
- widget.for_each_child_widget([&](auto& widget) -> IterationDecision {
- widget.dispatch_event(theme_event, this);
- recursive(widget, recursive);
- return IterationDecision::Continue;
- });
- };
- dispatch_theme_change(*m_main_widget.ptr(), dispatch_theme_change);
- return;
- }
+ if (event.type() == Event::ThemeChange)
+ return handle_theme_change_event(static_cast<ThemeChangeEvent&>(event));
Core::Object::event(event);
}
@@ -810,5 +841,4 @@ void Window::set_progress(int progress)
ASSERT(m_window_id);
WindowServerConnection::the().post_message(Messages::WindowServer::SetWindowProgress(m_window_id, progress));
}
-
}
diff --git a/Libraries/LibGUI/Window.h b/Libraries/LibGUI/Window.h
index 2b505b6b02..b6e8688978 100644
--- a/Libraries/LibGUI/Window.h
+++ b/Libraries/LibGUI/Window.h
@@ -209,6 +209,18 @@ protected:
private:
virtual bool is_window() const override final { return true; }
+ void handle_drop_event(DropEvent&);
+ void handle_mouse_event(MouseEvent&);
+ void handle_multi_paint_event(MultiPaintEvent&);
+ void handle_key_event(KeyEvent&);
+ void handle_resize_event(ResizeEvent&);
+ void handle_input_entered_or_left_event(Core::Event&);
+ void handle_became_active_or_inactive_event(Core::Event&);
+ void handle_close_request();
+ void handle_theme_change_event(ThemeChangeEvent&);
+ void handle_drag_move_event(DragEvent&);
+ void handle_left_event();
+
void server_did_destroy();
RefPtr<Gfx::Bitmap> create_backing_bitmap(const Gfx::IntSize&);