The JUCE cross-platform C++ framework, with DISTRHO/KXStudio specific changes
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.

297 lines
13KB

  1. /*
  2. ==============================================================================
  3. This file is part of the JUCE library.
  4. Copyright (c) 2022 - Raw Material Software Limited
  5. JUCE is an open source library subject to commercial or open-source
  6. licensing.
  7. By using JUCE, you agree to the terms of both the JUCE 7 End-User License
  8. Agreement and JUCE Privacy Policy.
  9. End User License Agreement: www.juce.com/juce-7-licence
  10. Privacy Policy: www.juce.com/juce-privacy-policy
  11. Or: You may also use this code under the terms of the GPL v3 (see
  12. www.gnu.org/licenses).
  13. JUCE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY, AND ALL WARRANTIES, WHETHER
  14. EXPRESSED OR IMPLIED, INCLUDING MERCHANTABILITY AND FITNESS FOR PURPOSE, ARE
  15. DISCLAIMED.
  16. ==============================================================================
  17. */
  18. namespace juce
  19. {
  20. #if JUCE_WEB_BROWSER || DOXYGEN
  21. //==============================================================================
  22. /**
  23. A component that displays an embedded web browser.
  24. The browser itself will be platform-dependent. On Mac and iOS it will be
  25. WebKit, on Android it will be Chrome, and on Linux it will be WebKit.
  26. On Windows it will be IE, but if JUCE_USE_WIN_WEBVIEW2 is enabled then using
  27. the WindowsWebView2WebBrowserComponent wrapper instead of this class directly
  28. will attempt to use the Microsoft Edge (Chromium) WebView2. See the documentation
  29. of that class for more information about its requirements.
  30. @tags{GUI}
  31. */
  32. class JUCE_API WebBrowserComponent : public Component
  33. {
  34. public:
  35. //==============================================================================
  36. /**
  37. Options to configure WebBrowserComponent.
  38. */
  39. class JUCE_API Options
  40. {
  41. public:
  42. //==============================================================================
  43. enum class Backend
  44. {
  45. /**
  46. Default web browser backend. WebKit will be used on macOS, gtk-webkit2 on Linux and internet
  47. explorer on Windows. On Windows, the default may change to webview2 in the fututre.
  48. */
  49. defaultBackend,
  50. /**
  51. Use Internet Explorer as the backend on Windows. By default, IE will use an ancient version
  52. of IE. To change this behaviour, you either need to add the following html element into your page's
  53. head section:
  54. <meta http-equiv="X-UA-Compatible" content="IE=edge" />
  55. or you need to change windows registry values for your application. More information on the latter
  56. can be found here:
  57. https://learn.microsoft.com/en-us/previous-versions/windows/internet-explorer/ie-developer/general-info/ee330730(v=vs.85)?redirectedfrom=MSDN#browser-emulation
  58. */
  59. ie,
  60. /**
  61. Use the chromium based WebView2 engine on Windows
  62. */
  63. webview2
  64. };
  65. /**
  66. Use a particular backend to create the WebViewBrowserComponent. JUCE will silently
  67. fallback to the default backend if the selected backend is not supported. To check
  68. if a specific backend is supported on your platform or not, use
  69. WebBrowserComponent::areOptionsSupported.
  70. */
  71. [[nodiscard]] Options withBackend (Backend backend) const { return withMember (*this, &Options::browserBackend, backend); }
  72. //==============================================================================
  73. /**
  74. Tell JUCE to keep the web page alive when the WebBrowserComponent is not visible.
  75. By default, JUCE will replace the current page with a blank page - this can be
  76. handy to stop the browser using resources in the background when it's not
  77. actually being used.
  78. */
  79. [[nodiscard]] Options withKeepPageLoadedWhenBrowserIsHidden() const { return withMember (*this, &Options::keepPageLoadedWhenBrowserIsHidden, true); }
  80. /**
  81. Use a specific user agent string when requesting web pages.
  82. */
  83. [[nodiscard]] Options withUserAgent (String ua) const { return withMember (*this, &Options::userAgent, std::move (ua)); }
  84. //==============================================================================
  85. /** Options specific to the WebView2 backend. These options will be ignored
  86. if another backend is used.
  87. */
  88. class WinWebView2
  89. {
  90. public:
  91. //==============================================================================
  92. /** Sets a custom location for the WebView2Loader.dll that is not a part of the
  93. standard system DLL search paths.
  94. */
  95. [[nodiscard]] WinWebView2 withDLLLocation (const File& location) const { return withMember (*this, &WinWebView2::dllLocation, location); }
  96. /** Sets a non-default location for storing user data for the browser instance. */
  97. [[nodiscard]] WinWebView2 withUserDataFolder (const File& folder) const { return withMember (*this, &WinWebView2::userDataFolder, folder); }
  98. /** If this is set, the status bar usually displayed in the lower-left of the webview
  99. will be disabled.
  100. */
  101. [[nodiscard]] WinWebView2 withStatusBarDisabled() const { return withMember (*this, &WinWebView2::disableStatusBar, true); }
  102. /** If this is set, a blank page will be displayed on error instead of the default
  103. built-in error page.
  104. */
  105. [[nodiscard]] WinWebView2 withBuiltInErrorPageDisabled() const { return withMember (*this, &WinWebView2::disableBuiltInErrorPage, true); }
  106. /** Sets the background colour that WebView2 renders underneath all web content.
  107. This colour must either be fully opaque or transparent. On Windows 7 this
  108. colour must be opaque.
  109. */
  110. [[nodiscard]] WinWebView2 withBackgroundColour (const Colour& colour) const
  111. {
  112. // the background colour must be either fully opaque or transparent!
  113. jassert (colour.isOpaque() || colour.isTransparent());
  114. return withMember (*this, &WinWebView2::backgroundColour, colour);
  115. }
  116. //==============================================================================
  117. File getDLLLocation() const { return dllLocation; }
  118. File getUserDataFolder() const { return userDataFolder; }
  119. bool getIsStatusBarDisabled() const noexcept { return disableStatusBar; }
  120. bool getIsBuiltInErrorPageDisabled() const noexcept { return disableBuiltInErrorPage; }
  121. Colour getBackgroundColour() const { return backgroundColour; }
  122. private:
  123. //==============================================================================
  124. File dllLocation, userDataFolder;
  125. bool disableStatusBar = false, disableBuiltInErrorPage = false;
  126. Colour backgroundColour;
  127. };
  128. [[nodiscard]] Options withWinWebView2Options (const WinWebView2& winWebView2Options) const
  129. {
  130. return withMember (*this, &Options::winWebView2, winWebView2Options);
  131. }
  132. //==============================================================================
  133. Backend getBackend() const noexcept { return browserBackend; }
  134. bool keepsPageLoadedWhenBrowserIsHidden() const noexcept { return keepPageLoadedWhenBrowserIsHidden; }
  135. String getUserAgent() const { return userAgent; }
  136. WinWebView2 getWinWebView2BackendOptions() const { return winWebView2; }
  137. private:
  138. //==============================================================================
  139. Backend browserBackend = Backend::defaultBackend;
  140. bool keepPageLoadedWhenBrowserIsHidden = false;
  141. String userAgent;
  142. WinWebView2 winWebView2;
  143. };
  144. //==============================================================================
  145. /** Creates a WebBrowserComponent with default options*/
  146. WebBrowserComponent() : WebBrowserComponent (Options {}) {}
  147. /** Creates a WebBrowserComponent.
  148. Once it's created and visible, send the browser to a URL using goToURL().
  149. */
  150. explicit WebBrowserComponent (const Options& options);
  151. /** Destructor. */
  152. ~WebBrowserComponent() override;
  153. //==============================================================================
  154. /** Check if the specified options are supported on this platform. */
  155. static bool areOptionsSupported (const Options& options);
  156. //==============================================================================
  157. /** Sends the browser to a particular URL.
  158. @param url the URL to go to.
  159. @param headers an optional set of parameters to put in the HTTP header. If
  160. you supply this, it should be a set of string in the form
  161. "HeaderKey: HeaderValue"
  162. @param postData an optional block of data that will be attached to the HTTP
  163. POST request
  164. */
  165. void goToURL (const String& url,
  166. const StringArray* headers = nullptr,
  167. const MemoryBlock* postData = nullptr);
  168. /** Stops the current page loading. */
  169. void stop();
  170. /** Sends the browser back one page. */
  171. void goBack();
  172. /** Sends the browser forward one page. */
  173. void goForward();
  174. /** Refreshes the browser. */
  175. void refresh();
  176. /** Clear cookies that the OS has stored for the WebComponents of this application */
  177. static void clearCookies();
  178. //==============================================================================
  179. /** This callback is called when the browser is about to navigate
  180. to a new location.
  181. You can override this method to perform some action when the user
  182. tries to go to a particular URL. To allow the operation to carry on,
  183. return true, or return false to stop the navigation happening.
  184. */
  185. virtual bool pageAboutToLoad (const String& newURL);
  186. /** This callback happens when the browser has finished loading a page. */
  187. virtual void pageFinishedLoading (const String& url);
  188. /** This callback happens when a network error was encountered while
  189. trying to load a page.
  190. You can override this method to show some other error page by calling
  191. goToURL. Return true to allow the browser to carry on to the internal
  192. browser error page.
  193. The errorInfo contains some platform dependent string describing the
  194. error.
  195. */
  196. virtual bool pageLoadHadNetworkError (const String& errorInfo);
  197. /** This callback occurs when a script or other activity in the browser asks for
  198. the window to be closed.
  199. */
  200. virtual void windowCloseRequest();
  201. /** This callback occurs when the browser attempts to load a URL in a new window.
  202. This won't actually load the window but gives you a chance to either launch a
  203. new window yourself or just load the URL into the current window with goToURL().
  204. */
  205. virtual void newWindowAttemptingToLoad (const String& newURL);
  206. //==============================================================================
  207. /** @internal */
  208. void paint (Graphics&) override;
  209. /** @internal */
  210. void resized() override;
  211. /** @internal */
  212. void parentHierarchyChanged() override;
  213. /** @internal */
  214. void visibilityChanged() override;
  215. /** @internal */
  216. void focusGainedWithDirection (FocusChangeType, FocusChangeDirection) override;
  217. /** @internal */
  218. class Pimpl;
  219. private:
  220. std::unique_ptr<AccessibilityHandler> createAccessibilityHandler() override
  221. {
  222. return std::make_unique<AccessibilityHandler> (*this, AccessibilityRole::group);
  223. }
  224. //==============================================================================
  225. std::unique_ptr<Pimpl> browser;
  226. bool blankPageShown = false, unloadPageWhenHidden;
  227. String lastURL;
  228. StringArray lastHeaders;
  229. MemoryBlock lastPostData;
  230. void reloadLastURL();
  231. void checkWindowAssociation();
  232. JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (WebBrowserComponent)
  233. };
  234. #endif
  235. } // namespace juce