File indexing completed on 2024-05-19 16:34:01
0001 /* 0002 SPDX-FileCopyrightText: 2020 Vlad Zahorodnii <vlad.zahorodnii@kde.org> 0003 0004 SPDX-License-Identifier: GPL-2.0-or-later 0005 */ 0006 0007 #pragma once 0008 0009 #include "kwinglobals.h" 0010 #include "options.h" 0011 0012 #include <QObject> 0013 0014 namespace KWin 0015 { 0016 0017 class RenderLoopPrivate; 0018 class Item; 0019 0020 /** 0021 * The RenderLoop class represents the compositing scheduler on a particular output. 0022 * 0023 * The RenderLoop class drives the compositing. The frameRequested() signal is emitted 0024 * when the loop wants a new frame to be rendered. The frameCompleted() signal is 0025 * emitted when a previously rendered frame has been presented on the screen. In case 0026 * you want the compositor to repaint the scene, call the scheduleRepaint() function. 0027 */ 0028 class KWIN_EXPORT RenderLoop : public QObject 0029 { 0030 Q_OBJECT 0031 0032 public: 0033 explicit RenderLoop(); 0034 ~RenderLoop() override; 0035 0036 /** 0037 * Pauses the render loop. While the render loop is inhibited, scheduleRepaint() 0038 * requests are queued. 0039 * 0040 * Once the render loop is uninhibited, the pending schedule requests are going to 0041 * be re-applied. 0042 */ 0043 void inhibit(); 0044 0045 /** 0046 * Uninhibits the render loop. 0047 */ 0048 void uninhibit(); 0049 0050 /** 0051 * This function must be called before the Compositor starts rendering the next 0052 * frame. 0053 */ 0054 void beginFrame(); 0055 0056 /** 0057 * This function must be called after the Compositor has finished rendering the 0058 * next frame. 0059 */ 0060 void endFrame(); 0061 0062 /** 0063 * Returns the refresh rate at which the output is being updated, in millihertz. 0064 */ 0065 int refreshRate() const; 0066 0067 /** 0068 * Sets the refresh rate of this RenderLoop to @a refreshRate, in millihertz. 0069 */ 0070 void setRefreshRate(int refreshRate); 0071 0072 /** 0073 * Schedules a compositing cycle at the next available moment. 0074 */ 0075 void scheduleRepaint(Item *item = nullptr); 0076 0077 /** 0078 * Returns the timestamp of the last frame that has been presented on the screen. 0079 * The returned timestamp is sourced from the monotonic clock. 0080 */ 0081 std::chrono::nanoseconds lastPresentationTimestamp() const; 0082 0083 /** 0084 * If a repaint has been scheduled, this function returns the expected time when 0085 * the next frame will be presented on the screen. The returned timestamp is sourced 0086 * from the monotonic clock. 0087 */ 0088 std::chrono::nanoseconds nextPresentationTimestamp() const; 0089 0090 /** 0091 * Sets the surface that currently gets scanned out, 0092 * so that this RenderLoop can adjust its timing behavior to that surface 0093 */ 0094 void setFullscreenSurface(Item *surface); 0095 0096 enum class VrrPolicy : uint32_t { 0097 Never = 0, 0098 Always = 1, 0099 Automatic = 2, 0100 }; 0101 Q_ENUM(VrrPolicy) 0102 0103 /** 0104 * the current policy regarding the use of variable refresh rate 0105 */ 0106 VrrPolicy vrrPolicy() const; 0107 0108 /** 0109 * Set the policy regarding the use of variable refresh rate with RenderLoop 0110 */ 0111 void setVrrPolicy(VrrPolicy vrrPolicy); 0112 0113 /** 0114 * Returns the latency policy for this render loop. 0115 */ 0116 LatencyPolicy latencyPolicy() const; 0117 0118 /** 0119 * Sets the latecy policy of this render loop to @a policy. By default, 0120 * the latency policy of this render loop matches options->latencyPolicy(). 0121 */ 0122 void setLatencyPolicy(LatencyPolicy policy); 0123 0124 /** 0125 * Resets the latency policy to the default value. 0126 */ 0127 void resetLatencyPolicy(); 0128 0129 Q_SIGNALS: 0130 /** 0131 * This signal is emitted when the refresh rate of this RenderLoop has changed. 0132 */ 0133 void refreshRateChanged(); 0134 /** 0135 * This signal is emitted when a frame has been actually presented on the screen. 0136 * @a timestamp indicates the time when it took place. 0137 */ 0138 void framePresented(RenderLoop *loop, std::chrono::nanoseconds timestamp); 0139 0140 /** 0141 * This signal is emitted when the render loop wants a new frame to be composited. 0142 * 0143 * The Compositor should make a connection to this signal using Qt::DirectConnection. 0144 */ 0145 void frameRequested(RenderLoop *loop); 0146 0147 private: 0148 std::unique_ptr<RenderLoopPrivate> d; 0149 friend class RenderLoopPrivate; 0150 }; 0151 0152 } // namespace KWin