Audio plugin host https://kx.studio/carla
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

367 lines
16KB

  1. /*
  2. ==============================================================================
  3. This file is part of the JUCE library.
  4. Copyright (c) 2013 - Raw Material Software Ltd.
  5. Permission is granted to use this software under the terms of either:
  6. a) the GPL v2 (or any later version)
  7. b) the Affero GPL v3
  8. Details of these licenses can be found at: www.gnu.org/licenses
  9. JUCE is distributed in the hope that it will be useful, but WITHOUT ANY
  10. WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
  11. A PARTICULAR PURPOSE. See the GNU General Public License for more details.
  12. ------------------------------------------------------------------------------
  13. To release a closed-source product which uses JUCE, commercial licenses are
  14. available: visit www.juce.com for more information.
  15. ==============================================================================
  16. */
  17. #ifndef JUCE_COMPONENTPEER_H_INCLUDED
  18. #define JUCE_COMPONENTPEER_H_INCLUDED
  19. //==============================================================================
  20. /**
  21. The Component class uses a ComponentPeer internally to create and manage a real
  22. operating-system window.
  23. This is an abstract base class - the platform specific code contains implementations of
  24. it for the various platforms.
  25. User-code should very rarely need to have any involvement with this class.
  26. @see Component::createNewPeer
  27. */
  28. class JUCE_API ComponentPeer
  29. {
  30. public:
  31. //==============================================================================
  32. /** A combination of these flags is passed to the ComponentPeer constructor. */
  33. enum StyleFlags
  34. {
  35. windowAppearsOnTaskbar = (1 << 0), /**< Indicates that the window should have a corresponding
  36. entry on the taskbar (ignored on MacOSX) */
  37. windowIsTemporary = (1 << 1), /**< Indicates that the window is a temporary popup, like a menu,
  38. tooltip, etc. */
  39. windowIgnoresMouseClicks = (1 << 2), /**< Indicates that the window should let mouse clicks pass
  40. through it (may not be possible on some platforms). */
  41. windowHasTitleBar = (1 << 3), /**< Indicates that the window should have a normal OS-specific
  42. title bar and frame. if not specified, the window will be
  43. borderless. */
  44. windowIsResizable = (1 << 4), /**< Indicates that the window should have a resizable border. */
  45. windowHasMinimiseButton = (1 << 5), /**< Indicates that if the window has a title bar, it should have a
  46. minimise button on it. */
  47. windowHasMaximiseButton = (1 << 6), /**< Indicates that if the window has a title bar, it should have a
  48. maximise button on it. */
  49. windowHasCloseButton = (1 << 7), /**< Indicates that if the window has a title bar, it should have a
  50. close button on it. */
  51. windowHasDropShadow = (1 << 8), /**< Indicates that the window should have a drop-shadow (this may
  52. not be possible on all platforms). */
  53. windowRepaintedExplictly = (1 << 9), /**< Not intended for public use - this tells a window not to
  54. do its own repainting, but only to repaint when the
  55. performAnyPendingRepaintsNow() method is called. */
  56. windowIgnoresKeyPresses = (1 << 10), /**< Tells the window not to catch any keypresses. This can
  57. be used for things like plugin windows, to stop them interfering
  58. with the host's shortcut keys */
  59. windowIsSemiTransparent = (1 << 31) /**< Not intended for public use - makes a window transparent. */
  60. };
  61. //==============================================================================
  62. /** Creates a peer.
  63. The component is the one that we intend to represent, and the style flags are
  64. a combination of the values in the StyleFlags enum
  65. */
  66. ComponentPeer (Component& component, int styleFlags);
  67. /** Destructor. */
  68. virtual ~ComponentPeer();
  69. //==============================================================================
  70. /** Returns the component being represented by this peer. */
  71. Component& getComponent() noexcept { return component; }
  72. /** Returns the set of style flags that were set when the window was created.
  73. @see Component::addToDesktop
  74. */
  75. int getStyleFlags() const noexcept { return styleFlags; }
  76. /** Returns a unique ID for this peer.
  77. Each peer that is created is given a different ID.
  78. */
  79. uint32 getUniqueID() const noexcept { return uniqueID; }
  80. //==============================================================================
  81. /** Returns the raw handle to whatever kind of window is being used.
  82. On windows, this is probably a HWND, on the mac, it's likely to be a WindowRef,
  83. but remember there's no guarantees what you'll get back.
  84. */
  85. virtual void* getNativeHandle() const = 0;
  86. /** Shows or hides the window. */
  87. virtual void setVisible (bool shouldBeVisible) = 0;
  88. /** Changes the title of the window. */
  89. virtual void setTitle (const String& title) = 0;
  90. /** If this type of window is capable of indicating that the document in it has been
  91. edited, then this changes its status.
  92. For example in OSX, this changes the appearance of the close button.
  93. @returns true if the window has a mechanism for showing this, or false if not.
  94. */
  95. virtual bool setDocumentEditedStatus (bool edited);
  96. /** If this type of window is capable of indicating that it represents a file, then
  97. this lets you set the file.
  98. E.g. in OSX it'll show an icon for the file in the title bar.
  99. */
  100. virtual void setRepresentedFile (const File&);
  101. //==============================================================================
  102. /** Moves and resizes the window.
  103. If the native window is contained in another window, then the coordinates are
  104. relative to the parent window's origin, not the screen origin.
  105. This should result in a callback to handleMovedOrResized().
  106. */
  107. virtual void setBounds (const Rectangle<int>& newBounds, bool isNowFullScreen) = 0;
  108. /** Updates the peer's bounds to match its component. */
  109. void updateBounds();
  110. /** Returns the current position and size of the window.
  111. If the native window is contained in another window, then the coordinates are
  112. relative to the parent window's origin, not the screen origin.
  113. */
  114. virtual Rectangle<int> getBounds() const = 0;
  115. /** Converts a position relative to the top-left of this component to screen coordinates. */
  116. virtual Point<int> localToGlobal (Point<int> relativePosition) = 0;
  117. /** Converts a rectangle relative to the top-left of this component to screen coordinates. */
  118. virtual Rectangle<int> localToGlobal (const Rectangle<int>& relativePosition);
  119. /** Converts a screen coordinate to a position relative to the top-left of this component. */
  120. virtual Point<int> globalToLocal (Point<int> screenPosition) = 0;
  121. /** Converts a screen area to a position relative to the top-left of this component. */
  122. virtual Rectangle<int> globalToLocal (const Rectangle<int>& screenPosition);
  123. /** Returns the area in peer coordinates that is covered by the given sub-comp (which
  124. may be at any depth)
  125. */
  126. Rectangle<int> getAreaCoveredBy (Component& subComponent) const;
  127. /** Minimises the window. */
  128. virtual void setMinimised (bool shouldBeMinimised) = 0;
  129. /** True if the window is currently minimised. */
  130. virtual bool isMinimised() const = 0;
  131. /** Enable/disable fullscreen mode for the window. */
  132. virtual void setFullScreen (bool shouldBeFullScreen) = 0;
  133. /** True if the window is currently full-screen. */
  134. virtual bool isFullScreen() const = 0;
  135. /** True if the window is in kiosk-mode. */
  136. virtual bool isKioskMode() const;
  137. /** Sets the size to restore to if fullscreen mode is turned off. */
  138. void setNonFullScreenBounds (const Rectangle<int>& newBounds) noexcept;
  139. /** Returns the size to restore to if fullscreen mode is turned off. */
  140. const Rectangle<int>& getNonFullScreenBounds() const noexcept;
  141. /** Attempts to change the icon associated with this window. */
  142. virtual void setIcon (const Image& newIcon) = 0;
  143. /** Sets a constrainer to use if the peer can resize itself.
  144. The constrainer won't be deleted by this object, so the caller must manage its lifetime.
  145. */
  146. void setConstrainer (ComponentBoundsConstrainer* newConstrainer) noexcept;
  147. /** Returns the current constrainer, if one has been set. */
  148. ComponentBoundsConstrainer* getConstrainer() const noexcept { return constrainer; }
  149. /** Checks if a point is in the window.
  150. The position is relative to the top-left of this window, in unscaled peer coordinates.
  151. If trueIfInAChildWindow is false, then this returns false if the point is actually
  152. inside a child of this window.
  153. */
  154. virtual bool contains (Point<int> localPos, bool trueIfInAChildWindow) const = 0;
  155. /** Returns the size of the window frame that's around this window.
  156. Whether or not the window has a normal window frame depends on the flags
  157. that were set when the window was created by Component::addToDesktop()
  158. */
  159. virtual BorderSize<int> getFrameSize() const = 0;
  160. /** This is called when the window's bounds change.
  161. A peer implementation must call this when the window is moved and resized, so that
  162. this method can pass the message on to the component.
  163. */
  164. void handleMovedOrResized();
  165. /** This is called if the screen resolution changes.
  166. A peer implementation must call this if the monitor arrangement changes or the available
  167. screen size changes.
  168. */
  169. virtual void handleScreenSizeChange();
  170. //==============================================================================
  171. /** This is called to repaint the component into the given context. */
  172. void handlePaint (LowLevelGraphicsContext& contextToPaintTo);
  173. //==============================================================================
  174. /** Sets this window to either be always-on-top or normal.
  175. Some kinds of window might not be able to do this, so should return false.
  176. */
  177. virtual bool setAlwaysOnTop (bool alwaysOnTop) = 0;
  178. /** Brings the window to the top, optionally also giving it focus. */
  179. virtual void toFront (bool makeActive) = 0;
  180. /** Moves the window to be just behind another one. */
  181. virtual void toBehind (ComponentPeer* other) = 0;
  182. /** Called when the window is brought to the front, either by the OS or by a call
  183. to toFront().
  184. */
  185. void handleBroughtToFront();
  186. //==============================================================================
  187. /** True if the window has the keyboard focus. */
  188. virtual bool isFocused() const = 0;
  189. /** Tries to give the window keyboard focus. */
  190. virtual void grabFocus() = 0;
  191. /** Called when the window gains keyboard focus. */
  192. void handleFocusGain();
  193. /** Called when the window loses keyboard focus. */
  194. void handleFocusLoss();
  195. Component* getLastFocusedSubcomponent() const noexcept;
  196. /** Called when a key is pressed.
  197. For keycode info, see the KeyPress class.
  198. Returns true if the keystroke was used.
  199. */
  200. bool handleKeyPress (int keyCode, juce_wchar textCharacter);
  201. /** Called whenever a key is pressed or released.
  202. Returns true if the keystroke was used.
  203. */
  204. bool handleKeyUpOrDown (bool isKeyDown);
  205. /** Called whenever a modifier key is pressed or released. */
  206. void handleModifierKeysChange();
  207. //==============================================================================
  208. /** Tells the window that text input may be required at the given position.
  209. This may cause things like a virtual on-screen keyboard to appear, depending
  210. on the OS.
  211. */
  212. virtual void textInputRequired (const Point<int>& position) = 0;
  213. /** If there's some kind of OS input-method in progress, this should dismiss it. */
  214. virtual void dismissPendingTextInput();
  215. /** Returns the currently focused TextInputTarget, or null if none is found. */
  216. TextInputTarget* findCurrentTextInputTarget();
  217. //==============================================================================
  218. /** Invalidates a region of the window to be repainted asynchronously. */
  219. virtual void repaint (const Rectangle<int>& area) = 0;
  220. /** This can be called (from the message thread) to cause the immediate redrawing
  221. of any areas of this window that need repainting.
  222. You shouldn't ever really need to use this, it's mainly for special purposes
  223. like supporting audio plugins where the host's event loop is out of our control.
  224. */
  225. virtual void performAnyPendingRepaintsNow() = 0;
  226. /** Changes the window's transparency. */
  227. virtual void setAlpha (float newAlpha) = 0;
  228. //==============================================================================
  229. void handleMouseEvent (int touchIndex, const Point<int> positionWithinPeer, const ModifierKeys newMods, int64 time);
  230. void handleMouseWheel (int touchIndex, const Point<int> positionWithinPeer, int64 time, const MouseWheelDetails&);
  231. void handleMagnifyGesture (int touchIndex, const Point<int> positionWithinPeer, int64 time, float scaleFactor);
  232. void handleUserClosingWindow();
  233. struct DragInfo
  234. {
  235. StringArray files;
  236. String text;
  237. Point<int> position;
  238. bool isEmpty() const noexcept { return files.size() == 0 && text.isEmpty(); }
  239. void clear() noexcept { files.clear(); text.clear(); }
  240. };
  241. bool handleDragMove (const DragInfo&);
  242. bool handleDragExit (const DragInfo&);
  243. bool handleDragDrop (const DragInfo&);
  244. //==============================================================================
  245. /** Returns the number of currently-active peers.
  246. @see getPeer
  247. */
  248. static int getNumPeers() noexcept;
  249. /** Returns one of the currently-active peers.
  250. @see getNumPeers
  251. */
  252. static ComponentPeer* getPeer (int index) noexcept;
  253. /** Returns the peer that's attached to the given component, or nullptr if there isn't one. */
  254. static ComponentPeer* getPeerFor (const Component*) noexcept;
  255. /** Checks if this peer object is valid.
  256. @see getNumPeers
  257. */
  258. static bool isValidPeer (const ComponentPeer* peer) noexcept;
  259. //==============================================================================
  260. virtual StringArray getAvailableRenderingEngines() = 0;
  261. virtual int getCurrentRenderingEngine() const;
  262. virtual void setCurrentRenderingEngine (int index);
  263. protected:
  264. //==============================================================================
  265. Component& component;
  266. const int styleFlags;
  267. Rectangle<int> lastNonFullscreenBounds;
  268. ComponentBoundsConstrainer* constrainer;
  269. private:
  270. //==============================================================================
  271. WeakReference<Component> lastFocusedComponent, dragAndDropTargetComponent;
  272. Component* lastDragAndDropCompUnderMouse;
  273. const uint32 uniqueID;
  274. bool isWindowMinimised;
  275. Component* getTargetForKeyPress();
  276. JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (ComponentPeer)
  277. };
  278. #endif // JUCE_COMPONENTPEER_H_INCLUDED