diff --git a/v2/internal/frontend/desktop/linux/window.go b/v2/internal/frontend/desktop/linux/window.go index 782325f57..9613f188f 100644 --- a/v2/internal/frontend/desktop/linux/window.go +++ b/v2/internal/frontend/desktop/linux/window.go @@ -214,7 +214,7 @@ gboolean close_button_pressed(GtkWidget *widget, GdkEvent *event, void* data) return TRUE; } -GtkWidget* setupWebview(void* contentManager, GtkWindow* window, int hideWindowOnClose) { +GtkWidget* setupWebview(void* contentManager, GtkWindow* window, int hideWindowOnClose, int gpuPolicy) { GtkWidget* webview = webkit_web_view_new_with_user_content_manager((WebKitUserContentManager*)contentManager); //gtk_container_add(GTK_CONTAINER(window), webview); WebKitWebContext *context = webkit_web_context_get_default(); @@ -228,6 +228,20 @@ GtkWidget* setupWebview(void* contentManager, GtkWindow* window, int hideWindowO WebKitSettings *settings = webkit_web_view_get_settings(WEBKIT_WEB_VIEW(webview)); webkit_settings_set_user_agent_with_application_details(settings, "wails.io", ""); + + switch (gpuPolicy) { + case 0: + webkit_settings_set_hardware_acceleration_policy(settings, WEBKIT_HARDWARE_ACCELERATION_POLICY_ALWAYS); + break; + case 1: + webkit_settings_set_hardware_acceleration_policy(settings, WEBKIT_HARDWARE_ACCELERATION_POLICY_ON_DEMAND); + break; + case 2: + webkit_settings_set_hardware_acceleration_policy(settings, WEBKIT_HARDWARE_ACCELERATION_POLICY_NEVER); + break; + default: + webkit_settings_set_hardware_acceleration_policy(settings, WEBKIT_HARDWARE_ACCELERATION_POLICY_ON_DEMAND); + } return webview; } @@ -706,7 +720,17 @@ func NewWindow(appoptions *options.App, debug bool) *Window { C.webkit_user_content_manager_register_script_message_handler(result.cWebKitUserContentManager(), external) C.setupInvokeSignal(result.contentManager) - webview := C.setupWebview(result.contentManager, result.asGTKWindow(), bool2Cint(appoptions.HideWindowOnClose)) + var webviewGpuPolicy int + if appoptions.Linux != nil { + webviewGpuPolicy = int(appoptions.Linux.WebviewGpuPolicy) + } + + webview := C.setupWebview( + result.contentManager, + result.asGTKWindow(), + bool2Cint(appoptions.HideWindowOnClose), + C.int(webviewGpuPolicy), + ) result.webview = unsafe.Pointer(webview) buttonPressedName := C.CString("button-press-event") defer C.free(unsafe.Pointer(buttonPressedName)) diff --git a/v2/internal/frontend/desktop/windows/frontend.go b/v2/internal/frontend/desktop/windows/frontend.go index d60e33fc3..0b96b7d1a 100644 --- a/v2/internal/frontend/desktop/windows/frontend.go +++ b/v2/internal/frontend/desktop/windows/frontend.go @@ -412,7 +412,12 @@ func (f *Frontend) setupChromium() { if opts := f.frontendOptions.Windows; opts != nil { chromium.DataPath = opts.WebviewUserDataPath chromium.BrowserPath = opts.WebviewBrowserPath + + if opts.WebviewGpuIsDisabled { + chromium.AdditionalBrowserArgs = append(chromium.AdditionalBrowserArgs, "--disable-gpu") + } } + chromium.MessageCallback = f.processMessage chromium.WebResourceRequestedCallback = f.processRequest chromium.NavigationCompletedCallback = f.navigationCompleted @@ -420,6 +425,7 @@ func (f *Frontend) setupChromium() { w32.PostMessage(f.mainWindow.Handle(), w32.WM_KEYDOWN, uintptr(vkey), 0) return false } + chromium.Embed(f.mainWindow.Handle()) chromium.Resize() settings, err := chromium.GetSettings() diff --git a/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/chromium.go b/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/chromium.go index 8938c6ea6..219aca35c 100644 --- a/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/chromium.go +++ b/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/chromium.go @@ -8,6 +8,7 @@ import ( "log" "os" "path/filepath" + "strings" "sync/atomic" "syscall" "unsafe" @@ -36,9 +37,10 @@ type Chromium struct { padding Rect // Settings - Debug bool - DataPath string - BrowserPath string + Debug bool + DataPath string + BrowserPath string + AdditionalBrowserArgs []string // permissions permissions map[CoreWebView2PermissionKind]CoreWebView2PermissionState @@ -98,7 +100,8 @@ func (e *Chromium) Embed(hwnd uintptr) bool { } } - if err := createCoreWebView2EnvironmentWithOptions(e.BrowserPath, dataPath, e.envCompleted); err != nil { + browserArgs := strings.Join(e.AdditionalBrowserArgs, " ") + if err := createCoreWebView2EnvironmentWithOptions(e.BrowserPath, dataPath, e.envCompleted, browserArgs); err != nil { log.Printf("Error calling Webview2Loader: %v", err) return false } diff --git a/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/create_env_go.go b/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/create_env_go.go index a43089f8c..a3b7374ca 100644 --- a/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/create_env_go.go +++ b/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/create_env_go.go @@ -8,12 +8,13 @@ import ( "github.com/wailsapp/wails/v2/internal/frontend/desktop/windows/go-webview2/webviewloader" ) -func createCoreWebView2EnvironmentWithOptions(browserExecutableFolder, userDataFolder string, environmentCompletedHandle *iCoreWebView2CreateCoreWebView2EnvironmentCompletedHandler) error { +func createCoreWebView2EnvironmentWithOptions(browserExecutableFolder, userDataFolder string, environmentCompletedHandle *iCoreWebView2CreateCoreWebView2EnvironmentCompletedHandler, additionalBrowserArgs string) error { e := &environmentCreatedHandler{environmentCompletedHandle} return webviewloader.CreateCoreWebView2EnvironmentWithOptions( e, webviewloader.WithBrowserExecutableFolder(browserExecutableFolder), webviewloader.WithUserDataFolder(userDataFolder), + webviewloader.WithAdditionalBrowserArguments(additionalBrowserArgs), ) } diff --git a/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/create_env_native.go b/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/create_env_native.go index 1d1b38b9c..39e13a2e7 100644 --- a/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/create_env_native.go +++ b/v2/internal/frontend/desktop/windows/go-webview2/pkg/edge/create_env_native.go @@ -12,7 +12,7 @@ import ( "golang.org/x/sys/windows" ) -func createCoreWebView2EnvironmentWithOptions(browserExecutableFolder, userDataFolder string, environmentCompletedHandle *iCoreWebView2CreateCoreWebView2EnvironmentCompletedHandler) error { +func createCoreWebView2EnvironmentWithOptions(browserExecutableFolder, userDataFolder string, environmentCompletedHandle *iCoreWebView2CreateCoreWebView2EnvironmentCompletedHandler, additionalBrowserArgs string) error { browserPathPtr, err := windows.UTF16PtrFromString(browserExecutableFolder) if err != nil { return fmt.Errorf("Error calling UTF16PtrFromString for %s: %v", browserExecutableFolder, err) diff --git a/v2/pkg/options/default.go b/v2/pkg/options/default.go index 186061e7c..e2555ebbc 100644 --- a/v2/pkg/options/default.go +++ b/v2/pkg/options/default.go @@ -7,13 +7,13 @@ import ( // Default options for creating the App var Default = &App{ - Width: 1024, - Height: 768, - Logger: logger.NewDefaultLogger(), - LogLevel: logger.INFO, - LogLevelProduction: logger.ERROR, - CSSDragProperty: "--wails-draggable", - CSSDragValue: "drag", + Width: 1024, + Height: 768, + Logger: logger.NewDefaultLogger(), + LogLevel: logger.INFO, + LogLevelProduction: logger.ERROR, + CSSDragProperty: "--wails-draggable", + CSSDragValue: "drag", } var defaultMacMenu = menu.NewMenuFromItems( diff --git a/v2/pkg/options/linux/linux.go b/v2/pkg/options/linux/linux.go index 9a9fa56f9..3726297c4 100644 --- a/v2/pkg/options/linux/linux.go +++ b/v2/pkg/options/linux/linux.go @@ -1,12 +1,34 @@ package linux +// WebviewGpuPolicy values used for determining the webview's hardware acceleration policy. +type WebviewGpuPolicy int + +const ( + // WebviewGpuPolicyAlways Hardware acceleration is always enabled. + WebviewGpuPolicyAlways WebviewGpuPolicy = iota + // WebviewGpuPolicyOnDemand Hardware acceleration is enabled/disabled as request by web contents. + WebviewGpuPolicyOnDemand + // WebviewGpuPolicyNever Hardware acceleration is always disabled. + WebviewGpuPolicyNever +) + // Options specific to Linux builds type Options struct { - Icon []byte + // Icon Sets up the icon representing the window. This icon is used when the window is minimized + // (also known as iconified). + Icon []byte + + // WindowIsTranslucent sets the window's background to transparent when enabled. WindowIsTranslucent bool - // User messages that can be customised + // Messages are messages that can be customised Messages *Messages + + // WebviewGpuPolicy used for determining the hardware acceleration policy for the webview. + // - WebviewGpuPolicyAlways + // - WebviewGpuPolicyOnDemand + // - WebviewGpuPolicyNever + WebviewGpuPolicy WebviewGpuPolicy } type Messages struct { diff --git a/v2/pkg/options/options.go b/v2/pkg/options/options.go index 839440d4c..3f45c6b43 100644 --- a/v2/pkg/options/options.go +++ b/v2/pkg/options/options.go @@ -2,6 +2,7 @@ package options import ( "context" + "github.com/wailsapp/wails/v2/pkg/options/linux" "html" "io/fs" "log" @@ -9,7 +10,6 @@ import ( "runtime" "github.com/wailsapp/wails/v2/pkg/options/assetserver" - "github.com/wailsapp/wails/v2/pkg/options/linux" "github.com/wailsapp/wails/v2/pkg/options/mac" "github.com/wailsapp/wails/v2/pkg/options/windows" diff --git a/v2/pkg/options/windows/windows.go b/v2/pkg/options/windows/windows.go index 166e58f7a..9a0f5c733 100644 --- a/v2/pkg/options/windows/windows.go +++ b/v2/pkg/options/windows/windows.go @@ -96,8 +96,12 @@ type Options struct { // OnSuspend is called when Windows enters low power mode OnSuspend func() + // OnResume is called when Windows resumes from low power mode OnResume func() + + // WebviewGpuIsDisabled is used to enable / disable GPU acceleration for the webview + WebviewGpuIsDisabled bool } func DefaultMessages() *Messages { diff --git a/website/docs/reference/options.mdx b/website/docs/reference/options.mdx index 1e7af4c19..72620d383 100644 --- a/website/docs/reference/options.mdx +++ b/website/docs/reference/options.mdx @@ -78,7 +78,8 @@ func main() { // OnSuspend is called when Windows enters low power mode OnSuspend func() // OnResume is called when Windows resumes from low power mode - OnResume func() + OnResume func(), + WebviewGpuDisabled: false, }, Mac: &mac.Options{ TitleBar: &mac.TitleBar{ @@ -101,6 +102,7 @@ func main() { Linux: &linux.Options{ Icon: icon, WindowIsTranslucent: false, + WebviewGpuPolicy: linux.WebviewGpuPolicyAlways, }, Debug: options.Debug{ OpenInspectorOnStartup: false, @@ -628,6 +630,13 @@ If set, this function will be called when Windows resumes from low power mode (s Name: OnResume
Type: `func()` +#### WebviewGpuIsDisabled + +Setting this to `true` will disable GPU hardware acceleration for the webview. + +Name: WebviewGpuIsDisabled
+Type: `bool` + ### Mac This defines [Mac specific options](#mac). @@ -824,6 +833,22 @@ Setting this to `true` will make the window background translucent. Some window Name: WindowIsTranslucent
Type: `bool` +#### WebviewGpuPolicy + +This option is used for determining the webview's hardware acceleration policy. + +Name: WebviewGpuPolicy
+Type: [`options.WebviewGpuPolicy`](#webviewgpupolicy-type)
+Default: `WebviewGpuPolicyAlways` + +##### WebviewGpuPolicy type + +| Value | Description | +| -------------------------| ----------- | +| WebviewGpuPolicyAlways | Hardware acceleration is always enabled| +| WebviewGpuPolicyOnDemand | Hardware acceleration is enabled/disabled as request by web contents| +| WebviewGpuPolicyNever | Hardware acceleration is always disabled | + ### Debug This defines [Debug specific options](#Debug) that apply to debug builds. diff --git a/website/src/pages/changelog.mdx b/website/src/pages/changelog.mdx index 69b2e4d64..3c06a7643 100644 --- a/website/src/pages/changelog.mdx +++ b/website/src/pages/changelog.mdx @@ -14,6 +14,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +### Added +- Added Webview GPU acceleration options for [Windows](/docs/reference/options#webviewgpuisdisabled) and [Linux](/docs/reference/options#webviewgpupolicy). Added by @Lyimmi in [PR](https://github.com/wailsapp/wails/pull/2266) + ## v2.3.0 - 2022-12-29 ### Added