File: screen_capturer_x11.h

package info (click to toggle)
chromium 138.0.7204.183-1
  • links: PTS, VCS
  • area: main
  • in suites: trixie
  • size: 6,071,908 kB
  • sloc: cpp: 34,937,088; ansic: 7,176,967; javascript: 4,110,704; python: 1,419,953; asm: 946,768; xml: 739,971; pascal: 187,324; sh: 89,623; perl: 88,663; objc: 79,944; sql: 50,304; cs: 41,786; fortran: 24,137; makefile: 21,806; php: 13,980; tcl: 13,166; yacc: 8,925; ruby: 7,485; awk: 3,720; lisp: 3,096; lex: 1,327; ada: 727; jsp: 228; sed: 36
file content (147 lines) | stat: -rw-r--r-- 5,322 bytes parent folder | download | duplicates (25)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
/*
 *  Copyright 2018 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#ifndef MODULES_DESKTOP_CAPTURE_LINUX_X11_SCREEN_CAPTURER_X11_H_
#define MODULES_DESKTOP_CAPTURE_LINUX_X11_SCREEN_CAPTURER_X11_H_

#include <X11/X.h>
#include <X11/Xlib.h>
#include <X11/extensions/Xdamage.h>
#include <X11/extensions/Xfixes.h>
#include <X11/extensions/Xrandr.h>

#include <memory>

#include "modules/desktop_capture/desktop_capture_options.h"
#include "modules/desktop_capture/desktop_capturer.h"
#include "modules/desktop_capture/desktop_frame.h"
#include "modules/desktop_capture/desktop_region.h"
#include "modules/desktop_capture/linux/x11/shared_x_display.h"
#include "modules/desktop_capture/linux/x11/x_atom_cache.h"
#include "modules/desktop_capture/linux/x11/x_server_pixel_buffer.h"
#include "modules/desktop_capture/screen_capture_frame_queue.h"
#include "modules/desktop_capture/screen_capturer_helper.h"
#include "modules/desktop_capture/shared_desktop_frame.h"

namespace webrtc {

// A class to perform video frame capturing for Linux on X11.
//
// If XDamage is used, this class sets DesktopFrame::updated_region() according
// to the areas reported by XDamage. Otherwise this class does not detect
// DesktopFrame::updated_region(), the field is always set to the entire frame
// rectangle. ScreenCapturerDifferWrapper should be used if that functionality
// is necessary.
class ScreenCapturerX11 : public DesktopCapturer,
                          public SharedXDisplay::XEventHandler {
 public:
  ScreenCapturerX11();
  ~ScreenCapturerX11() override;

  ScreenCapturerX11(const ScreenCapturerX11&) = delete;
  ScreenCapturerX11& operator=(const ScreenCapturerX11&) = delete;

  static std::unique_ptr<DesktopCapturer> CreateRawScreenCapturer(
      const DesktopCaptureOptions& options);

  // TODO(ajwong): Do we really want this to be synchronous?
  bool Init(const DesktopCaptureOptions& options);

  // DesktopCapturer interface.
  void Start(Callback* delegate) override;
  void CaptureFrame() override;
  bool GetSourceList(SourceList* sources) override;
  bool SelectSource(SourceId id) override;

 private:
  Display* display() { return options_.x_display()->display(); }

  // SharedXDisplay::XEventHandler interface.
  bool HandleXEvent(const XEvent& event) override;

  void InitXDamage();
  void InitXrandr();
  void UpdateMonitors();

  // Capture screen pixels to the current buffer in the queue. In the DAMAGE
  // case, the ScreenCapturerHelper already holds the list of invalid rectangles
  // from HandleXEvent(). In the non-DAMAGE case, this captures the
  // whole screen, then calculates some invalid rectangles that include any
  // differences between this and the previous capture.
  std::unique_ptr<DesktopFrame> CaptureScreen();

  // Called when the screen configuration is changed.
  void ScreenConfigurationChanged();

  // Synchronize the current buffer with `last_buffer_`, by copying pixels from
  // the area of `last_invalid_rects`.
  // Note this only works on the assumption that kNumBuffers == 2, as
  // `last_invalid_rects` holds the differences from the previous buffer and
  // the one prior to that (which will then be the current buffer).
  void SynchronizeFrame();

  void DeinitXlib();

  DesktopCaptureOptions options_;

  Callback* callback_ = nullptr;

  // X11 graphics context.
  GC gc_ = nullptr;
  Window root_window_ = BadValue;

  // XRandR 1.5 monitors.
  bool use_randr_ = false;
  int randr_event_base_ = 0;
  XRRMonitorInfo* monitors_ = nullptr;
  int num_monitors_ = 0;
  DesktopRect selected_monitor_rect_;
  // selected_monitor_name_ will be changed to kFullDesktopScreenId
  // by a call to SelectSource() at the end of Init() because
  // selected_monitor_rect_ should be updated as well.
  // Setting it to kFullDesktopScreenId here might be misleading.
  Atom selected_monitor_name_ = 0;
  typedef XRRMonitorInfo* (*get_monitors_func)(Display*, Window, Bool, int*);
  typedef void (*free_monitors_func)(XRRMonitorInfo*);
  get_monitors_func get_monitors_ = nullptr;
  free_monitors_func free_monitors_ = nullptr;

  // XFixes.
  bool has_xfixes_ = false;
  int xfixes_event_base_ = -1;
  int xfixes_error_base_ = -1;

  // XDamage information.
  bool use_damage_ = false;
  Damage damage_handle_ = 0;
  int damage_event_base_ = -1;
  int damage_error_base_ = -1;
  XserverRegion damage_region_ = 0;

  // Access to the X Server's pixel buffer.
  XServerPixelBuffer x_server_pixel_buffer_;

  // A thread-safe list of invalid rectangles, and the size of the most
  // recently captured screen.
  ScreenCapturerHelper helper_;

  // Queue of the frames buffers.
  ScreenCaptureFrameQueue<SharedDesktopFrame> queue_;

  // Invalid region from the previous capture. This is used to synchronize the
  // current with the last buffer used.
  DesktopRegion last_invalid_region_;

  std::unique_ptr<XAtomCache> atom_cache_;
};

}  // namespace webrtc

#endif  // MODULES_DESKTOP_CAPTURE_LINUX_X11_SCREEN_CAPTURER_X11_H_