Serenity Operating System
at hosted 133 lines 4.0 kB view raw
1/* 2 * Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org> 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright notice, this 9 * list of conditions and the following disclaimer. 10 * 11 * 2. Redistributions in binary form must reproduce the above copyright notice, 12 * this list of conditions and the following disclaimer in the documentation 13 * and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 16 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 18 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE 19 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 20 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 21 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 22 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 23 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 24 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 25 */ 26 27#pragma once 28 29#include <AK/HashTable.h> 30#include <LibGUI/ScrollableWidget.h> 31 32class FormWidget; 33class Tool; 34class WidgetTreeModel; 35 36class FormEditorWidget final : public GUI::ScrollableWidget { 37 C_OBJECT(FormEditorWidget) 38public: 39 virtual ~FormEditorWidget() override; 40 41 FormWidget& form_widget() { return *m_form_widget; } 42 const FormWidget& form_widget() const { return *m_form_widget; } 43 44 Tool& tool() { return *m_tool; } 45 const Tool& tool() const { return *m_tool; } 46 47 void set_tool(NonnullOwnPtr<Tool>); 48 49 WidgetTreeModel& model(); 50 51 class WidgetSelection { 52 public: 53 Function<void(GUI::Widget&)> on_remove; 54 Function<void(GUI::Widget&)> on_add; 55 Function<void()> on_clear; 56 57 void enable_hooks() { m_hooks_enabled = true; } 58 void disable_hooks() { m_hooks_enabled = false; } 59 60 bool is_empty() const 61 { 62 return m_widgets.is_empty(); 63 } 64 65 bool contains(GUI::Widget& widget) const 66 { 67 return m_widgets.contains(&widget); 68 } 69 70 void toggle(GUI::Widget& widget) 71 { 72 if (contains(widget)) 73 remove(widget); 74 else 75 add(widget); 76 } 77 78 void set(GUI::Widget& widget) 79 { 80 clear(); 81 add(widget); 82 } 83 84 void remove(GUI::Widget& widget) 85 { 86 ASSERT(m_widgets.contains(&widget)); 87 m_widgets.remove(&widget); 88 if (m_hooks_enabled && on_remove) 89 on_remove(widget); 90 } 91 92 void add(GUI::Widget& widget) 93 { 94 m_widgets.set(&widget); 95 if (m_hooks_enabled && on_add) 96 on_add(widget); 97 } 98 99 void clear() 100 { 101 m_widgets.clear(); 102 if (m_hooks_enabled && on_clear) 103 on_clear(); 104 } 105 106 template<typename Callback> 107 void for_each(Callback callback) 108 { 109 for (auto& it : m_widgets) { 110 if (callback(*it) == IterationDecision::Break) 111 break; 112 } 113 } 114 115 WidgetSelection() {} 116 117 private: 118 HashTable<GUI::Widget*> m_widgets; 119 bool m_hooks_enabled { true }; 120 }; 121 122 WidgetSelection& selection() { return m_selection; } 123 124private: 125 virtual void paint_event(GUI::PaintEvent&) override; 126 127 FormEditorWidget(); 128 129 RefPtr<FormWidget> m_form_widget; 130 RefPtr<WidgetTreeModel> m_widget_tree_model; 131 NonnullOwnPtr<Tool> m_tool; 132 WidgetSelection m_selection; 133};