Flutter Windows Embedder
display_monitor.cc
Go to the documentation of this file.
1 // Copyright 2013 The Flutter Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include "display_monitor.h"
6 
7 #include <windows.h>
8 
11 
12 namespace flutter {
13 
14 namespace {
15 
16 // Data structure to pass to the display enumeration callback.
17 struct MonitorEnumState {
18  const DisplayMonitor* display_monitor;
19  std::vector<FlutterEngineDisplay>* displays;
20 };
21 
22 } // namespace
23 
25  : engine_(engine), win32_(engine->windows_proc_table()) {}
26 
28 
29 BOOL CALLBACK DisplayMonitor::EnumMonitorCallback(HMONITOR monitor,
30  HDC hdc,
31  LPRECT rect,
32  LPARAM data) {
33  MonitorEnumState* state = reinterpret_cast<MonitorEnumState*>(data);
34  const DisplayMonitor* self = state->display_monitor;
35  std::vector<FlutterEngineDisplay>* displays = state->displays;
36 
37  MONITORINFOEXW monitor_info = {};
38  monitor_info.cbSize = sizeof(monitor_info);
39  if (self->win32_->GetMonitorInfoW(monitor, &monitor_info) == 0) {
40  // Return TRUE to continue enumeration and skip this monitor.
41  // Returning FALSE would stop the entire enumeration process,
42  // potentially missing other valid monitors.
43  return TRUE;
44  }
45 
46  DEVMODEW dev_mode = {};
47  dev_mode.dmSize = sizeof(dev_mode);
48  if (!self->win32_->EnumDisplaySettingsW(monitor_info.szDevice,
49  ENUM_CURRENT_SETTINGS, &dev_mode)) {
50  // Return TRUE to continue enumeration and skip this monitor.
51  // Returning FALSE would stop the entire enumeration process,
52  // potentially missing other valid monitors.
53  return TRUE;
54  }
55 
56  UINT dpi = GetDpiForMonitor(monitor);
57 
58  FlutterEngineDisplay display = {};
59  display.struct_size = sizeof(FlutterEngineDisplay);
60  display.display_id = reinterpret_cast<FlutterEngineDisplayId>(monitor);
61  display.single_display = false;
62  display.refresh_rate = dev_mode.dmDisplayFrequency;
63  display.width = monitor_info.rcMonitor.right - monitor_info.rcMonitor.left;
64  display.height = monitor_info.rcMonitor.bottom - monitor_info.rcMonitor.top;
65  display.device_pixel_ratio =
66  static_cast<double>(dpi) / static_cast<double>(kDefaultDpi);
67 
68  displays->push_back(display);
69  return TRUE;
70 }
71 
73  auto displays = GetDisplays();
74  engine_->UpdateDisplay(displays);
75 }
76 
78  UINT message,
79  WPARAM wparam,
80  LPARAM lparam,
81  LRESULT* result) {
82  switch (message) {
83  case WM_DISPLAYCHANGE:
84  case WM_DPICHANGED:
86  break;
87  }
88  return false;
89 }
90 
91 std::vector<FlutterEngineDisplay> DisplayMonitor::GetDisplays() const {
92  std::vector<FlutterEngineDisplay> displays;
93  MonitorEnumState state = {this, &displays};
94  win32_->EnumDisplayMonitors(nullptr, nullptr, EnumMonitorCallback,
95  reinterpret_cast<LPARAM>(&state));
96 
97  if (displays.size() == 1) {
98  displays[0].single_display = true;
99  }
100 
101  return displays;
102 }
103 
104 } // namespace flutter
std::vector< FlutterEngineDisplay > GetDisplays() const
DisplayMonitor(FlutterWindowsEngine *engine)
bool HandleWindowMessage(HWND hwnd, UINT message, WPARAM wparam, LPARAM lparam, LRESULT *result)
void UpdateDisplay(const std::vector< FlutterEngineDisplay > &displays)
const DisplayMonitor * display_monitor
std::vector< FlutterEngineDisplay > * displays
Win32Message message
UINT GetDpiForMonitor(HMONITOR monitor)
Definition: dpi_utils.cc:132
constexpr UINT kDefaultDpi
Definition: dpi_utils.h:12