summaryrefslogtreecommitdiffstats
path: root/xbmc/windowing/OSScreenSaver.h
blob: 367d6dbe4adcda3f43ed66cd0e9d9662ba6b7ff3 (plain)
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
/*
 *  Copyright (C) 2017-2018 Team Kodi
 *  This file is part of Kodi - https://kodi.tv
 *
 *  SPDX-License-Identifier: GPL-2.0-or-later
 *  See LICENSES/README.md for more information.
 */

#pragma once

#include <memory>
#include <utility>

namespace KODI
{
namespace WINDOWING
{

class COSScreenSaverManager;

/**
 * Inhibit the OS screen saver as long as this object is alive
 *
 * Destroy or call \ref Release to stop this inhibitor from being active.
 * The OS screen saver may still be inhibited as long as other inhibitors are
 * active though.
 *
 * \note Make sure to release or destroy the inhibitor before the \ref
 *       COSScreenSaverManager is destroyed
 */
class COSScreenSaverInhibitor
{
public:
  COSScreenSaverInhibitor() noexcept;
  COSScreenSaverInhibitor(COSScreenSaverInhibitor&& other) noexcept;
  COSScreenSaverInhibitor& operator=(COSScreenSaverInhibitor&& other) noexcept;
  ~COSScreenSaverInhibitor() noexcept;
  void Release();
  bool IsActive() const;
  operator bool() const;

private:
  friend class COSScreenSaverManager;
  explicit COSScreenSaverInhibitor(COSScreenSaverManager* manager);
  bool m_active;
  COSScreenSaverManager* m_manager;

  COSScreenSaverInhibitor(COSScreenSaverInhibitor const& other) = delete;
  COSScreenSaverInhibitor& operator=(COSScreenSaverInhibitor const& other) = delete;
};

/**
 * Interface for OS screen saver control implementations
 */
class IOSScreenSaver
{
public:
  virtual ~IOSScreenSaver() = default;
  /**
   * Do not allow the OS screen saver to become active
   *
   * Calling this function multiple times without calling \ref Unhibit
   * MUST NOT produce any side-effects.
   */
  virtual void Inhibit() = 0;
  /**
   * Allow the OS screen saver to become active again
   *
   * Calling this function multiple times or at all without calling \ref Inhibit
   * MUST NOT produce any side-effects.
   */
  virtual void Uninhibit() = 0;
};

/**
 * Dummy implementation of IOSScreenSaver
 */
class CDummyOSScreenSaver : public IOSScreenSaver
{
public:
  void Inhibit() override {}
  void Uninhibit() override {}
};

/**
 * Manage the OS screen saver
 *
 * This class keeps track of a number of \ref COSScreenSaverInhibitor instances
 * and keeps the OS screen saver inhibited as long as at least one of them
 * exists and is active.
 */
class COSScreenSaverManager
{
public:
  /**
   * Create manager with backing OS-specific implementation
   */
  explicit COSScreenSaverManager(std::unique_ptr<IOSScreenSaver> impl);
  /**
   * Create inhibitor that prevents the OS screen saver from becoming active as
   * long as it is alive
   */
  COSScreenSaverInhibitor CreateInhibitor();
  /**
   * Check whether the OS screen saver is currently inhibited
   */
  bool IsInhibited();

private:
  friend class COSScreenSaverInhibitor;
  void RemoveInhibitor();

  unsigned int m_inhibitionCount{0u};
  std::unique_ptr<IOSScreenSaver> m_impl;
};

}
}