【问题标题】:SDL2 How to position a window on a second monitor?SDL2 如何在第二台显示器上定位窗口?
【发布时间】:2017-06-04 08:53:37
【问题描述】:

我正在使用SDL_SetWindowPosition 来定位我的窗口。我可以使用此功能将我的窗口定位在另一台显示器上吗?

更新

在 Windows 10 中更改文本大小时,使用 SDL_GetDisplayBounds 将无法返回正确的监视器位置。任何想法如何解决此问题?

【问题讨论】:

  • 非常感谢您提出这个问题。我想知道为什么我在使用 SDL 时缩放完全错误,但事实证明这是因为 Windows 125% 缩放。节省了我数小时的调试时间。

标签: c++ window sdl sdl-2 monitor


【解决方案1】:

SDL2 使用全局屏幕空间坐标系。每个显示设备在此坐标空间内都有自己的边界。以下示例在第二个显示设备上放置一个窗口:

// enumerate displays
int displays = SDL_GetNumVideoDisplays();
assert( displays > 1 );  // assume we have secondary monitor

// get display bounds for all displays
vector< SDL_Rect > displayBounds;
for( int i = 0; i < displays; i++ ) {
    displayBounds.push_back( SDL_Rect() );
    SDL_GetDisplayBounds( i, &displayBounds.back() );
}

// window of dimensions 500 * 500 offset 100 pixels on secondary monitor
int x = displayBounds[ 1 ].x + 100;
int y = displayBounds[ 1 ].y + 100;
int w = 500;
int h = 500;

// so now x and y are on secondary display
SDL_Window * window = SDL_CreateWindow( "title", x, y, w, h, FLAGS... );

查看SDL_video.hSDL_WINDOWPOS_CENTERED的定义,我们看到它被定义为

#define SDL_WINDOWPOS_CENTERED         SDL_WINDOWPOS_CENTERED_DISPLAY(0)

所以我们也可以使用宏SDL_WINDOWPOS_CENTERED_DISPLAY( n ),其中n 是显示索引。

Windows 10 更新 - DPI 缩放问题

似乎 SDL2 确实存在错误并更改 Windows 中的 DPI 比例(即文本比例)。

这里有两个与问题相关的错误报告。他们都显然仍未解决。

https://bugzilla.libsdl.org/show_bug.cgi?id=3433

https://bugzilla.libsdl.org/show_bug.cgi?id=2713

潜在解决方案

我确信 OP 可以使用 WIN32 api 来确定@​​987654330@ 的 dpi 比例,然后以此来更正边界。

【讨论】:

  • 我想对原始问题发表评论以回答您的问题,但我还没有特权。我的猜测是更改 Windows 10 中的 文本比例 会以某种方式影响 SDL 的屏幕坐标。我有一个不同但相关的问题,直到我弄清楚如何将 SDL2 与我的 Mac 的 Retina 显示器一起使用。 (Retina 使用缩放)。我建议您尝试以下实验:在 Windows 10 下,当您更改文本比例设置时,输出显示范围,并检查它们是否发生变化。
  • 这可能是 SDL2 的错误。您是否在 Windows 10 上搜索过具有相同体验的其他人?
  • 如果我的假设是正确的,由于 125% 的文本比例,所有屏幕位置都将乘以 1.25。
  • 对于 Win 10 缩放问题,请参阅这篇精彩的文章:nlguillemot.wordpress.com/2016/12/11/high-dpi-rendering 如果您让您的应用了解 dpi(通过使用清单或 winapi 的SetProcessDpiAwarenessSDL_WINDOWPOS_CENTERED_DISPLAY 就可以正常工作! ;)
【解决方案2】:

DPI 缩放问题(“更改文本大小时不会返回正确的显示器位置”)

这是 SDL2 的一个已知问题(我在这些版本中遇到过:2.0.6、2.0.7、2.0.8,可能旧版本也有这个问题)。

解决方案:

1) 使用清单文件并在那里设置:

<dpiAware>True/PM</dpiAware>

(您需要将清单文件包含在您的应用分发中)

2) 尝试 SetProcessDPIAware()。

【讨论】:

    【解决方案3】:

    是的,如果您知道第二个监视器的边界,您可以使用 SetWindowPosition。 您可以使用函数 SDL_GetDisplayBounds(int displayIndex,SDL_Rect* rect) 来获取它们。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-11-12
      • 2022-01-27
      • 2018-10-24
      • 2012-03-03
      • 1970-01-01
      相关资源
      最近更新 更多