mirror of
https://github.com/RGBCube/serenity
synced 2025-05-25 20:55:07 +00:00
WindowServer/GMenu: Adjust the popup position to fit the window inside the screen
Rather than passing a "top_anchored" bool. Fixes #22.
This commit is contained in:
parent
a4b0dfff43
commit
f55965b5e8
9 changed files with 20 additions and 17 deletions
|
@ -27,7 +27,7 @@ TaskbarButton::~TaskbarButton()
|
||||||
|
|
||||||
void TaskbarButton::context_menu_event(GContextMenuEvent&)
|
void TaskbarButton::context_menu_event(GContextMenuEvent&)
|
||||||
{
|
{
|
||||||
ensure_menu().popup(screen_relative_rect().location(), /* top_anchored */ false);
|
ensure_menu().popup(screen_relative_rect().location());
|
||||||
}
|
}
|
||||||
|
|
||||||
GMenu& TaskbarButton::ensure_menu()
|
GMenu& TaskbarButton::ensure_menu()
|
||||||
|
|
|
@ -39,7 +39,7 @@ void GMenu::add_separator()
|
||||||
m_items.append(make<GMenuItem>(m_menu_id, GMenuItem::Separator));
|
m_items.append(make<GMenuItem>(m_menu_id, GMenuItem::Separator));
|
||||||
}
|
}
|
||||||
|
|
||||||
void GMenu::popup(const Point& screen_position, bool top_anchored)
|
void GMenu::popup(const Point& screen_position)
|
||||||
{
|
{
|
||||||
if (!m_menu_id)
|
if (!m_menu_id)
|
||||||
realize_menu();
|
realize_menu();
|
||||||
|
@ -47,7 +47,6 @@ void GMenu::popup(const Point& screen_position, bool top_anchored)
|
||||||
request.type = WSAPI_ClientMessage::Type::PopupMenu;
|
request.type = WSAPI_ClientMessage::Type::PopupMenu;
|
||||||
request.menu.menu_id = m_menu_id;
|
request.menu.menu_id = m_menu_id;
|
||||||
request.menu.position = screen_position;
|
request.menu.position = screen_position;
|
||||||
request.menu.top_anchored = top_anchored;
|
|
||||||
GEventLoop::post_message_to_server(request);
|
GEventLoop::post_message_to_server(request);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -21,7 +21,7 @@ public:
|
||||||
void add_action(Retained<GAction>);
|
void add_action(Retained<GAction>);
|
||||||
void add_separator();
|
void add_separator();
|
||||||
|
|
||||||
void popup(const Point& screen_position, bool top_anchored = true);
|
void popup(const Point& screen_position);
|
||||||
void dismiss();
|
void dismiss();
|
||||||
|
|
||||||
Function<void(unsigned)> on_item_activation;
|
Function<void(unsigned)> on_item_activation;
|
||||||
|
|
|
@ -258,7 +258,6 @@ struct WSAPI_ClientMessage {
|
||||||
bool checkable;
|
bool checkable;
|
||||||
bool checked;
|
bool checked;
|
||||||
WSAPI_Point position;
|
WSAPI_Point position;
|
||||||
bool top_anchored;
|
|
||||||
} menu;
|
} menu;
|
||||||
struct {
|
struct {
|
||||||
WSAPI_Rect rect;
|
WSAPI_Rect rect;
|
||||||
|
|
|
@ -260,7 +260,7 @@ void WSClientConnection::handle_request(const WSAPIPopupMenuRequest& request)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
auto& menu = *(*it).value;
|
auto& menu = *(*it).value;
|
||||||
menu.popup(position, request.top_anchored());
|
menu.popup(position);
|
||||||
}
|
}
|
||||||
|
|
||||||
void WSClientConnection::handle_request(const WSAPIDismissMenuRequest& request)
|
void WSClientConnection::handle_request(const WSAPIDismissMenuRequest& request)
|
||||||
|
|
|
@ -235,22 +235,19 @@ private:
|
||||||
|
|
||||||
class WSAPIPopupMenuRequest : public WSAPIClientRequest {
|
class WSAPIPopupMenuRequest : public WSAPIClientRequest {
|
||||||
public:
|
public:
|
||||||
WSAPIPopupMenuRequest(int client_id, int menu_id, const Point& position, bool top_anchored)
|
WSAPIPopupMenuRequest(int client_id, int menu_id, const Point& position)
|
||||||
: WSAPIClientRequest(WSEvent::APIPopupMenuRequest, client_id)
|
: WSAPIClientRequest(WSEvent::APIPopupMenuRequest, client_id)
|
||||||
, m_menu_id(menu_id)
|
, m_menu_id(menu_id)
|
||||||
, m_position(position)
|
, m_position(position)
|
||||||
, m_top_anchored(top_anchored)
|
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
int menu_id() const { return m_menu_id; }
|
int menu_id() const { return m_menu_id; }
|
||||||
Point position() const { return m_position; }
|
Point position() const { return m_position; }
|
||||||
bool top_anchored() const { return m_top_anchored; }
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
int m_menu_id;
|
int m_menu_id;
|
||||||
Point m_position;
|
Point m_position;
|
||||||
bool m_top_anchored;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
class WSAPIDismissMenuRequest : public WSAPIClientRequest {
|
class WSAPIDismissMenuRequest : public WSAPIClientRequest {
|
||||||
|
|
|
@ -158,7 +158,7 @@ bool WSEventLoop::on_receive_from_client(int client_id, const WSAPI_ClientMessag
|
||||||
post_event(client, make<WSAPICreateMenuRequest>(client_id, String(message.text, message.text_length)));
|
post_event(client, make<WSAPICreateMenuRequest>(client_id, String(message.text, message.text_length)));
|
||||||
break;
|
break;
|
||||||
case WSAPI_ClientMessage::Type::PopupMenu:
|
case WSAPI_ClientMessage::Type::PopupMenu:
|
||||||
post_event(client, make<WSAPIPopupMenuRequest>(client_id, message.menu.menu_id, message.menu.position, message.menu.top_anchored));
|
post_event(client, make<WSAPIPopupMenuRequest>(client_id, message.menu.menu_id, message.menu.position));
|
||||||
break;
|
break;
|
||||||
case WSAPI_ClientMessage::Type::DismissMenu:
|
case WSAPI_ClientMessage::Type::DismissMenu:
|
||||||
post_event(client, make<WSAPIDismissMenuRequest>(client_id, message.menu.menu_id));
|
post_event(client, make<WSAPIDismissMenuRequest>(client_id, message.menu.menu_id));
|
||||||
|
|
|
@ -4,6 +4,7 @@
|
||||||
#include "WSEvent.h"
|
#include "WSEvent.h"
|
||||||
#include "WSEventLoop.h"
|
#include "WSEventLoop.h"
|
||||||
#include "WSWindowManager.h"
|
#include "WSWindowManager.h"
|
||||||
|
#include "WSScreen.h"
|
||||||
#include <WindowServer/WSAPITypes.h>
|
#include <WindowServer/WSAPITypes.h>
|
||||||
#include <WindowServer/WSClientConnection.h>
|
#include <WindowServer/WSClientConnection.h>
|
||||||
#include <SharedGraphics/CharacterBitmap.h>
|
#include <SharedGraphics/CharacterBitmap.h>
|
||||||
|
@ -227,14 +228,21 @@ void WSMenu::close()
|
||||||
menu_window()->set_visible(false);
|
menu_window()->set_visible(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
void WSMenu::popup(const Point& position, bool top_anchored)
|
void WSMenu::popup(const Point& position)
|
||||||
{
|
{
|
||||||
ASSERT(!is_empty());
|
ASSERT(!is_empty());
|
||||||
|
|
||||||
auto& window = ensure_menu_window();
|
auto& window = ensure_menu_window();
|
||||||
if (top_anchored)
|
const int margin = 30;
|
||||||
window.move_to(position);
|
Point adjusted_pos = position;
|
||||||
else
|
if (adjusted_pos.x() + window.width() >= WSScreen::the().width() - margin) {
|
||||||
window.move_to(position.translated(0, -window.height()));
|
adjusted_pos = adjusted_pos.translated(-window.width(), 0);
|
||||||
|
}
|
||||||
|
if (adjusted_pos.y() + window.height() >= WSScreen::the().height() - margin) {
|
||||||
|
adjusted_pos = adjusted_pos.translated(0, -window.height());
|
||||||
|
}
|
||||||
|
|
||||||
|
window.move_to(adjusted_pos);
|
||||||
window.set_visible(true);
|
window.set_visible(true);
|
||||||
WSWindowManager::the().set_current_menu(this);
|
WSWindowManager::the().set_current_menu(this);
|
||||||
}
|
}
|
||||||
|
|
|
@ -74,7 +74,7 @@ public:
|
||||||
|
|
||||||
void close();
|
void close();
|
||||||
|
|
||||||
void popup(const Point&, bool top_anchored);
|
void popup(const Point&);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
virtual void event(CEvent&) override;
|
virtual void event(CEvent&) override;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue