mirror of
https://github.com/electron/electron.git
synced 2026-02-19 03:14:51 -05:00
Compare commits
11 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4e9c583230 | ||
|
|
cbc345892c | ||
|
|
6ecae84da3 | ||
|
|
8d8751106b | ||
|
|
eda2ceda1e | ||
|
|
01aafab563 | ||
|
|
325549ffce | ||
|
|
ab272cb767 | ||
|
|
a3acea9fd6 | ||
|
|
c9d2d69397 | ||
|
|
65f2726851 |
2
DEPS
2
DEPS
@@ -2,7 +2,7 @@ gclient_gn_args_from = 'src'
|
||||
|
||||
vars = {
|
||||
'chromium_version':
|
||||
'116.0.5845.179',
|
||||
'116.0.5845.188',
|
||||
'node_version':
|
||||
'v18.16.1',
|
||||
'nan_version':
|
||||
|
||||
@@ -27,7 +27,7 @@ const cachedArchives = new Map<string, NodeJS.AsarArchive>();
|
||||
const getOrCreateArchive = (archivePath: string) => {
|
||||
const isCached = cachedArchives.has(archivePath);
|
||||
if (isCached) {
|
||||
return cachedArchives.get(archivePath);
|
||||
return cachedArchives.get(archivePath)!;
|
||||
}
|
||||
|
||||
try {
|
||||
@@ -39,6 +39,8 @@ const getOrCreateArchive = (archivePath: string) => {
|
||||
}
|
||||
};
|
||||
|
||||
process._getOrCreateArchive = getOrCreateArchive;
|
||||
|
||||
const asarRe = /\.asar/i;
|
||||
|
||||
// Separate asar package's path from full path.
|
||||
|
||||
@@ -84,11 +84,20 @@ const v8Util = process._linkedBinding('electron_common_v8_util');
|
||||
let packagePath = null;
|
||||
let packageJson = null;
|
||||
const searchPaths: string[] = v8Util.getHiddenValue(global, 'appSearchPaths');
|
||||
const searchPathsOnlyLoadASAR: boolean = v8Util.getHiddenValue(global, 'appSearchPathsOnlyLoadASAR');
|
||||
// Borrow the _getOrCreateArchive asar helper
|
||||
const getOrCreateArchive = process._getOrCreateArchive;
|
||||
delete process._getOrCreateArchive;
|
||||
|
||||
if (process.resourcesPath) {
|
||||
for (packagePath of searchPaths) {
|
||||
try {
|
||||
packagePath = path.join(process.resourcesPath, packagePath);
|
||||
if (searchPathsOnlyLoadASAR) {
|
||||
if (!getOrCreateArchive?.(packagePath)) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
packageJson = Module._load(path.join(packagePath, 'package.json'));
|
||||
break;
|
||||
} catch {
|
||||
|
||||
@@ -131,3 +131,4 @@ potential_fix_for_flaky_desktopcaptureapitest_delegation_unittest.patch
|
||||
fix_select_the_first_menu_item_when_opened_via_keyboard.patch
|
||||
chore_add_buildflag_guard_around_new_include.patch
|
||||
fix_use_delegated_generic_capturer_when_available.patch
|
||||
revert_remove_the_allowaggressivethrottlingwithwebsocket_feature.patch
|
||||
|
||||
@@ -0,0 +1,41 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Samuel Attard <samuel.r.attard@gmail.com>
|
||||
Date: Tue, 5 Sep 2023 13:22:31 -0700
|
||||
Subject: Revert "Remove the AllowAggressiveThrottlingWithWebSocket feature."
|
||||
|
||||
This reverts commit 615c1810a187840ffeb04096087efff86edb37de.
|
||||
|
||||
diff --git a/third_party/blink/renderer/modules/websockets/websocket_channel_impl.cc b/third_party/blink/renderer/modules/websockets/websocket_channel_impl.cc
|
||||
index 98a78f1a7b6a5005f7d5da4ac279e38b61fac4dc..330e1e37b2d9f154ccc360d1102375efded12ff9 100644
|
||||
--- a/third_party/blink/renderer/modules/websockets/websocket_channel_impl.cc
|
||||
+++ b/third_party/blink/renderer/modules/websockets/websocket_channel_impl.cc
|
||||
@@ -94,6 +94,17 @@ enum WebSocketOpCode {
|
||||
kOpCodeBinary = 0x2,
|
||||
};
|
||||
|
||||
+// When enabled, a page can be aggressively throttled even if it uses a
|
||||
+// WebSocket. Aggressive throttling does not affect the execution of WebSocket
|
||||
+// event handlers, so there is little reason to disable it on pages using a
|
||||
+// WebSocket.
|
||||
+//
|
||||
+// TODO(crbug.com/1121725): Cleanup this feature in June 2021, when it becomes
|
||||
+// enabled by default on Stable.
|
||||
+BASE_FEATURE(kAllowAggressiveThrottlingWithWebSocket,
|
||||
+ "AllowAggressiveThrottlingWithWebSocket",
|
||||
+ base::FEATURE_ENABLED_BY_DEFAULT);
|
||||
+
|
||||
} // namespace
|
||||
|
||||
void WebSocketChannelImpl::MessageDataDeleter::operator()(char* p) const {
|
||||
@@ -284,7 +295,10 @@ bool WebSocketChannelImpl::Connect(const KURL& url, const String& protocol) {
|
||||
// even if the `WebSocketChannel` is closed.
|
||||
feature_handle_for_scheduler_ = scheduler->RegisterFeature(
|
||||
SchedulingPolicy::Feature::kWebSocket,
|
||||
- SchedulingPolicy{SchedulingPolicy::DisableBackForwardCache()});
|
||||
+ base::FeatureList::IsEnabled(kAllowAggressiveThrottlingWithWebSocket)
|
||||
+ ? SchedulingPolicy{SchedulingPolicy::DisableBackForwardCache()}
|
||||
+ : SchedulingPolicy{SchedulingPolicy::DisableAggressiveThrottling(),
|
||||
+ SchedulingPolicy::DisableBackForwardCache()});
|
||||
scheduler->RegisterStickyFeature(
|
||||
SchedulingPolicy::Feature::kWebSocketSticky,
|
||||
SchedulingPolicy{SchedulingPolicy::DisableBackForwardCache()});
|
||||
@@ -2671,14 +2671,6 @@ void WebContents::OpenDevTools(gin::Arguments* args) {
|
||||
state = "detach";
|
||||
}
|
||||
|
||||
#if BUILDFLAG(IS_WIN)
|
||||
auto* win = static_cast<NativeWindowViews*>(owner_window());
|
||||
// Force a detached state when WCO is enabled to match Chrome
|
||||
// behavior and prevent occlusion of DevTools.
|
||||
if (win && win->IsWindowControlsOverlayEnabled())
|
||||
state = "detach";
|
||||
#endif
|
||||
|
||||
bool activate = true;
|
||||
if (args && args->Length() == 1) {
|
||||
gin_helper::Dictionary options;
|
||||
|
||||
@@ -40,13 +40,6 @@ namespace electron {
|
||||
|
||||
namespace {
|
||||
|
||||
bool IsAppRTL() {
|
||||
const std::string& locale = g_browser_process->GetApplicationLocale();
|
||||
base::i18n::TextDirection text_direction =
|
||||
base::i18n::GetTextDirectionForLocaleInStartUp(locale.c_str());
|
||||
return text_direction == base::i18n::RIGHT_TO_LEFT;
|
||||
}
|
||||
|
||||
NSString* GetAppPathForProtocol(const GURL& url) {
|
||||
NSURL* ns_url = [NSURL
|
||||
URLWithString:base::SysUTF8ToNSString(url.possibly_invalid_spec())];
|
||||
|
||||
@@ -689,9 +689,6 @@ void NativeWindowMac::DetachChildren() {
|
||||
}
|
||||
|
||||
void NativeWindowMac::SetFullScreen(bool fullscreen) {
|
||||
if (!has_frame() && !HasStyleMask(NSWindowStyleMaskTitled))
|
||||
return;
|
||||
|
||||
// [NSWindow -toggleFullScreen] is an asynchronous operation, which means
|
||||
// that it's possible to call it while a fullscreen transition is currently
|
||||
// in process. This can create weird behavior (incl. phantom windows),
|
||||
@@ -724,7 +721,8 @@ void NativeWindowMac::SetFullScreen(bool fullscreen) {
|
||||
? FullScreenTransitionState::kEntering
|
||||
: FullScreenTransitionState::kExiting;
|
||||
|
||||
[window_ toggleFullScreenMode:nil];
|
||||
if (![window_ toggleFullScreenMode:nil])
|
||||
fullscreen_transition_state_ = FullScreenTransitionState::kNone;
|
||||
}
|
||||
|
||||
bool NativeWindowMac::IsFullscreen() const {
|
||||
@@ -1723,6 +1721,9 @@ void NativeWindowMac::NotifyWindowEnterFullScreen() {
|
||||
// Restore the window title under fullscreen mode.
|
||||
if (buttons_proxy_)
|
||||
[window_ setTitleVisibility:NSWindowTitleVisible];
|
||||
|
||||
if (transparent() || !has_frame())
|
||||
[window_ setTitlebarAppearsTransparent:NO];
|
||||
}
|
||||
|
||||
void NativeWindowMac::NotifyWindowLeaveFullScreen() {
|
||||
@@ -1732,6 +1733,9 @@ void NativeWindowMac::NotifyWindowLeaveFullScreen() {
|
||||
[buttons_proxy_ redraw];
|
||||
[buttons_proxy_ setVisible:YES];
|
||||
}
|
||||
|
||||
if (transparent() || !has_frame())
|
||||
[window_ setTitlebarAppearsTransparent:YES];
|
||||
}
|
||||
|
||||
void NativeWindowMac::NotifyWindowWillEnterFullScreen() {
|
||||
|
||||
@@ -44,7 +44,7 @@ class ScopedDisableResize {
|
||||
- (electron::NativeWindowMac*)shell;
|
||||
- (id)accessibilityFocusedUIElement;
|
||||
- (NSRect)originalContentRectForFrameRect:(NSRect)frameRect;
|
||||
- (void)toggleFullScreenMode:(id)sender;
|
||||
- (BOOL)toggleFullScreenMode:(id)sender;
|
||||
- (NSImage*)_cornerMask;
|
||||
@end
|
||||
|
||||
|
||||
@@ -334,7 +334,10 @@ void SwizzleSwipeWithEvent(NSView* view, SEL swiz_selector) {
|
||||
}
|
||||
}
|
||||
|
||||
- (void)toggleFullScreenMode:(id)sender {
|
||||
- (BOOL)toggleFullScreenMode:(id)sender {
|
||||
if (!shell_->has_frame() && !shell_->HasStyleMask(NSWindowStyleMaskTitled))
|
||||
return NO;
|
||||
|
||||
bool is_simple_fs = shell_->IsSimpleFullScreen();
|
||||
bool always_simple_fs = shell_->always_simple_fullscreen();
|
||||
|
||||
@@ -363,6 +366,8 @@ void SwizzleSwipeWithEvent(NSView* view, SEL swiz_selector) {
|
||||
bool maximizable = shell_->IsMaximizable();
|
||||
shell_->SetMaximizable(maximizable);
|
||||
}
|
||||
|
||||
return YES;
|
||||
}
|
||||
|
||||
- (void)performMiniaturize:(id)sender {
|
||||
|
||||
@@ -44,11 +44,13 @@
|
||||
#include "services/network/public/cpp/simple_url_loader_stream_consumer.h"
|
||||
#include "services/network/public/cpp/wrapper_shared_url_loader_factory.h"
|
||||
#include "shell/browser/api/electron_api_web_contents.h"
|
||||
#include "shell/browser/native_window_views.h"
|
||||
#include "shell/browser/net/asar/asar_url_loader_factory.h"
|
||||
#include "shell/browser/protocol_registry.h"
|
||||
#include "shell/browser/ui/inspectable_web_contents_delegate.h"
|
||||
#include "shell/browser/ui/inspectable_web_contents_view.h"
|
||||
#include "shell/browser/ui/inspectable_web_contents_view_delegate.h"
|
||||
#include "shell/common/application_info.h"
|
||||
#include "shell/common/platform_util.h"
|
||||
#include "third_party/blink/public/common/logging/logging_utils.h"
|
||||
#include "third_party/blink/public/common/page/page_zoom.h"
|
||||
@@ -573,6 +575,23 @@ void InspectableWebContents::LoadCompleted() {
|
||||
prefs.FindString("currentDockState");
|
||||
base::RemoveChars(*current_dock_state, "\"", &dock_state_);
|
||||
}
|
||||
#if BUILDFLAG(IS_WIN)
|
||||
auto* api_web_contents = api::WebContents::From(GetWebContents());
|
||||
if (api_web_contents) {
|
||||
auto* win =
|
||||
static_cast<NativeWindowViews*>(api_web_contents->owner_window());
|
||||
// When WCO is enabled, undock the devtools if the current dock
|
||||
// position overlaps with the position of window controls to avoid
|
||||
// broken layout.
|
||||
if (win && win->IsWindowControlsOverlayEnabled()) {
|
||||
if (IsAppRTL() && dock_state_ == "left") {
|
||||
dock_state_ = "undocked";
|
||||
} else if (dock_state_ == "right") {
|
||||
dock_state_ = "undocked";
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
std::u16string javascript = base::UTF8ToUTF16(
|
||||
"UI.DockController.instance().setDockSide(\"" + dock_state_ + "\");");
|
||||
GetDevToolsWebContents()->GetPrimaryMainFrame()->ExecuteJavaScript(
|
||||
|
||||
@@ -4,8 +4,10 @@
|
||||
|
||||
#include "shell/common/application_info.h"
|
||||
|
||||
#include "base/i18n/rtl.h"
|
||||
#include "base/no_destructor.h"
|
||||
#include "base/strings/stringprintf.h"
|
||||
#include "chrome/browser/browser_process.h"
|
||||
#include "chrome/common/chrome_version.h"
|
||||
#include "content/public/common/user_agent.h"
|
||||
#include "electron/electron_version.h"
|
||||
@@ -47,4 +49,11 @@ std::string GetApplicationUserAgent() {
|
||||
return content::BuildUserAgentFromProduct(user_agent);
|
||||
}
|
||||
|
||||
bool IsAppRTL() {
|
||||
const std::string& locale = g_browser_process->GetApplicationLocale();
|
||||
base::i18n::TextDirection text_direction =
|
||||
base::i18n::GetTextDirectionForLocaleInStartUp(locale.c_str());
|
||||
return text_direction == base::i18n::RIGHT_TO_LEFT;
|
||||
}
|
||||
|
||||
} // namespace electron
|
||||
|
||||
@@ -25,6 +25,8 @@ std::string GetApplicationVersion();
|
||||
// Returns the user agent of Electron.
|
||||
std::string GetApplicationUserAgent();
|
||||
|
||||
bool IsAppRTL();
|
||||
|
||||
#if BUILDFLAG(IS_WIN)
|
||||
PCWSTR GetRawAppUserModelID();
|
||||
bool GetAppUserModelID(ScopedHString* app_id);
|
||||
|
||||
@@ -704,9 +704,362 @@
|
||||
}
|
||||
}
|
||||
],
|
||||
// Electron does not yet support tab events - we define them here because otherwise extensions crash when
|
||||
// they try to listen for them.
|
||||
"events": [
|
||||
{
|
||||
"name": "onCreated",
|
||||
"deprecated": "chrome.tabs.onCreated is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fired when a tab is created. Note that the tab's URL and tab group membership may not be set at the time this event is fired, but you can listen to onUpdated events so as to be notified when a URL is set or the tab is added to a tab group.",
|
||||
"parameters": [
|
||||
{
|
||||
"$ref": "Tab",
|
||||
"name": "tab",
|
||||
"description": "Details of the tab that was created."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onUpdated",
|
||||
"deprecated": "chrome.tabs.onUpdated is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fired when a tab is updated.",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "integer",
|
||||
"name": "tabId",
|
||||
"minimum": 0
|
||||
},
|
||||
{
|
||||
"type": "object",
|
||||
"name": "changeInfo",
|
||||
"description": "Lists the changes to the state of the tab that was updated.",
|
||||
"properties": {
|
||||
"status": {
|
||||
"$ref": "TabStatus",
|
||||
"optional": true,
|
||||
"description": "The tab's loading status."
|
||||
},
|
||||
"url": {
|
||||
"type": "string",
|
||||
"optional": true,
|
||||
"description": "The tab's URL if it has changed."
|
||||
},
|
||||
"groupId": {
|
||||
"type": "integer",
|
||||
"optional": true,
|
||||
"minimum": -1,
|
||||
"description": "The tab's new group."
|
||||
},
|
||||
"pinned": {
|
||||
"type": "boolean",
|
||||
"optional": true,
|
||||
"description": "The tab's new pinned state."
|
||||
},
|
||||
"audible": {
|
||||
"type": "boolean",
|
||||
"optional": true,
|
||||
"description": "The tab's new audible state."
|
||||
},
|
||||
"discarded": {
|
||||
"type": "boolean",
|
||||
"optional": true,
|
||||
"description": "The tab's new discarded state."
|
||||
},
|
||||
"autoDiscardable": {
|
||||
"type": "boolean",
|
||||
"optional": true,
|
||||
"description": "The tab's new auto-discardable state."
|
||||
},
|
||||
"mutedInfo": {
|
||||
"$ref": "MutedInfo",
|
||||
"optional": true,
|
||||
"description": "The tab's new muted state and the reason for the change."
|
||||
},
|
||||
"favIconUrl": {
|
||||
"type": "string",
|
||||
"optional": true,
|
||||
"description": "The tab's new favicon URL."
|
||||
},
|
||||
"title": {
|
||||
"type": "string",
|
||||
"optional": true,
|
||||
"description": "The tab's new title."
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"$ref": "Tab",
|
||||
"name": "tab",
|
||||
"description": "Gives the state of the tab that was updated."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onMoved",
|
||||
"deprecated": "chrome.tabs.onMoved is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fired when a tab is moved within a window. Only one move event is fired, representing the tab the user directly moved. Move events are not fired for the other tabs that must move in response to the manually-moved tab. This event is not fired when a tab is moved between windows; for details, see $(ref:tabs.onDetached).",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "integer",
|
||||
"name": "tabId",
|
||||
"minimum": 0
|
||||
},
|
||||
{
|
||||
"type": "object",
|
||||
"name": "moveInfo",
|
||||
"properties": {
|
||||
"windowId": {
|
||||
"type": "integer",
|
||||
"minimum": 0
|
||||
},
|
||||
"fromIndex": {
|
||||
"type": "integer",
|
||||
"minimum": 0
|
||||
},
|
||||
"toIndex": {
|
||||
"type": "integer",
|
||||
"minimum": 0
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onSelectionChanged",
|
||||
"deprecated": "chrome.tabs.onSelectionChanged is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fires when the selected tab in a window changes.",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "integer",
|
||||
"name": "tabId",
|
||||
"minimum": 0,
|
||||
"description": "The ID of the tab that has become active."
|
||||
},
|
||||
{
|
||||
"type": "object",
|
||||
"name": "selectInfo",
|
||||
"properties": {
|
||||
"windowId": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "The ID of the window the selected tab changed inside of."
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onActiveChanged",
|
||||
"deprecated": "chrome.tabs.onActiveChanged is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fires when the selected tab in a window changes. Note that the tab's URL may not be set at the time this event fired, but you can listen to $(ref:tabs.onUpdated) events so as to be notified when a URL is set.",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "integer",
|
||||
"name": "tabId",
|
||||
"minimum": 0,
|
||||
"description": "The ID of the tab that has become active."
|
||||
},
|
||||
{
|
||||
"type": "object",
|
||||
"name": "selectInfo",
|
||||
"properties": {
|
||||
"windowId": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "The ID of the window the selected tab changed inside of."
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onActivated",
|
||||
"deprecated": "chrome.tabs.onActivated is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fires when the active tab in a window changes. Note that the tab's URL may not be set at the time this event fired, but you can listen to onUpdated events so as to be notified when a URL is set.",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "object",
|
||||
"name": "activeInfo",
|
||||
"properties": {
|
||||
"tabId": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "The ID of the tab that has become active."
|
||||
},
|
||||
"windowId": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "The ID of the window the active tab changed inside of."
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onHighlightChanged",
|
||||
"deprecated": "chrome.tabs.onHighlightChanged is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fired when the highlighted or selected tabs in a window changes.",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "object",
|
||||
"name": "selectInfo",
|
||||
"properties": {
|
||||
"windowId": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "The window whose tabs changed."
|
||||
},
|
||||
"tabIds": {
|
||||
"type": "array",
|
||||
"name": "tabIds",
|
||||
"items": {
|
||||
"type": "integer",
|
||||
"minimum": 0
|
||||
},
|
||||
"description": "All highlighted tabs in the window."
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onHighlighted",
|
||||
"deprecated": "chrome.tabs.onHighlighted is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fired when the highlighted or selected tabs in a window changes.",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "object",
|
||||
"name": "highlightInfo",
|
||||
"properties": {
|
||||
"windowId": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "The window whose tabs changed."
|
||||
},
|
||||
"tabIds": {
|
||||
"type": "array",
|
||||
"name": "tabIds",
|
||||
"items": {
|
||||
"type": "integer",
|
||||
"minimum": 0
|
||||
},
|
||||
"description": "All highlighted tabs in the window."
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onDetached",
|
||||
"deprecated": "chrome.tabs.onDetached is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fired when a tab is detached from a window; for example, because it was moved between windows.",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "integer",
|
||||
"name": "tabId",
|
||||
"minimum": 0
|
||||
},
|
||||
{
|
||||
"type": "object",
|
||||
"name": "detachInfo",
|
||||
"properties": {
|
||||
"oldWindowId": {
|
||||
"type": "integer",
|
||||
"minimum": 0
|
||||
},
|
||||
"oldPosition": {
|
||||
"type": "integer",
|
||||
"minimum": 0
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onAttached",
|
||||
"deprecated": "chrome.tabs.onAttached is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fired when a tab is attached to a window; for example, because it was moved between windows.",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "integer",
|
||||
"name": "tabId",
|
||||
"minimum": 0
|
||||
},
|
||||
{
|
||||
"type": "object",
|
||||
"name": "attachInfo",
|
||||
"properties": {
|
||||
"newWindowId": {
|
||||
"type": "integer",
|
||||
"minimum": 0
|
||||
},
|
||||
"newPosition": {
|
||||
"type": "integer",
|
||||
"minimum": 0
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onRemoved",
|
||||
"deprecated": "chrome.tabs.onRemoved is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fired when a tab is closed.",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "integer",
|
||||
"name": "tabId",
|
||||
"minimum": 0
|
||||
},
|
||||
{
|
||||
"type": "object",
|
||||
"name": "removeInfo",
|
||||
"properties": {
|
||||
"windowId": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "The window whose tab is closed."
|
||||
},
|
||||
"isWindowClosing": {
|
||||
"type": "boolean",
|
||||
"description": "True when the tab was closed because its parent window was closed."
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onReplaced",
|
||||
"deprecated": "chrome.tabs.onReplaced is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fired when a tab is replaced with another tab due to prerendering or instant.",
|
||||
"parameters": [
|
||||
{
|
||||
"type": "integer",
|
||||
"name": "addedTabId",
|
||||
"minimum": 0
|
||||
},
|
||||
{
|
||||
"type": "integer",
|
||||
"name": "removedTabId",
|
||||
"minimum": 0
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "onZoomChange",
|
||||
"deprecated": "chrome.tabs.onZoomChange is not current supported in Electron",
|
||||
"type": "function",
|
||||
"description": "Fired when a tab is zoomed.",
|
||||
"parameters": [
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
|
||||
#include "base/containers/fixed_flat_map.h"
|
||||
#include "base/strings/string_util.h"
|
||||
#include "base/strings/utf_string_conversion_utils.h"
|
||||
#include "base/strings/utf_string_conversions.h"
|
||||
#include "gin/converter.h"
|
||||
#include "gin/data_object_builder.h"
|
||||
@@ -275,11 +276,18 @@ bool Converter<blink::WebKeyboardEvent>::FromV8(v8::Isolate* isolate,
|
||||
|
||||
if ((out->GetType() == blink::WebInputEvent::Type::kChar ||
|
||||
out->GetType() == blink::WebInputEvent::Type::kRawKeyDown)) {
|
||||
// If the keyCode is e.g. Space or Plus we want to use the character
|
||||
// instead of the keyCode: ' ' instead of 'Space', '+' instead of 'Plus'.
|
||||
std::string character_str;
|
||||
if (str.size() > 1 && domKey.IsCharacter())
|
||||
base::WriteUnicodeCharacter(domKey.ToCharacter(), &character_str);
|
||||
|
||||
// Make sure to not read beyond the buffer in case some bad code doesn't
|
||||
// NULL-terminate it (this is called from plugins).
|
||||
size_t text_length_cap = blink::WebKeyboardEvent::kTextLengthCap;
|
||||
std::u16string text16 = base::UTF8ToUTF16(str);
|
||||
|
||||
std::u16string text16 = character_str.empty()
|
||||
? base::UTF8ToUTF16(str)
|
||||
: base::UTF8ToUTF16(character_str);
|
||||
std::fill_n(out->text, text_length_cap, 0);
|
||||
std::fill_n(out->unmodified_text, text_length_cap, 0);
|
||||
for (size_t i = 0; i < std::min(text_length_cap - 1, text16.size()); ++i) {
|
||||
|
||||
@@ -512,6 +512,13 @@ node::Environment* NodeBindings::CreateEnvironment(
|
||||
electron::fuses::IsOnlyLoadAppFromAsarEnabled()
|
||||
? app_asar_search_paths
|
||||
: search_paths));
|
||||
context->Global()->SetPrivate(
|
||||
context,
|
||||
v8::Private::ForApi(
|
||||
isolate, gin::ConvertToV8(isolate, "appSearchPathsOnlyLoadASAR")
|
||||
.As<v8::String>()),
|
||||
gin::ConvertToV8(isolate,
|
||||
electron::fuses::IsOnlyLoadAppFromAsarEnabled()));
|
||||
}
|
||||
|
||||
base::FilePath resources_path = GetResourcesPath();
|
||||
|
||||
@@ -5,8 +5,8 @@ import * as path from 'path';
|
||||
import { setTimeout } from 'timers/promises';
|
||||
import { ifdescribe } from './lib/spec-helpers';
|
||||
|
||||
// FIXME: The tests are skipped on arm/arm64 and ia32.
|
||||
ifdescribe(!(['arm', 'arm64', 'ia32'].includes(process.arch)))('contentTracing', () => {
|
||||
// FIXME: The tests are skipped on linux arm/arm64
|
||||
ifdescribe(!(['arm', 'arm64'].includes(process.arch)) || (process.platform !== 'linux'))('contentTracing', () => {
|
||||
const record = async (options: TraceConfig | TraceCategoriesAndOptions, outputFilePath: string | undefined, recordTimeInMilliseconds = 1e1) => {
|
||||
await app.whenReady();
|
||||
|
||||
@@ -25,8 +25,6 @@ ifdescribe(!(['arm', 'arm64', 'ia32'].includes(process.arch)))('contentTracing',
|
||||
});
|
||||
|
||||
describe('startRecording', function () {
|
||||
this.timeout(5e3);
|
||||
|
||||
const getFileSizeInKiloBytes = (filePath: string) => {
|
||||
const stats = fs.statSync(filePath);
|
||||
const fileSizeInBytes = stats.size;
|
||||
@@ -84,8 +82,6 @@ ifdescribe(!(['arm', 'arm64', 'ia32'].includes(process.arch)))('contentTracing',
|
||||
});
|
||||
|
||||
describe('stopRecording', function () {
|
||||
this.timeout(5e3);
|
||||
|
||||
it('does not crash on empty string', async () => {
|
||||
const options = {
|
||||
categoryFilter: '*',
|
||||
@@ -120,9 +116,7 @@ ifdescribe(!(['arm', 'arm64', 'ia32'].includes(process.arch)))('contentTracing',
|
||||
|
||||
describe('captured events', () => {
|
||||
it('include V8 samples from the main process', async function () {
|
||||
// This test is flaky on macOS CI.
|
||||
this.retries(3);
|
||||
|
||||
this.timeout(60000);
|
||||
await contentTracing.startRecording({
|
||||
categoryFilter: 'disabled-by-default-v8.cpu_profiler',
|
||||
traceOptions: 'record-until-full'
|
||||
@@ -131,7 +125,7 @@ ifdescribe(!(['arm', 'arm64', 'ia32'].includes(process.arch)))('contentTracing',
|
||||
const start = +new Date();
|
||||
let n = 0;
|
||||
const f = () => {};
|
||||
while (+new Date() - start < 200 || n < 500) {
|
||||
while (+new Date() - start < 200 && n < 500) {
|
||||
await setTimeout(0);
|
||||
f();
|
||||
n++;
|
||||
|
||||
@@ -818,6 +818,20 @@ describe('webContents module', () => {
|
||||
expect(altKey).to.be.false();
|
||||
});
|
||||
|
||||
it('can correctly convert accelerators to key codes', async () => {
|
||||
const keyup = once(ipcMain, 'keyup');
|
||||
w.webContents.sendInputEvent({ keyCode: 'Plus', type: 'char' });
|
||||
w.webContents.sendInputEvent({ keyCode: 'Space', type: 'char' });
|
||||
w.webContents.sendInputEvent({ keyCode: 'Plus', type: 'char' });
|
||||
w.webContents.sendInputEvent({ keyCode: 'Space', type: 'char' });
|
||||
w.webContents.sendInputEvent({ keyCode: 'Plus', type: 'char' });
|
||||
w.webContents.sendInputEvent({ keyCode: 'Plus', type: 'keyUp' });
|
||||
|
||||
await keyup;
|
||||
const inputText = await w.webContents.executeJavaScript('document.getElementById("input").value');
|
||||
expect(inputText).to.equal('+ + +');
|
||||
});
|
||||
|
||||
it('can send char events with modifiers', async () => {
|
||||
const keypress = once(ipcMain, 'keypress');
|
||||
w.webContents.sendInputEvent({ type: 'keyDown', keyCode: 'Z' });
|
||||
|
||||
10
spec/fixtures/pages/key-events.html
vendored
10
spec/fixtures/pages/key-events.html
vendored
@@ -1,11 +1,17 @@
|
||||
<html>
|
||||
<body>
|
||||
<input type="text" id="input" autofocus/>
|
||||
<script type="text/javascript" charset="utf-8">
|
||||
const { ipcRenderer } = require('electron')
|
||||
|
||||
document.onkeydown = function (e) {
|
||||
require('electron').ipcRenderer.send('keydown', e.key, e.code, e.keyCode, e.shiftKey, e.ctrlKey, e.altKey)
|
||||
ipcRenderer.send('keydown', e.key, e.code, e.keyCode, e.shiftKey, e.ctrlKey, e.altKey)
|
||||
}
|
||||
document.onkeypress = function (e) {
|
||||
require('electron').ipcRenderer.send('keypress', e.key, e.code, e.keyCode, e.shiftKey, e.ctrlKey, e.altKey)
|
||||
ipcRenderer.send('keypress', e.key, e.code, e.keyCode, e.shiftKey, e.ctrlKey, e.altKey)
|
||||
}
|
||||
document.onkeyup = function (e) {
|
||||
ipcRenderer.send('keyup', e.key, e.code, e.keyCode, e.shiftKey, e.ctrlKey, e.altKey)
|
||||
}
|
||||
</script>
|
||||
</body>
|
||||
|
||||
1
typings/internal-ambient.d.ts
vendored
1
typings/internal-ambient.d.ts
vendored
@@ -247,6 +247,7 @@ declare namespace NodeJS {
|
||||
// Additional properties
|
||||
_firstFileName?: string;
|
||||
_serviceStartupScript: string;
|
||||
_getOrCreateArchive?: (path: string) => NodeJS.AsarArchive | null;
|
||||
|
||||
helperExecPath: string;
|
||||
mainModule?: NodeJS.Module | undefined;
|
||||
|
||||
@@ -214,9 +214,9 @@
|
||||
vscode-uri "^3.0.7"
|
||||
|
||||
"@electron/typescript-definitions@^8.14.5":
|
||||
version "8.14.5"
|
||||
resolved "https://registry.yarnpkg.com/@electron/typescript-definitions/-/typescript-definitions-8.14.5.tgz#07ffc7dac6008e0f659215e3b88bc0d7c6bc6ece"
|
||||
integrity sha512-68JfMTcj6X7B0dhjhj8lGGnnOlfuiR4f+2UBEtQDYRHfeSuFriKErno3Lh+jAolGSqhw39qr4lLO+FGToVdCew==
|
||||
version "8.14.6"
|
||||
resolved "https://registry.yarnpkg.com/@electron/typescript-definitions/-/typescript-definitions-8.14.6.tgz#78ba1fa8314f06255bb9309791b33c9695ac42ef"
|
||||
integrity sha512-HK70Q3nrp6h4cCxb/P65vFixdJ99vABLIG8TpqU21/fmuHdYboL4zcleWaYhXhU2EwduuOPfORFMrUTdBRc+lw==
|
||||
dependencies:
|
||||
"@types/node" "^11.13.7"
|
||||
chalk "^2.4.2"
|
||||
|
||||
Reference in New Issue
Block a user