mirror of
https://github.com/RGBCube/serenity
synced 2025-07-24 22:17:42 +00:00
WindowServer: Clean up any menu objects on process exit.
..and now that this works, implement the Quit menu action in Terminal. :^)
This commit is contained in:
parent
f311d0f353
commit
4b8133e925
10 changed files with 76 additions and 16 deletions
|
@ -76,22 +76,29 @@ int main(int argc, char** argv)
|
||||||
auto menubar = make<GMenuBar>();
|
auto menubar = make<GMenuBar>();
|
||||||
|
|
||||||
auto app_menu = make<GMenu>("Terminal");
|
auto app_menu = make<GMenu>("Terminal");
|
||||||
app_menu->add_item(1, "Quit");
|
app_menu->add_item(0, "Quit");
|
||||||
|
app_menu->on_item_activation = [] (unsigned identifier) {
|
||||||
|
if (identifier == 0) {
|
||||||
|
dbgprintf("Terminal: Quit menu activated!\n");
|
||||||
|
GApplication::the().exit(0);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
};
|
||||||
menubar->add_menu(move(app_menu));
|
menubar->add_menu(move(app_menu));
|
||||||
|
|
||||||
auto font_menu = make<GMenu>("Font");
|
auto font_menu = make<GMenu>("Font");
|
||||||
font_menu->add_item(30, "Liza Thin");
|
font_menu->add_item(0, "Liza Thin");
|
||||||
font_menu->add_item(31, "Liza Regular");
|
font_menu->add_item(1, "Liza Regular");
|
||||||
font_menu->add_item(32, "Liza Bold");
|
font_menu->add_item(2, "Liza Bold");
|
||||||
font_menu->on_item_activation = [&terminal] (unsigned identifier) {
|
font_menu->on_item_activation = [&terminal] (unsigned identifier) {
|
||||||
switch (identifier) {
|
switch (identifier) {
|
||||||
case 30:
|
case 0:
|
||||||
terminal.set_font(Font::load_from_file("/res/fonts/Liza8x10.font"));
|
terminal.set_font(Font::load_from_file("/res/fonts/Liza8x10.font"));
|
||||||
break;
|
break;
|
||||||
case 31:
|
case 1:
|
||||||
terminal.set_font(Font::load_from_file("/res/fonts/LizaRegular8x10.font"));
|
terminal.set_font(Font::load_from_file("/res/fonts/LizaRegular8x10.font"));
|
||||||
break;
|
break;
|
||||||
case 32:
|
case 2:
|
||||||
terminal.set_font(Font::load_from_file("/res/fonts/LizaBold8x10.font"));
|
terminal.set_font(Font::load_from_file("/res/fonts/LizaBold8x10.font"));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -100,7 +107,7 @@ int main(int argc, char** argv)
|
||||||
menubar->add_menu(move(font_menu));
|
menubar->add_menu(move(font_menu));
|
||||||
|
|
||||||
auto help_menu = make<GMenu>("Help");
|
auto help_menu = make<GMenu>("Help");
|
||||||
help_menu->add_item(2, "About");
|
help_menu->add_item(0, "About");
|
||||||
menubar->add_menu(move(help_menu));
|
menubar->add_menu(move(help_menu));
|
||||||
|
|
||||||
app.set_menubar(move(menubar));
|
app.set_menubar(move(menubar));
|
||||||
|
|
|
@ -2133,6 +2133,7 @@ void Process::finalize()
|
||||||
{
|
{
|
||||||
ASSERT(current == g_finalizer);
|
ASSERT(current == g_finalizer);
|
||||||
|
|
||||||
|
destroy_all_menus();
|
||||||
destroy_all_windows();
|
destroy_all_windows();
|
||||||
m_fds.clear();
|
m_fds.clear();
|
||||||
m_tty = nullptr;
|
m_tty = nullptr;
|
||||||
|
|
|
@ -244,6 +244,7 @@ public:
|
||||||
static void initialize();
|
static void initialize();
|
||||||
static void initialize_gui_statics();
|
static void initialize_gui_statics();
|
||||||
int make_window_id();
|
int make_window_id();
|
||||||
|
void destroy_all_menus();
|
||||||
void destroy_all_windows();
|
void destroy_all_windows();
|
||||||
|
|
||||||
void crash() NORETURN;
|
void crash() NORETURN;
|
||||||
|
@ -419,6 +420,7 @@ private:
|
||||||
Vector<GUI_Event> m_gui_events;
|
Vector<GUI_Event> m_gui_events;
|
||||||
Lock m_gui_events_lock;
|
Lock m_gui_events_lock;
|
||||||
int m_next_window_id { 1 };
|
int m_next_window_id { 1 };
|
||||||
|
bool m_has_created_menus { false };
|
||||||
|
|
||||||
dword m_wakeup_requested { false };
|
dword m_wakeup_requested { false };
|
||||||
bool m_has_used_fpu { false };
|
bool m_has_used_fpu { false };
|
||||||
|
|
|
@ -257,6 +257,13 @@ int Process::gui$set_global_cursor_tracking_enabled(int window_id, bool enabled)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Process::destroy_all_menus()
|
||||||
|
{
|
||||||
|
if (!m_has_created_menus)
|
||||||
|
return;
|
||||||
|
WSWindowManager::the().destroy_all_menus(*this);
|
||||||
|
}
|
||||||
|
|
||||||
void Process::destroy_all_windows()
|
void Process::destroy_all_windows()
|
||||||
{
|
{
|
||||||
for (auto& it : m_windows) {
|
for (auto& it : m_windows) {
|
||||||
|
@ -267,7 +274,6 @@ void Process::destroy_all_windows()
|
||||||
m_windows.clear();
|
m_windows.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
DisplayInfo Process::set_video_resolution(int width, int height)
|
DisplayInfo Process::set_video_resolution(int width, int height)
|
||||||
{
|
{
|
||||||
DisplayInfo info;
|
DisplayInfo info;
|
||||||
|
@ -288,6 +294,7 @@ DisplayInfo Process::set_video_resolution(int width, int height)
|
||||||
|
|
||||||
int Process::gui$menubar_create()
|
int Process::gui$menubar_create()
|
||||||
{
|
{
|
||||||
|
m_has_created_menus = true;
|
||||||
return WSWindowManager::the().api$menubar_create();
|
return WSWindowManager::the().api$menubar_create();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -305,6 +312,7 @@ int Process::gui$menu_create(const char* name)
|
||||||
{
|
{
|
||||||
if (!validate_read_str(name))
|
if (!validate_read_str(name))
|
||||||
return -EFAULT;
|
return -EFAULT;
|
||||||
|
m_has_created_menus = true;
|
||||||
return WSWindowManager::the().api$menu_create(String(name));
|
return WSWindowManager::the().api$menu_create(String(name));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -7,6 +7,10 @@ GMenuBar::GMenuBar()
|
||||||
|
|
||||||
GMenuBar::~GMenuBar()
|
GMenuBar::~GMenuBar()
|
||||||
{
|
{
|
||||||
|
if (m_menubar_id) {
|
||||||
|
gui_menubar_destroy(m_menubar_id);
|
||||||
|
m_menubar_id = 0;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void GMenuBar::add_menu(OwnPtr<GMenu>&& menu)
|
void GMenuBar::add_menu(OwnPtr<GMenu>&& menu)
|
||||||
|
|
|
@ -18,6 +18,7 @@ public:
|
||||||
~WSMenu();
|
~WSMenu();
|
||||||
|
|
||||||
int menu_id() const { return m_menu_id; }
|
int menu_id() const { return m_menu_id; }
|
||||||
|
const Process* process() const { return m_process.ptr(); }
|
||||||
|
|
||||||
WSMenuBar* menu_bar() { return m_menubar; }
|
WSMenuBar* menu_bar() { return m_menubar; }
|
||||||
const WSMenuBar* menu_bar() const { return m_menubar; }
|
const WSMenuBar* menu_bar() const { return m_menubar; }
|
||||||
|
|
|
@ -3,8 +3,9 @@
|
||||||
#include "WSMenuItem.h"
|
#include "WSMenuItem.h"
|
||||||
#include <Kernel/Process.h>
|
#include <Kernel/Process.h>
|
||||||
|
|
||||||
WSMenuBar::WSMenuBar(Process& process)
|
WSMenuBar::WSMenuBar(int menubar_id, Process& process)
|
||||||
: m_process(process.make_weak_ptr())
|
: m_menubar_id(menubar_id)
|
||||||
|
, m_process(process.make_weak_ptr())
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -8,9 +8,11 @@ class Process;
|
||||||
|
|
||||||
class WSMenuBar {
|
class WSMenuBar {
|
||||||
public:
|
public:
|
||||||
explicit WSMenuBar(Process&);
|
WSMenuBar(int menubar_id, Process&);
|
||||||
~WSMenuBar();
|
~WSMenuBar();
|
||||||
|
|
||||||
|
int menubar_id() const { return m_menubar_id; }
|
||||||
|
const Process* process() const { return m_process.ptr(); }
|
||||||
void add_menu(WSMenu* menu) { m_menus.append(menu); }
|
void add_menu(WSMenu* menu) { m_menus.append(menu); }
|
||||||
|
|
||||||
template<typename Callback>
|
template<typename Callback>
|
||||||
|
@ -23,6 +25,7 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
int m_menubar_id { 0 };
|
||||||
WeakPtr<Process> m_process;
|
WeakPtr<Process> m_process;
|
||||||
Vector<WSMenu*> m_menus;
|
Vector<WSMenu*> m_menus;
|
||||||
};
|
};
|
||||||
|
|
|
@ -761,8 +761,8 @@ void WSWindowManager::flush(const Rect& a_rect)
|
||||||
void WSWindowManager::close_menu(WSMenu& menu)
|
void WSWindowManager::close_menu(WSMenu& menu)
|
||||||
{
|
{
|
||||||
LOCKER(m_lock);
|
LOCKER(m_lock);
|
||||||
ASSERT(m_current_menu == &menu);
|
if (m_current_menu == &menu)
|
||||||
close_current_menu();
|
close_current_menu();
|
||||||
}
|
}
|
||||||
|
|
||||||
WSMenu& WSWindowManager::create_menu(String&& name)
|
WSMenu& WSWindowManager::create_menu(String&& name)
|
||||||
|
@ -779,8 +779,8 @@ WSMenu& WSWindowManager::create_menu(String&& name)
|
||||||
int WSWindowManager::api$menubar_create()
|
int WSWindowManager::api$menubar_create()
|
||||||
{
|
{
|
||||||
LOCKER(m_lock);
|
LOCKER(m_lock);
|
||||||
auto menubar = make<WSMenuBar>(*current);
|
|
||||||
int menubar_id = m_next_menubar_id++;
|
int menubar_id = m_next_menubar_id++;
|
||||||
|
auto menubar = make<WSMenuBar>(menubar_id, *current);
|
||||||
m_menubars.set(menubar_id, move(menubar));
|
m_menubars.set(menubar_id, move(menubar));
|
||||||
return menubar_id;
|
return menubar_id;
|
||||||
}
|
}
|
||||||
|
@ -793,7 +793,7 @@ int WSWindowManager::api$menubar_destroy(int menubar_id)
|
||||||
return -EBADMENUBAR;
|
return -EBADMENUBAR;
|
||||||
auto& menubar = *(*it).value;
|
auto& menubar = *(*it).value;
|
||||||
if (&menubar == m_current_menubar)
|
if (&menubar == m_current_menubar)
|
||||||
ASSERT_NOT_REACHED();
|
set_current_menubar(nullptr);
|
||||||
m_menubars.remove(it);
|
m_menubars.remove(it);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -827,6 +827,8 @@ int WSWindowManager::api$menu_destroy(int menu_id)
|
||||||
auto it = m_menus.find(menu_id);
|
auto it = m_menus.find(menu_id);
|
||||||
if (it == m_menus.end())
|
if (it == m_menus.end())
|
||||||
return -EBADMENU;
|
return -EBADMENU;
|
||||||
|
auto& menu = *(*it).value;
|
||||||
|
close_menu(menu);
|
||||||
m_menus.remove(it);
|
m_menus.remove(it);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -868,3 +870,33 @@ int WSWindowManager::api$app_set_menubar(int menubar_id)
|
||||||
invalidate();
|
invalidate();
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void WSWindowManager::destroy_all_menus(Process& process)
|
||||||
|
{
|
||||||
|
LOCKER(m_lock);
|
||||||
|
Vector<int> menu_ids;
|
||||||
|
bool should_close_current_menu = false;
|
||||||
|
for (auto& it : m_menus) {
|
||||||
|
if (it.value->process() == &process)
|
||||||
|
menu_ids.append(it.value->menu_id());
|
||||||
|
if (m_current_menu == it.value.ptr())
|
||||||
|
should_close_current_menu = true;
|
||||||
|
}
|
||||||
|
if (should_close_current_menu)
|
||||||
|
close_current_menu();
|
||||||
|
for (int menu_id : menu_ids)
|
||||||
|
m_menus.remove(menu_id);
|
||||||
|
|
||||||
|
Vector<int> menubar_ids;
|
||||||
|
bool should_close_current_menubar = false;
|
||||||
|
for (auto& it : m_menubars) {
|
||||||
|
if (it.value->process() == &process)
|
||||||
|
menubar_ids.append(it.value->menubar_id());
|
||||||
|
if (m_current_menubar == it.value.ptr())
|
||||||
|
should_close_current_menubar = true;
|
||||||
|
}
|
||||||
|
if (should_close_current_menubar)
|
||||||
|
set_current_menubar(nullptr);
|
||||||
|
for (int menubar_id : menubar_ids)
|
||||||
|
m_menubars.remove(menubar_id);
|
||||||
|
}
|
||||||
|
|
|
@ -62,6 +62,7 @@ public:
|
||||||
int api$menu_add_separator(int menu_id);
|
int api$menu_add_separator(int menu_id);
|
||||||
int api$menu_add_item(int menu_id, unsigned identifier, String&& text);
|
int api$menu_add_item(int menu_id, unsigned identifier, String&& text);
|
||||||
int api$app_set_menubar(int menubar_id);
|
int api$app_set_menubar(int menubar_id);
|
||||||
|
void destroy_all_menus(Process&);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
WSWindowManager();
|
WSWindowManager();
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue