Consider transform when calculating monitor size (#88)

When using a rotated monitor, the width value is incorrect and most of
the widgets are off screen.
When taking the transform into account (swapping width and height when
90/270° rotation is applied) the width is correct.
This commit is contained in:
Alexis Howells 2024-04-19 21:47:14 +01:00 committed by GitHub
parent b9ab546c4f
commit 3a7ff0d179
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
3 changed files with 41 additions and 4 deletions

View file

@ -179,7 +179,25 @@ namespace Wayland
// Output Callbacks // Output Callbacks
// Very bloated, indeed // Very bloated, indeed
static void OnOutputGeometry(void*, wl_output*, int32_t, int32_t, int32_t, int32_t, int32_t, const char*, const char*, int32_t) {} static void OnOutputGeometry(void*, wl_output* output, int32_t, int32_t, int32_t, int32_t, int32_t, const char*, const char*, int32_t transform)
{
auto it = monitors.find(output);
ASSERT(it != monitors.end(), "Error: OnOutputGeometry called on unknown monitor");
switch (transform)
{
case WL_OUTPUT_TRANSFORM_NORMAL:
case WL_OUTPUT_TRANSFORM_FLIPPED: it->second.rotation = 0; break;
case WL_OUTPUT_TRANSFORM_90:
case WL_OUTPUT_TRANSFORM_FLIPPED_90: it->second.rotation = 90; break;
case WL_OUTPUT_TRANSFORM_180:
case WL_OUTPUT_TRANSFORM_FLIPPED_180: it->second.rotation = 180; break;
case WL_OUTPUT_TRANSFORM_270:
case WL_OUTPUT_TRANSFORM_FLIPPED_270: it->second.rotation = 270; break;
}
}
static void OnOutputMode(void*, wl_output* output, uint32_t, int32_t width, int32_t height, int32_t) static void OnOutputMode(void*, wl_output* output, uint32_t, int32_t width, int32_t height, int32_t)
{ {
auto it = monitors.find(output); auto it = monitors.find(output);
@ -211,7 +229,7 @@ namespace Wayland
if (strcmp(interface, "wl_output") == 0) if (strcmp(interface, "wl_output") == 0)
{ {
wl_output* output = (wl_output*)wl_registry_bind(registry, name, &wl_output_interface, 4); wl_output* output = (wl_output*)wl_registry_bind(registry, name, &wl_output_interface, 4);
Monitor mon = Monitor{"", name, 0, 0, 0, nullptr, (uint32_t)monitors.size()}; Monitor mon = Monitor{"", name, 0, 0, 0, 0, nullptr, (uint32_t)monitors.size()};
monitors.emplace(output, mon); monitors.emplace(output, mon);
LOG("Wayland: Register <pending> at ID " << mon.ID); LOG("Wayland: Register <pending> at ID " << mon.ID);

View file

@ -13,6 +13,7 @@ namespace Wayland
int32_t width; int32_t width;
int32_t height; int32_t height;
int32_t scale; // TODO: Handle fractional scaling int32_t scale; // TODO: Handle fractional scaling
uint32_t rotation;
zext_workspace_group_handle_v1* workspaceGroup; zext_workspace_group_handle_v1* workspaceGroup;
// The Gdk monitor index. This is only a hacky approximation, since there is no way to get the wl_output from a GdkMonitor // The Gdk monitor index. This is only a hacky approximation, since there is no way to get the wl_output from a GdkMonitor
uint32_t ID; uint32_t ID;

View file

@ -246,7 +246,16 @@ int Window::GetWidth() const
const Wayland::Monitor* mon = Wayland::FindMonitorByName(m_MonitorName); const Wayland::Monitor* mon = Wayland::FindMonitorByName(m_MonitorName);
ASSERT(mon, "Window: Couldn't find monitor"); ASSERT(mon, "Window: Couldn't find monitor");
return mon->width / mon->scale;
int viewedWidth = mon->width;
// A 90/270 rotation should use the height for the viewed width
switch (mon->rotation)
{
case 90:
case 270: viewedWidth = mon->height; break;
}
return viewedWidth / mon->scale;
} }
int Window::GetHeight() const int Window::GetHeight() const
@ -257,7 +266,16 @@ int Window::GetHeight() const
const Wayland::Monitor* mon = Wayland::FindMonitorByName(m_MonitorName); const Wayland::Monitor* mon = Wayland::FindMonitorByName(m_MonitorName);
ASSERT(mon, "Window: Couldn't find monitor"); ASSERT(mon, "Window: Couldn't find monitor");
return mon->height / mon->scale;
int viewedHeight = mon->height;
// A 90/270 rotation should use the width for the viewed height
switch (mon->rotation)
{
case 90:
case 270: viewedHeight = mon->width; break;
}
return viewedHeight / mon->scale;
} }
void Window::MonitorAdded(GdkDisplay*, GdkMonitor*) void Window::MonitorAdded(GdkDisplay*, GdkMonitor*)