chrome-devtools-frontend 1.0.1667564 → 1.0.1669021
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.agents/skills/devtools-ci/SKILL.md +65 -0
- package/.agents/skills/devtools-setting-migration/SKILL.md +290 -0
- package/.agents/skills/gerrit-cli/SKILL.md +59 -0
- package/.agents/skills/gerrit-cli/references/commands.md +93 -0
- package/.agents/skills/gerrit-cli/references/workflows.md +56 -0
- package/.agents/skills/gerrit-cli/scripts/gerrit_client_wrapper.py +47 -0
- package/.agents/skills/gerrit-cli/scripts/import_upstream.py +230 -0
- package/.agents/skills/ui-eng-vision-widget-promoter/SKILL.md +11 -4
- package/.agents/skills/ui-widgets/SKILL.md +25 -1
- package/docs/contributing/infrastructure.md +7 -1
- package/docs/ui_engineering.md +44 -1
- package/front_end/core/common/Settings.ts +11 -4
- package/front_end/core/host/AidaClient.ts +66 -47
- package/front_end/core/host/GcaClient.ts +4 -6
- package/front_end/core/host/ResourceLoader.ts +4 -2
- package/front_end/core/root/Runtime.ts +5 -5
- package/front_end/core/sdk/CSSModel.test.api.ts +102 -0
- package/front_end/core/sdk/CSSModel.ts +3 -2
- package/front_end/core/sdk/ConsoleModel.ts +3 -2
- package/front_end/core/sdk/DebuggerModel.ts +16 -7
- package/front_end/core/sdk/SDKSettings.ts +38 -0
- package/front_end/core/sdk/sdk-meta.ts +0 -120
- package/front_end/core/sdk/sdk.ts +2 -0
- package/front_end/entrypoints/main/MainImpl.ts +10 -3
- package/front_end/foundation/Universe.ts +7 -0
- package/front_end/generated/InspectorBackendCommands.ts +2 -2
- package/front_end/generated/protocol.ts +11 -3
- package/front_end/models/ai_assistance/AiAgent2.ts +1 -1
- package/front_end/models/ai_assistance/AiUtils.ts +67 -4
- package/front_end/models/ai_assistance/BuiltInAi.ts +11 -6
- package/front_end/models/ai_assistance/ChangeManager.ts +17 -1
- package/front_end/models/ai_assistance/StorageItem.ts +26 -5
- package/front_end/models/ai_code_completion/AiCodeCompletion.ts +2 -19
- package/front_end/models/ai_code_generation/AiCodeGeneration.ts +2 -3
- package/front_end/models/javascript_metadata/NativeFunctions.js +22 -9
- package/front_end/models/source_map_scopes/NamesResolver.ts +23 -17
- package/front_end/models/trace/handlers/RendererHandler.ts +20 -4
- package/front_end/models/trace/types/File.ts +1 -0
- package/front_end/models/workspace/UISourceCode.ts +0 -10
- package/front_end/panels/ai_assistance/AiAssistancePanel.ts +61 -182
- package/front_end/panels/ai_assistance/components/ChatInput.ts +25 -8
- package/front_end/panels/ai_assistance/components/ChatMessage.ts +13 -69
- package/front_end/panels/ai_assistance/components/ChatView.ts +14 -8
- package/front_end/panels/ai_assistance/components/chatMessage.css +2 -20
- package/front_end/panels/application/ApplicationPanelSidebar.ts +2 -2
- package/front_end/panels/application/ApplicationPanelTreeElement.ts +41 -3
- package/front_end/panels/application/ServiceWorkerUpdateCycleView.ts +131 -134
- package/front_end/panels/application/ServiceWorkersView.ts +8 -8
- package/front_end/panels/application/application.ts +2 -0
- package/front_end/panels/application/components/AdsView.ts +10 -6
- package/front_end/panels/application/preloading/PreloadingView.ts +53 -45
- package/front_end/panels/application/preloading/components/PreloadingDetailsReportView.ts +111 -119
- package/front_end/panels/application/preloading/components/preloadingDetailsReportView.css +22 -24
- package/front_end/panels/application/serviceWorkerUpdateCycleView.css +105 -102
- package/front_end/panels/common/AiCodeCompletionDisclaimer.ts +107 -96
- package/front_end/panels/common/AiCodeCompletionSummaryToolbar.ts +17 -19
- package/front_end/panels/common/AiCodeCompletionTeaser.ts +6 -6
- package/front_end/panels/common/AiCodeGenerationTeaser.ts +28 -26
- package/front_end/panels/common/common.ts +1 -1
- package/front_end/panels/console/ConsoleInsightTeaser.ts +6 -8
- package/front_end/panels/console/ConsoleView.ts +6 -4
- package/front_end/panels/console/ConsoleViewMessage.ts +1 -1
- package/front_end/panels/console/console-meta.ts +28 -0
- package/front_end/panels/elements/StylesAiCodeCompletionProvider.ts +1 -1
- package/front_end/panels/elements/StylesSidebarPane.ts +3 -2
- package/front_end/panels/emulation/DeviceModeToolbar.ts +2 -2
- package/front_end/panels/emulation/DeviceModeView.ts +63 -104
- package/front_end/panels/emulation/DeviceModeWrapper.ts +18 -4
- package/front_end/panels/explain/components/ConsoleInsight.ts +4 -6
- package/front_end/panels/explain/explain-meta.ts +7 -49
- package/front_end/panels/network/NetworkDataGridNode.ts +1 -1
- package/front_end/panels/network/NetworkLogView.ts +1 -0
- package/front_end/panels/network/OriginalResourceChunkView.ts +340 -0
- package/front_end/panels/network/ResourceChunkView.ts +72 -46
- package/front_end/panels/network/ResourceDirectSocketChunkView.ts +3 -2
- package/front_end/panels/network/ResourceWebSocketFrameView.ts +3 -3
- package/front_end/panels/network/originalResourceChunkView.css +49 -0
- package/front_end/panels/screencast/ScreencastView.ts +401 -260
- package/front_end/panels/screencast/screencastView.css +113 -100
- package/front_end/panels/sensors/LocationsSettingsTab.ts +329 -135
- package/front_end/panels/sensors/locationsSettingsTab.css +78 -4
- package/front_end/panels/settings/AISettingsTab.ts +17 -100
- package/front_end/panels/snippets/ScriptSnippetFileSystem.ts +2 -2
- package/front_end/panels/snippets/SnippetsQuickOpen.ts +4 -4
- package/front_end/panels/sources/AddSourceMapURLDialog.ts +3 -3
- package/front_end/panels/sources/AiCodeCompletionPlugin.ts +4 -3
- package/front_end/panels/sources/BreakpointEditDialog.ts +14 -14
- package/front_end/panels/sources/BreakpointsView.ts +14 -14
- package/front_end/panels/sources/CallStackSidebarPane.ts +6 -6
- package/front_end/panels/sources/CategorizedBreakpointL10n.ts +18 -18
- package/front_end/panels/sources/CoveragePlugin.ts +7 -7
- package/front_end/panels/sources/DebuggerPausedMessage.ts +23 -23
- package/front_end/panels/sources/DebuggerPlugin.ts +31 -31
- package/front_end/panels/sources/FilteredUISourceCodeListProvider.ts +2 -2
- package/front_end/panels/sources/GoToLineQuickOpen.ts +10 -10
- package/front_end/panels/sources/NavigatorView.ts +34 -27
- package/front_end/panels/sources/OutlineQuickOpen.ts +3 -3
- package/front_end/panels/sources/PersistenceActions.ts +9 -9
- package/front_end/panels/sources/ProfilePlugin.ts +1 -1
- package/front_end/panels/sources/ScopeChainSidebarPane.ts +5 -5
- package/front_end/panels/sources/SnippetsPlugin.ts +2 -2
- package/front_end/panels/sources/SourcesNavigator.ts +20 -18
- package/front_end/panels/sources/SourcesPanel.ts +26 -25
- package/front_end/panels/sources/SourcesView.ts +5 -6
- package/front_end/panels/sources/TabbedEditorContainer.ts +3 -3
- package/front_end/panels/sources/ThreadsSidebarPane.ts +1 -1
- package/front_end/panels/sources/UISourceCodeFrame.ts +0 -2
- package/front_end/panels/sources/WatchExpressionsSidebarPane.ts +7 -7
- package/front_end/panels/sources/components/HeadersView.ts +2 -2
- package/front_end/panels/sources/sources-meta.ts +164 -71
- package/front_end/panels/sources/sources.ts +0 -2
- package/front_end/panels/timeline/TimelineHistoryManager.ts +14 -3
- package/front_end/panels/timeline/TimelineLoader.ts +72 -42
- package/front_end/panels/timeline/TimelinePanel.ts +29 -4
- package/front_end/panels/timeline/timelineHistoryManager.css +4 -0
- package/front_end/third_party/chromium/README.chromium +1 -1
- package/front_end/third_party/puppeteer/README.chromium +2 -2
- package/front_end/third_party/puppeteer/package/lib/es5-iife/puppeteer-core-browser.d.ts +187 -1
- package/front_end/third_party/puppeteer/package/lib/es5-iife/puppeteer-core-browser.js +91 -38
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Browser.d.ts +145 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Browser.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Browser.js +0 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Browser.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/BrowserContext.d.ts +0 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/BrowserContext.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/BrowserContext.js +0 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/BrowserContext.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Dialog.d.ts +3 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Dialog.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Dialog.js +8 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Dialog.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/JSHandle.d.ts +0 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/JSHandle.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/JSHandle.js +0 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/JSHandle.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Page.d.ts +1 -3
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Page.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Page.js +0 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Page.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Realm.d.ts +0 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Realm.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Realm.js +0 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/api/Realm.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/bidi/BidiOverCdp.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/bidi/BidiOverCdp.js +2 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/bidi/BidiOverCdp.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/bidi/Browser.d.ts +5 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/bidi/Browser.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/bidi/Browser.js +12 -0
- package/front_end/third_party/puppeteer/package/lib/puppeteer/bidi/Browser.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/bidi/HTTPResponse.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/bidi/HTTPResponse.js +4 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/bidi/HTTPResponse.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/cdp/Browser.d.ts +5 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/cdp/Browser.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/cdp/Browser.js +49 -0
- package/front_end/third_party/puppeteer/package/lib/puppeteer/cdp/Browser.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/common/EventEmitter.d.ts +0 -6
- package/front_end/third_party/puppeteer/package/lib/puppeteer/common/EventEmitter.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/common/EventEmitter.js +0 -6
- package/front_end/third_party/puppeteer/package/lib/puppeteer/common/EventEmitter.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/generated/injected.d.ts +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/generated/injected.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/generated/injected.js +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/generated/injected.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/injected/util.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/injected/util.js +3 -0
- package/front_end/third_party/puppeteer/package/lib/puppeteer/injected/util.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/node/ScreenRecorder.d.ts +0 -3
- package/front_end/third_party/puppeteer/package/lib/puppeteer/node/ScreenRecorder.d.ts.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/node/ScreenRecorder.js +0 -3
- package/front_end/third_party/puppeteer/package/lib/puppeteer/node/ScreenRecorder.js.map +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/revisions.d.ts +3 -3
- package/front_end/third_party/puppeteer/package/lib/puppeteer/revisions.js +3 -3
- package/front_end/third_party/puppeteer/package/lib/puppeteer/util/disposable.d.ts +2 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/util/disposable.js +2 -2
- package/front_end/third_party/puppeteer/package/lib/puppeteer/util/version.d.ts +1 -1
- package/front_end/third_party/puppeteer/package/lib/puppeteer/util/version.js +1 -1
- package/front_end/third_party/puppeteer/package/lib/types.d.ts +187 -1
- package/front_end/third_party/puppeteer/package/package.json +5 -5
- package/front_end/third_party/puppeteer/package/src/api/Browser.ts +155 -2
- package/front_end/third_party/puppeteer/package/src/api/BrowserContext.ts +0 -2
- package/front_end/third_party/puppeteer/package/src/api/Dialog.ts +10 -2
- package/front_end/third_party/puppeteer/package/src/api/JSHandle.ts +0 -2
- package/front_end/third_party/puppeteer/package/src/api/Page.ts +1 -3
- package/front_end/third_party/puppeteer/package/src/api/Realm.ts +0 -1
- package/front_end/third_party/puppeteer/package/src/bidi/BidiOverCdp.ts +4 -2
- package/front_end/third_party/puppeteer/package/src/bidi/Browser.ts +17 -0
- package/front_end/third_party/puppeteer/package/src/bidi/HTTPResponse.ts +5 -4
- package/front_end/third_party/puppeteer/package/src/cdp/Browser.ts +66 -0
- package/front_end/third_party/puppeteer/package/src/common/EventEmitter.ts +0 -6
- package/front_end/third_party/puppeteer/package/src/generated/injected.ts +1 -1
- package/front_end/third_party/puppeteer/package/src/injected/util.ts +4 -1
- package/front_end/third_party/puppeteer/package/src/node/ScreenRecorder.ts +0 -3
- package/front_end/third_party/puppeteer/package/src/revisions.ts +3 -3
- package/front_end/third_party/puppeteer/package/src/util/disposable.ts +2 -2
- package/front_end/third_party/puppeteer/package/src/util/version.ts +1 -1
- package/front_end/ui/components/text_editor/AiCodeCompletionProvider.ts +9 -7
- package/front_end/ui/components/text_editor/AiCodeGenerationProvider.ts +7 -8
- package/front_end/ui/legacy/Dialog.ts +103 -4
- package/front_end/ui/legacy/InspectorView.ts +1 -5
- package/front_end/ui/legacy/PopoverHelper.ts +5 -5
- package/front_end/ui/legacy/TabbedPane.ts +7 -2
- package/front_end/ui/legacy/components/cookie_table/CookiesTable.ts +40 -24
- package/front_end/ui/legacy/components/data_grid/DataGrid.ts +1 -0
- package/front_end/ui/legacy/components/data_grid/DataGridElement.ts +8 -4
- package/front_end/ui/legacy/components/perf_ui/FlameChart.ts +14 -7
- package/front_end/ui/legacy/components/quick_open/CommandMenu.ts +11 -1
- package/front_end/ui/visual_logging/KnownContextValues.ts +3 -0
- package/package.json +1 -1
- package/front_end/panels/sources/AiWarningInfobarPlugin.ts +0 -78
|
@@ -2,20 +2,21 @@
|
|
|
2
2
|
// Use of this source code is governed by a BSD-style license that can be
|
|
3
3
|
// found in the LICENSE file.
|
|
4
4
|
|
|
5
|
-
/* eslint-disable @devtools/no-imperative-dom-api */
|
|
6
|
-
|
|
7
5
|
import * as Common from '../../core/common/common.js';
|
|
8
6
|
import * as Host from '../../core/host/host.js';
|
|
9
7
|
import * as i18n from '../../core/i18n/i18n.js';
|
|
10
8
|
import type * as Platform from '../../core/platform/platform.js';
|
|
11
9
|
import * as SDK from '../../core/sdk/sdk.js';
|
|
12
10
|
import * as Protocol from '../../generated/protocol.js';
|
|
13
|
-
import
|
|
11
|
+
import * as Buttons from '../../ui/components/buttons/buttons.js';
|
|
14
12
|
import * as UI from '../../ui/legacy/legacy.js';
|
|
13
|
+
import {Directives, html, nothing, render} from '../../ui/lit/lit.js';
|
|
15
14
|
|
|
16
15
|
import {InputModel} from './InputModel.js';
|
|
17
16
|
import screencastViewStyles from './screencastView.css.js';
|
|
18
17
|
|
|
18
|
+
const {ref, styleMap, classMap} = Directives;
|
|
19
|
+
|
|
19
20
|
const UIStrings = {
|
|
20
21
|
/**
|
|
21
22
|
* @description Accessible alt text for the Screencast canvas rendering of the debug target webpage.
|
|
@@ -62,7 +63,186 @@ interface Point {
|
|
|
62
63
|
y: number;
|
|
63
64
|
}
|
|
64
65
|
|
|
65
|
-
export
|
|
66
|
+
export interface CanvasRenderingInput {
|
|
67
|
+
screencastImage?: HTMLImageElement;
|
|
68
|
+
screenOffsetTop: number;
|
|
69
|
+
screenZoom: number;
|
|
70
|
+
imageZoom: number;
|
|
71
|
+
highlightModel?: Protocol.DOM.BoxModel|null;
|
|
72
|
+
highlightConfig?: Protocol.Overlay.HighlightConfig|null;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
export interface ViewInput extends CanvasRenderingInput {
|
|
76
|
+
navigationUrl: string;
|
|
77
|
+
canGoBack: boolean;
|
|
78
|
+
canGoForward: boolean;
|
|
79
|
+
isTouchEmulated: boolean;
|
|
80
|
+
glassPaneText: string;
|
|
81
|
+
glassPaneHidden: boolean;
|
|
82
|
+
isViewportHidden: boolean;
|
|
83
|
+
viewportWidth?: string;
|
|
84
|
+
viewportHeight?: string;
|
|
85
|
+
progressPercent: number;
|
|
86
|
+
elementTitleData?: ElementTitleData;
|
|
87
|
+
onBackClick: () => void;
|
|
88
|
+
onForwardClick: () => void;
|
|
89
|
+
onReloadClick: () => void;
|
|
90
|
+
onUrlInputKeyUp: (event: KeyboardEvent) => void;
|
|
91
|
+
onToggleTouch: (emulateTouch: boolean) => void;
|
|
92
|
+
onCanvasMouseEvent: (event: MouseEvent) => void;
|
|
93
|
+
onCanvasWheel: (event: WheelEvent) => void;
|
|
94
|
+
onCanvasKeyEvent: (event: KeyboardEvent) => void;
|
|
95
|
+
onCanvasContextMenu: (event: Event) => void;
|
|
96
|
+
onCanvasBlur: () => void;
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
export interface ElementTitleData {
|
|
100
|
+
visible: boolean;
|
|
101
|
+
tagName?: string;
|
|
102
|
+
attribute?: string;
|
|
103
|
+
width?: string;
|
|
104
|
+
height?: string;
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
export interface ViewOutput {
|
|
108
|
+
focusUrlInput?: () => void;
|
|
109
|
+
focusCanvas?: () => void;
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
export type View = (input: ViewInput, output: ViewOutput, target: HTMLElement) => void;
|
|
113
|
+
|
|
114
|
+
export const DEFAULT_VIEW = (input: ViewInput, output: ViewOutput, target: HTMLElement): void => {
|
|
115
|
+
let canvasElement: HTMLCanvasElement|null = null;
|
|
116
|
+
// clang-format off
|
|
117
|
+
render(html`
|
|
118
|
+
<style>${screencastViewStyles}</style>
|
|
119
|
+
<div class="screencast-navigation">
|
|
120
|
+
<devtools-button class="navigation"
|
|
121
|
+
.data=${{
|
|
122
|
+
variant: Buttons.Button.Variant.TOOLBAR,
|
|
123
|
+
iconName: 'arrow-back',
|
|
124
|
+
disabled: !input.canGoBack,
|
|
125
|
+
title: i18nString(UIStrings.back),
|
|
126
|
+
accessibleLabel: i18nString(UIStrings.back),
|
|
127
|
+
} as Buttons.Button.ButtonData}
|
|
128
|
+
@click=${input.onBackClick}></devtools-button>
|
|
129
|
+
<devtools-button class="navigation"
|
|
130
|
+
.data=${{
|
|
131
|
+
variant: Buttons.Button.Variant.TOOLBAR,
|
|
132
|
+
iconName: 'arrow-forward',
|
|
133
|
+
disabled: !input.canGoForward,
|
|
134
|
+
title: i18nString(UIStrings.forward),
|
|
135
|
+
accessibleLabel: i18nString(UIStrings.forward),
|
|
136
|
+
} as Buttons.Button.ButtonData}
|
|
137
|
+
@click=${input.onForwardClick}></devtools-button>
|
|
138
|
+
<devtools-button class="navigation"
|
|
139
|
+
.data=${{
|
|
140
|
+
variant: Buttons.Button.Variant.TOOLBAR,
|
|
141
|
+
iconName: 'refresh',
|
|
142
|
+
title: i18nString(UIStrings.reload),
|
|
143
|
+
accessibleLabel: i18nString(UIStrings.reload),
|
|
144
|
+
} as Buttons.Button.ButtonData}
|
|
145
|
+
@click=${input.onReloadClick}></devtools-button>
|
|
146
|
+
<input type="text" class="harmony-input" aria-label=${i18nString(UIStrings.addressBar)}
|
|
147
|
+
.value=${input.navigationUrl}
|
|
148
|
+
@keyup=${input.onUrlInputKeyUp}
|
|
149
|
+
${ref(el => {
|
|
150
|
+
if (el instanceof HTMLInputElement) {
|
|
151
|
+
output.focusUrlInput = (): void => {
|
|
152
|
+
el.focus();
|
|
153
|
+
el.select();
|
|
154
|
+
};
|
|
155
|
+
}
|
|
156
|
+
})}
|
|
157
|
+
/>
|
|
158
|
+
<devtools-button
|
|
159
|
+
.data=${{
|
|
160
|
+
variant: Buttons.Button.Variant.TOOLBAR,
|
|
161
|
+
iconName: 'mouse',
|
|
162
|
+
toggledIconName: 'mouse',
|
|
163
|
+
disabled: !input.isTouchEmulated,
|
|
164
|
+
toggled: !input.isTouchEmulated,
|
|
165
|
+
toggleType: Buttons.Button.ToggleType.PRIMARY,
|
|
166
|
+
title: i18nString(UIStrings.mouseInput),
|
|
167
|
+
accessibleLabel: i18nString(UIStrings.mouseInput),
|
|
168
|
+
} as Buttons.Button.ButtonData}
|
|
169
|
+
@click=${() => input.onToggleTouch(false)}></devtools-button>
|
|
170
|
+
<devtools-button
|
|
171
|
+
.data=${{
|
|
172
|
+
variant: Buttons.Button.Variant.TOOLBAR,
|
|
173
|
+
iconName: 'touch-app',
|
|
174
|
+
toggledIconName: 'touch-app',
|
|
175
|
+
disabled: input.isTouchEmulated,
|
|
176
|
+
toggled: input.isTouchEmulated,
|
|
177
|
+
toggleType: Buttons.Button.ToggleType.PRIMARY,
|
|
178
|
+
title: i18nString(UIStrings.touchInput),
|
|
179
|
+
accessibleLabel: i18nString(UIStrings.touchInput),
|
|
180
|
+
} as Buttons.Button.ButtonData}
|
|
181
|
+
@click=${() => input.onToggleTouch(true)}></devtools-button>
|
|
182
|
+
<div class="progress" style=${styleMap({width: `${(input.progressPercent ?? 0) * 100}%`})}></div>
|
|
183
|
+
</div>
|
|
184
|
+
<div
|
|
185
|
+
class=${classMap({
|
|
186
|
+
'screencast-viewport': true,
|
|
187
|
+
hidden: input.isViewportHidden,
|
|
188
|
+
})}
|
|
189
|
+
style=${styleMap({
|
|
190
|
+
width: input.viewportWidth,
|
|
191
|
+
height: input.viewportHeight,
|
|
192
|
+
})}>
|
|
193
|
+
<div class=${classMap({
|
|
194
|
+
'screencast-canvas-container': true,
|
|
195
|
+
touchable: input.isTouchEmulated,
|
|
196
|
+
})}>
|
|
197
|
+
<div class=${classMap({
|
|
198
|
+
'screencast-glasspane': true,
|
|
199
|
+
fill: true,
|
|
200
|
+
hidden: input.glassPaneHidden,
|
|
201
|
+
})}>${input.glassPaneText}</div>
|
|
202
|
+
<canvas aria-label=${i18nString(UIStrings.screencastViewOfDebugTarget)} tabindex="0"
|
|
203
|
+
@mousedown=${input.onCanvasMouseEvent}
|
|
204
|
+
@mouseup=${input.onCanvasMouseEvent}
|
|
205
|
+
@mousemove=${input.onCanvasMouseEvent}
|
|
206
|
+
@wheel=${input.onCanvasWheel}
|
|
207
|
+
@click=${input.onCanvasMouseEvent}
|
|
208
|
+
@contextmenu=${input.onCanvasContextMenu}
|
|
209
|
+
@keydown=${input.onCanvasKeyEvent}
|
|
210
|
+
@keyup=${input.onCanvasKeyEvent}
|
|
211
|
+
@keypress=${input.onCanvasKeyEvent}
|
|
212
|
+
@blur=${input.onCanvasBlur}
|
|
213
|
+
${ref(el => {
|
|
214
|
+
if (el instanceof HTMLCanvasElement) {
|
|
215
|
+
output.focusCanvas = (): void => el.focus();
|
|
216
|
+
canvasElement = el;
|
|
217
|
+
ScreencastView.repaintScreencastCanvas(el, input);
|
|
218
|
+
}
|
|
219
|
+
})}></canvas>
|
|
220
|
+
<div
|
|
221
|
+
class=${classMap({
|
|
222
|
+
'screencast-element-title': true,
|
|
223
|
+
monospace: true,
|
|
224
|
+
hidden: !input.elementTitleData?.visible,
|
|
225
|
+
})}
|
|
226
|
+
${ref(el => {
|
|
227
|
+
if (el instanceof HTMLElement && canvasElement && input.elementTitleData?.visible && !el.classList.contains('hidden')) {
|
|
228
|
+
ScreencastView.clampTooltipPosition(canvasElement, el, input.highlightModel);
|
|
229
|
+
}
|
|
230
|
+
})}>
|
|
231
|
+
<span class="screencast-tag-name">${input.elementTitleData?.tagName ?? nothing}</span>
|
|
232
|
+
<span class="screencast-attribute">${input.elementTitleData?.attribute ?? nothing}</span>
|
|
233
|
+
<span class="screencast-dimension"> <span>${input.elementTitleData?.width ?? nothing}</span> × <span>${input.elementTitleData?.height ?? nothing}</span>
|
|
234
|
+
</span>
|
|
235
|
+
</div>
|
|
236
|
+
</div>
|
|
237
|
+
</div>
|
|
238
|
+
`, target);
|
|
239
|
+
// clang-format on
|
|
240
|
+
};
|
|
241
|
+
|
|
242
|
+
export class ScreencastView extends UI.Widget.Widget implements SDK.OverlayModel.Highlighter {
|
|
243
|
+
readonly #view: View;
|
|
244
|
+
#viewOutput: ViewOutput;
|
|
245
|
+
|
|
66
246
|
private readonly screenCaptureModel: SDK.ScreenCaptureModel.ScreenCaptureModel;
|
|
67
247
|
private domModel: SDK.DOMModel.DOMModel|null;
|
|
68
248
|
private readonly overlayModel: SDK.OverlayModel.OverlayModel|null;
|
|
@@ -76,43 +256,38 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
76
256
|
private screenOffsetTop: number;
|
|
77
257
|
private pageScaleFactor: number;
|
|
78
258
|
private imageElement!: HTMLImageElement;
|
|
79
|
-
private viewportElement!: HTMLElement;
|
|
80
|
-
private glassPaneElement!: HTMLElement;
|
|
81
|
-
private canvasElement!: HTMLCanvasElement;
|
|
82
|
-
private titleElement!: HTMLElement;
|
|
83
|
-
private context!: CanvasRenderingContext2D;
|
|
84
259
|
private imageZoom: number;
|
|
85
|
-
private tagNameElement!: HTMLElement;
|
|
86
|
-
private attributeElement!: HTMLElement;
|
|
87
|
-
private nodeWidthElement!: HTMLElement;
|
|
88
|
-
private nodeHeightElement!: HTMLElement;
|
|
89
260
|
private model!: Protocol.DOM.BoxModel|null;
|
|
90
261
|
private highlightConfig!: Protocol.Overlay.HighlightConfig|null;
|
|
91
|
-
private navigationUrl!: HTMLInputElement;
|
|
92
|
-
private navigationBack!: HTMLButtonElement;
|
|
93
|
-
private navigationForward!: HTMLButtonElement;
|
|
94
|
-
private canvasContainerElement?: HTMLElement;
|
|
95
|
-
private checkerboardPattern?: CanvasPattern|null;
|
|
96
262
|
private targetInactive?: boolean;
|
|
97
263
|
private deferredCasting?: number;
|
|
98
264
|
private highlightNode?: SDK.DOMModel.DOMNode|null;
|
|
99
265
|
private config?: Protocol.Overlay.HighlightConfig|null;
|
|
100
266
|
private node?: SDK.DOMModel.DOMNode|null;
|
|
101
267
|
private inspectModeConfig?: Protocol.Overlay.HighlightConfig|null;
|
|
102
|
-
private navigationBar?: HTMLElement;
|
|
103
|
-
private navigationReload?: HTMLElement;
|
|
104
268
|
private navigationProgressBar?: ProgressTracker;
|
|
105
|
-
private touchInputToggle?: HTMLButtonElement;
|
|
106
|
-
private mouseInputToggle?: HTMLButtonElement;
|
|
107
|
-
private touchInputToggleIcon?: Icon;
|
|
108
|
-
private mouseInputToggleIcon?: Icon;
|
|
109
269
|
private historyIndex?: number;
|
|
110
270
|
private historyEntries?: Protocol.Page.NavigationEntry[];
|
|
111
271
|
private isCasting = false;
|
|
112
272
|
private screencastOperationId?: number;
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
273
|
+
|
|
274
|
+
#navigationUrlText = '';
|
|
275
|
+
#canGoBack = false;
|
|
276
|
+
#canGoForward = false;
|
|
277
|
+
#isTouchEmulated = false;
|
|
278
|
+
#glassPaneText = '';
|
|
279
|
+
#glassPaneHidden = true;
|
|
280
|
+
#isViewportHidden = true;
|
|
281
|
+
#viewportWidth = '';
|
|
282
|
+
#viewportHeight = '';
|
|
283
|
+
#progressPercent = 0;
|
|
284
|
+
#elementTitleData: ElementTitleData = {visible: false};
|
|
285
|
+
|
|
286
|
+
constructor(screenCaptureModel: SDK.ScreenCaptureModel.ScreenCaptureModel, element?: HTMLElement,
|
|
287
|
+
view: View = DEFAULT_VIEW) {
|
|
288
|
+
super(element);
|
|
289
|
+
this.#view = view;
|
|
290
|
+
this.#viewOutput = {};
|
|
116
291
|
this.screenCaptureModel = screenCaptureModel;
|
|
117
292
|
this.domModel = screenCaptureModel.target().model(SDK.DOMModel.DOMModel);
|
|
118
293
|
this.overlayModel = screenCaptureModel.target().model(SDK.OverlayModel.OverlayModel);
|
|
@@ -132,48 +307,58 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
132
307
|
}
|
|
133
308
|
|
|
134
309
|
initialize(): void {
|
|
135
|
-
this.element.classList.add('screencast');
|
|
136
|
-
|
|
137
310
|
this.createNavigationBar();
|
|
138
|
-
this.viewportElement = this.element.createChild('div', 'screencast-viewport hidden');
|
|
139
|
-
this.canvasContainerElement = this.viewportElement.createChild('div', 'screencast-canvas-container');
|
|
140
|
-
this.glassPaneElement = this.canvasContainerElement.createChild('div', 'screencast-glasspane fill hidden');
|
|
141
|
-
this.canvasElement = this.canvasContainerElement.createChild('canvas');
|
|
142
|
-
UI.ARIAUtils.setLabel(this.canvasElement, i18nString(UIStrings.screencastViewOfDebugTarget));
|
|
143
|
-
this.canvasElement.tabIndex = 0;
|
|
144
|
-
this.canvasElement.addEventListener('mousedown', this.handleMouseEvent.bind(this), false);
|
|
145
|
-
this.canvasElement.addEventListener('mouseup', this.handleMouseEvent.bind(this), false);
|
|
146
|
-
this.canvasElement.addEventListener('mousemove', this.handleMouseEvent.bind(this), false);
|
|
147
|
-
this.canvasElement.addEventListener('wheel', this.handleWheelEvent.bind(this), false);
|
|
148
|
-
this.canvasElement.addEventListener('click', this.handleMouseEvent.bind(this), false);
|
|
149
|
-
this.canvasElement.addEventListener('contextmenu', this.handleContextMenuEvent.bind(this), false);
|
|
150
|
-
this.canvasElement.addEventListener('keydown', this.handleKeyEvent.bind(this), false);
|
|
151
|
-
this.canvasElement.addEventListener('keyup', this.handleKeyEvent.bind(this), false);
|
|
152
|
-
this.canvasElement.addEventListener('keypress', this.handleKeyEvent.bind(this), false);
|
|
153
|
-
this.canvasElement.addEventListener('blur', this.handleBlurEvent.bind(this), false);
|
|
154
|
-
this.titleElement = this.canvasContainerElement.createChild('div', 'screencast-element-title monospace hidden');
|
|
155
|
-
this.tagNameElement = this.titleElement.createChild('span', 'screencast-tag-name');
|
|
156
|
-
this.attributeElement = this.titleElement.createChild('span', 'screencast-attribute');
|
|
157
|
-
UI.UIUtils.createTextChild(this.titleElement, ' ');
|
|
158
|
-
const dimension = this.titleElement.createChild('span', 'screencast-dimension');
|
|
159
|
-
this.nodeWidthElement = dimension.createChild('span');
|
|
160
|
-
UI.UIUtils.createTextChild(dimension, ' × ');
|
|
161
|
-
this.nodeHeightElement = dimension.createChild('span');
|
|
162
|
-
this.titleElement.style.top = '0';
|
|
163
|
-
this.titleElement.style.left = '0';
|
|
164
|
-
|
|
165
311
|
this.imageElement = new Image();
|
|
166
|
-
this.context = this.canvasElement.getContext('2d') as CanvasRenderingContext2D;
|
|
167
|
-
this.checkerboardPattern = this.createCheckerboardPattern(this.context);
|
|
168
|
-
|
|
169
312
|
this.shortcuts[UI.KeyboardShortcut.KeyboardShortcut.makeKey('l', UI.KeyboardShortcut.Modifiers.Ctrl.value)] =
|
|
170
313
|
this.focusNavigationBar.bind(this);
|
|
171
|
-
|
|
172
314
|
SDK.TargetManager.TargetManager.instance().addEventListener(
|
|
173
315
|
SDK.TargetManager.Events.SUSPEND_STATE_CHANGED, this.onSuspendStateChange, this);
|
|
174
316
|
this.updateGlasspane();
|
|
175
317
|
}
|
|
176
318
|
|
|
319
|
+
override wasShown(): void {
|
|
320
|
+
super.wasShown();
|
|
321
|
+
if (this.deferredCasting) {
|
|
322
|
+
clearTimeout(this.deferredCasting);
|
|
323
|
+
delete this.deferredCasting;
|
|
324
|
+
}
|
|
325
|
+
this.deferredCasting = window.setTimeout(this.startCasting.bind(this), 100);
|
|
326
|
+
this.requestUpdate();
|
|
327
|
+
}
|
|
328
|
+
|
|
329
|
+
override performUpdate(): void {
|
|
330
|
+
const input: ViewInput = {
|
|
331
|
+
navigationUrl: this.#navigationUrlText,
|
|
332
|
+
canGoBack: this.#canGoBack,
|
|
333
|
+
canGoForward: this.#canGoForward,
|
|
334
|
+
isTouchEmulated: this.#isTouchEmulated,
|
|
335
|
+
glassPaneText: this.#glassPaneText,
|
|
336
|
+
glassPaneHidden: this.#glassPaneHidden,
|
|
337
|
+
isViewportHidden: this.#isViewportHidden,
|
|
338
|
+
viewportWidth: this.#viewportWidth,
|
|
339
|
+
viewportHeight: this.#viewportHeight,
|
|
340
|
+
progressPercent: this.#progressPercent,
|
|
341
|
+
elementTitleData: this.#elementTitleData,
|
|
342
|
+
screencastImage: this.imageElement,
|
|
343
|
+
screenOffsetTop: this.screenOffsetTop,
|
|
344
|
+
screenZoom: this.screenZoom,
|
|
345
|
+
imageZoom: this.imageZoom,
|
|
346
|
+
highlightModel: this.model,
|
|
347
|
+
highlightConfig: this.config,
|
|
348
|
+
onBackClick: () => this.navigateToHistoryEntry(-1),
|
|
349
|
+
onForwardClick: () => this.navigateToHistoryEntry(1),
|
|
350
|
+
onReloadClick: () => this.navigateReload(),
|
|
351
|
+
onUrlInputKeyUp: (e: KeyboardEvent) => this.navigationUrlKeyUp(e),
|
|
352
|
+
onToggleTouch: (emulateTouch: boolean) => this.#toggleTouchEmulation(emulateTouch),
|
|
353
|
+
onCanvasMouseEvent: (e: MouseEvent) => void this.handleMouseEvent(e),
|
|
354
|
+
onCanvasWheel: (e: WheelEvent) => void this.handleWheelEvent(e),
|
|
355
|
+
onCanvasKeyEvent: (e: KeyboardEvent) => this.handleKeyEvent(e),
|
|
356
|
+
onCanvasContextMenu: (e: Event) => this.handleContextMenuEvent(e),
|
|
357
|
+
onCanvasBlur: () => this.handleBlurEvent(),
|
|
358
|
+
};
|
|
359
|
+
this.#view(input, this.#viewOutput, this.contentElement);
|
|
360
|
+
}
|
|
361
|
+
|
|
177
362
|
override willHide(): void {
|
|
178
363
|
super.willHide();
|
|
179
364
|
this.stopCasting();
|
|
@@ -229,6 +414,7 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
229
414
|
for (const emulationModel of SDK.TargetManager.TargetManager.instance().models(SDK.EmulationModel.EmulationModel)) {
|
|
230
415
|
void emulationModel.overrideEmulateTouch(false);
|
|
231
416
|
}
|
|
417
|
+
this.#isTouchEmulated = false;
|
|
232
418
|
if (this.overlayModel) {
|
|
233
419
|
this.overlayModel.setHighlighter(null);
|
|
234
420
|
}
|
|
@@ -243,18 +429,26 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
243
429
|
|
|
244
430
|
const deviceSizeRatio = metadata.deviceHeight / metadata.deviceWidth;
|
|
245
431
|
const dimensionsCSS = this.viewportDimensions();
|
|
432
|
+
if (dimensionsCSS.width <= 0 || dimensionsCSS.height <= 0) {
|
|
433
|
+
return;
|
|
434
|
+
}
|
|
246
435
|
|
|
247
436
|
this.imageZoom = Math.min(
|
|
248
437
|
dimensionsCSS.width / this.imageElement.naturalWidth,
|
|
249
438
|
dimensionsCSS.height / (this.imageElement.naturalWidth * deviceSizeRatio));
|
|
250
|
-
this.viewportElement.classList.remove('hidden');
|
|
251
439
|
const bordersSize = BORDERS_SIZE;
|
|
252
440
|
if (this.imageZoom < 1.01 / window.devicePixelRatio) {
|
|
253
441
|
this.imageZoom = 1 / window.devicePixelRatio;
|
|
254
442
|
}
|
|
255
443
|
this.screenZoom = this.imageElement.naturalWidth * this.imageZoom / metadata.deviceWidth;
|
|
256
|
-
|
|
257
|
-
|
|
444
|
+
const newWidth = metadata.deviceWidth * this.screenZoom + bordersSize + 'px';
|
|
445
|
+
const newHeight = metadata.deviceHeight * this.screenZoom + bordersSize + 'px';
|
|
446
|
+
if (this.#viewportWidth !== newWidth || this.#viewportHeight !== newHeight || this.#isViewportHidden) {
|
|
447
|
+
this.#viewportWidth = newWidth;
|
|
448
|
+
this.#viewportHeight = newHeight;
|
|
449
|
+
this.#isViewportHidden = false;
|
|
450
|
+
this.requestUpdate();
|
|
451
|
+
}
|
|
258
452
|
|
|
259
453
|
const data = this.highlightNode ? {node: this.highlightNode} : {clear: true};
|
|
260
454
|
void this.updateHighlightInOverlayAndRepaint(data, this.highlightConfig);
|
|
@@ -263,7 +457,7 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
263
457
|
}
|
|
264
458
|
|
|
265
459
|
private isGlassPaneActive(): boolean {
|
|
266
|
-
return !this
|
|
460
|
+
return !this.#glassPaneHidden;
|
|
267
461
|
}
|
|
268
462
|
|
|
269
463
|
private screencastVisibilityChanged(visible: boolean): void {
|
|
@@ -281,14 +475,20 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
281
475
|
}
|
|
282
476
|
|
|
283
477
|
private updateGlasspane(): void {
|
|
478
|
+
let newText = '';
|
|
479
|
+
let newHidden = true;
|
|
284
480
|
if (this.targetInactive) {
|
|
285
|
-
|
|
286
|
-
|
|
481
|
+
newText = i18nString(UIStrings.theTabIsInactive);
|
|
482
|
+
newHidden = false;
|
|
287
483
|
} else if (SDK.TargetManager.TargetManager.instance().allTargetsSuspended()) {
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
}
|
|
291
|
-
|
|
484
|
+
newText = i18nString(UIStrings.profilingInProgress);
|
|
485
|
+
newHidden = false;
|
|
486
|
+
}
|
|
487
|
+
|
|
488
|
+
if (this.#glassPaneText !== newText || this.#glassPaneHidden !== newHidden) {
|
|
489
|
+
this.#glassPaneText = newText;
|
|
490
|
+
this.#glassPaneHidden = newHidden;
|
|
491
|
+
this.requestUpdate();
|
|
292
492
|
}
|
|
293
493
|
}
|
|
294
494
|
|
|
@@ -306,7 +506,7 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
306
506
|
}
|
|
307
507
|
event.preventDefault();
|
|
308
508
|
if (event.type === 'mousedown') {
|
|
309
|
-
this.
|
|
509
|
+
this.#viewOutput.focusCanvas?.();
|
|
310
510
|
}
|
|
311
511
|
return;
|
|
312
512
|
}
|
|
@@ -359,11 +559,11 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
359
559
|
this.inputModel.emitKeyEvent(event);
|
|
360
560
|
}
|
|
361
561
|
event.consume();
|
|
362
|
-
this.
|
|
562
|
+
this.#viewOutput.focusCanvas?.();
|
|
363
563
|
}
|
|
364
564
|
|
|
365
565
|
private handleBlurEvent(): void {
|
|
366
|
-
if (this.inputModel && this
|
|
566
|
+
if (this.inputModel && !this.#isTouchEmulated) {
|
|
367
567
|
const event = new MouseEvent('mouseup');
|
|
368
568
|
this.inputModel.emitMouseEvent(event, this.screenOffsetTop, this.screenZoom);
|
|
369
569
|
}
|
|
@@ -416,20 +616,25 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
416
616
|
this.model = null;
|
|
417
617
|
this.config = null;
|
|
418
618
|
this.node = null;
|
|
419
|
-
this.
|
|
420
|
-
|
|
619
|
+
if (this.#elementTitleData.visible) {
|
|
620
|
+
this.#elementTitleData = {visible: false};
|
|
621
|
+
}
|
|
622
|
+
this.drawElementTitle();
|
|
623
|
+
this.requestUpdate();
|
|
421
624
|
return;
|
|
422
625
|
}
|
|
423
626
|
|
|
424
627
|
this.node = node;
|
|
425
628
|
void node.boxModel().then(model => {
|
|
426
629
|
if (!model || !this.pageScaleFactor) {
|
|
427
|
-
this.
|
|
630
|
+
this.drawElementTitle();
|
|
631
|
+
this.requestUpdate();
|
|
428
632
|
return;
|
|
429
633
|
}
|
|
430
634
|
this.model = this.scaleModel(model);
|
|
431
635
|
this.config = config;
|
|
432
|
-
this.
|
|
636
|
+
this.drawElementTitle();
|
|
637
|
+
this.requestUpdate();
|
|
433
638
|
});
|
|
434
639
|
}
|
|
435
640
|
|
|
@@ -448,31 +653,25 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
448
653
|
return model;
|
|
449
654
|
}
|
|
450
655
|
|
|
451
|
-
|
|
452
|
-
const
|
|
453
|
-
|
|
656
|
+
static repaintScreencastCanvas(el: HTMLCanvasElement, input: CanvasRenderingInput): void {
|
|
657
|
+
const context = el.getContext('2d');
|
|
658
|
+
if (!context) {
|
|
659
|
+
return;
|
|
660
|
+
}
|
|
454
661
|
|
|
455
|
-
const
|
|
456
|
-
const
|
|
457
|
-
this.canvasElement.width = window.devicePixelRatio * canvasWidth;
|
|
458
|
-
this.canvasElement.height = window.devicePixelRatio * canvasHeight;
|
|
662
|
+
const model = input.highlightModel;
|
|
663
|
+
const config = input.highlightConfig;
|
|
459
664
|
|
|
460
|
-
|
|
461
|
-
|
|
665
|
+
const canvasWidth = el.getBoundingClientRect().width;
|
|
666
|
+
const canvasHeight = el.getBoundingClientRect().height;
|
|
667
|
+
el.width = window.devicePixelRatio * canvasWidth;
|
|
668
|
+
el.height = window.devicePixelRatio * canvasHeight;
|
|
462
669
|
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
if (this.checkerboardPattern) {
|
|
466
|
-
this.context.fillStyle = this.checkerboardPattern;
|
|
467
|
-
}
|
|
468
|
-
this.context.fillRect(0, 0, canvasWidth, this.screenOffsetTop * this.screenZoom);
|
|
469
|
-
this.context.fillRect(
|
|
470
|
-
0, this.screenOffsetTop * this.screenZoom + this.imageElement.naturalHeight * this.imageZoom, canvasWidth,
|
|
471
|
-
canvasHeight);
|
|
472
|
-
this.context.restore();
|
|
670
|
+
context.save();
|
|
671
|
+
context.scale(window.devicePixelRatio, window.devicePixelRatio);
|
|
473
672
|
|
|
474
673
|
if (model && config) {
|
|
475
|
-
|
|
674
|
+
context.save();
|
|
476
675
|
const quads = [];
|
|
477
676
|
const isTransparent = (color: Protocol.DOM.RGBA): boolean => Boolean(color.a && color.a === 0);
|
|
478
677
|
if (model.content && config.contentColor && !isTransparent(config.contentColor)) {
|
|
@@ -489,25 +688,23 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
489
688
|
}
|
|
490
689
|
|
|
491
690
|
for (let i = quads.length - 1; i > 0; --i) {
|
|
492
|
-
|
|
691
|
+
ScreencastView.drawOutlinedQuadWithClip(context, quads[i].quad, quads[i - 1].quad, quads[i].color);
|
|
493
692
|
}
|
|
494
693
|
if (quads.length > 0) {
|
|
495
|
-
|
|
694
|
+
ScreencastView.drawOutlinedQuad(context, quads[0].quad, quads[0].color);
|
|
496
695
|
}
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
this.drawElementTitle();
|
|
500
|
-
|
|
501
|
-
this.context.globalCompositeOperation = 'destination-over';
|
|
696
|
+
context.globalCompositeOperation = 'destination-over';
|
|
502
697
|
}
|
|
503
698
|
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
699
|
+
if (input.screencastImage) {
|
|
700
|
+
context.drawImage(input.screencastImage, 0, input.screenOffsetTop * input.screenZoom,
|
|
701
|
+
input.screencastImage.naturalWidth * input.imageZoom,
|
|
702
|
+
input.screencastImage.naturalHeight * input.imageZoom);
|
|
703
|
+
}
|
|
704
|
+
context.restore();
|
|
508
705
|
}
|
|
509
706
|
|
|
510
|
-
private cssColor(color: Protocol.DOM.RGBA): string {
|
|
707
|
+
private static cssColor(color: Protocol.DOM.RGBA): string {
|
|
511
708
|
if (!color) {
|
|
512
709
|
return 'transparent';
|
|
513
710
|
}
|
|
@@ -516,64 +713,83 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
516
713
|
'';
|
|
517
714
|
}
|
|
518
715
|
|
|
519
|
-
private quadToPath(quad: Protocol.DOM.Quad): CanvasRenderingContext2D {
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
return
|
|
716
|
+
private static quadToPath(context: CanvasRenderingContext2D, quad: Protocol.DOM.Quad): CanvasRenderingContext2D {
|
|
717
|
+
context.beginPath();
|
|
718
|
+
context.moveTo(quad[0], quad[1]);
|
|
719
|
+
context.lineTo(quad[2], quad[3]);
|
|
720
|
+
context.lineTo(quad[4], quad[5]);
|
|
721
|
+
context.lineTo(quad[6], quad[7]);
|
|
722
|
+
context.closePath();
|
|
723
|
+
return context;
|
|
527
724
|
}
|
|
528
725
|
|
|
529
|
-
private drawOutlinedQuad(
|
|
530
|
-
|
|
531
|
-
|
|
532
|
-
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
726
|
+
private static drawOutlinedQuad(context: CanvasRenderingContext2D, quad: Protocol.DOM.Quad,
|
|
727
|
+
fillColor: Protocol.DOM.RGBA): void {
|
|
728
|
+
context.save();
|
|
729
|
+
context.lineWidth = 2;
|
|
730
|
+
ScreencastView.quadToPath(context, quad).clip();
|
|
731
|
+
context.fillStyle = ScreencastView.cssColor(fillColor);
|
|
732
|
+
context.fill();
|
|
733
|
+
context.restore();
|
|
536
734
|
}
|
|
537
735
|
|
|
538
|
-
private drawOutlinedQuadWithClip(
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
736
|
+
private static drawOutlinedQuadWithClip(context: CanvasRenderingContext2D, quad: Protocol.DOM.Quad,
|
|
737
|
+
clipQuad: Protocol.DOM.Quad, fillColor: Protocol.DOM.RGBA): void {
|
|
738
|
+
context.fillStyle = ScreencastView.cssColor(fillColor);
|
|
739
|
+
context.save();
|
|
740
|
+
context.lineWidth = 0;
|
|
741
|
+
ScreencastView.quadToPath(context, quad).fill();
|
|
742
|
+
context.globalCompositeOperation = 'destination-out';
|
|
743
|
+
context.fillStyle = 'red';
|
|
744
|
+
ScreencastView.quadToPath(context, clipQuad).fill();
|
|
745
|
+
context.restore();
|
|
548
746
|
}
|
|
549
747
|
|
|
550
748
|
private drawElementTitle(): void {
|
|
551
749
|
if (!this.node) {
|
|
750
|
+
if (this.#elementTitleData.visible) {
|
|
751
|
+
this.#elementTitleData = {visible: false};
|
|
752
|
+
this.requestUpdate();
|
|
753
|
+
}
|
|
552
754
|
return;
|
|
553
755
|
}
|
|
554
756
|
|
|
555
|
-
const canvasWidth = this.canvasElement.getBoundingClientRect().width;
|
|
556
|
-
const canvasHeight = this.canvasElement.getBoundingClientRect().height;
|
|
557
|
-
|
|
558
757
|
const lowerCaseName = this.node.localName() || this.node.nodeName().toLowerCase();
|
|
559
|
-
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
758
|
+
const attribute = getAttributesForElementTitle(this.node);
|
|
759
|
+
const width = String(this.model ? this.model.width : 0);
|
|
760
|
+
const height = String(this.model ? this.model.height : 0);
|
|
761
|
+
|
|
762
|
+
if (!this.#elementTitleData.visible || this.#elementTitleData.tagName !== lowerCaseName ||
|
|
763
|
+
this.#elementTitleData.attribute !== attribute || this.#elementTitleData.width !== width ||
|
|
764
|
+
this.#elementTitleData.height !== height) {
|
|
765
|
+
this.#elementTitleData = {
|
|
766
|
+
visible: true,
|
|
767
|
+
tagName: lowerCaseName,
|
|
768
|
+
attribute,
|
|
769
|
+
width,
|
|
770
|
+
height,
|
|
771
|
+
};
|
|
772
|
+
this.requestUpdate();
|
|
773
|
+
}
|
|
774
|
+
}
|
|
564
775
|
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
776
|
+
static clampTooltipPosition(canvas: HTMLCanvasElement, titleElement: HTMLElement,
|
|
777
|
+
model?: Protocol.DOM.BoxModel|null): void {
|
|
778
|
+
if (!model) {
|
|
779
|
+
return;
|
|
780
|
+
}
|
|
781
|
+
const canvasWidth = canvas.getBoundingClientRect().width;
|
|
782
|
+
const canvasHeight = canvas.getBoundingClientRect().height;
|
|
783
|
+
const titleWidth = titleElement.offsetWidth;
|
|
784
|
+
const titleHeight = titleElement.offsetHeight;
|
|
568
785
|
|
|
569
|
-
const anchorTop =
|
|
570
|
-
const anchorBottom =
|
|
786
|
+
const anchorTop = model.margin[1];
|
|
787
|
+
const anchorBottom = model.margin[7];
|
|
571
788
|
|
|
572
789
|
const arrowHeight = 7;
|
|
573
|
-
let
|
|
574
|
-
let renderArrowDown = false;
|
|
790
|
+
let arrowDirection: 'up'|'down'|undefined;
|
|
575
791
|
|
|
576
|
-
let boxX = Math.max(2,
|
|
792
|
+
let boxX = Math.max(2, model.margin[0]);
|
|
577
793
|
if (boxX + titleWidth > canvasWidth) {
|
|
578
794
|
boxX = canvasWidth - titleWidth - 2;
|
|
579
795
|
}
|
|
@@ -581,47 +797,24 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
581
797
|
let boxY;
|
|
582
798
|
if (anchorTop > canvasHeight) {
|
|
583
799
|
boxY = canvasHeight - titleHeight - arrowHeight;
|
|
584
|
-
|
|
800
|
+
arrowDirection = 'down';
|
|
585
801
|
} else if (anchorBottom < 0) {
|
|
586
802
|
boxY = arrowHeight;
|
|
587
|
-
|
|
803
|
+
arrowDirection = 'up';
|
|
588
804
|
} else if (anchorBottom + titleHeight + arrowHeight < canvasHeight) {
|
|
589
805
|
boxY = anchorBottom + arrowHeight - 4;
|
|
590
|
-
|
|
806
|
+
arrowDirection = 'up';
|
|
591
807
|
} else if (anchorTop - titleHeight - arrowHeight > 0) {
|
|
592
808
|
boxY = anchorTop - titleHeight - arrowHeight + 3;
|
|
593
|
-
|
|
809
|
+
arrowDirection = 'down';
|
|
594
810
|
} else {
|
|
595
811
|
boxY = arrowHeight;
|
|
596
812
|
}
|
|
597
813
|
|
|
598
|
-
|
|
599
|
-
|
|
600
|
-
|
|
601
|
-
|
|
602
|
-
if (renderArrowUp) {
|
|
603
|
-
this.context.lineTo(boxX + 2 * arrowHeight, boxY);
|
|
604
|
-
this.context.lineTo(boxX + 3 * arrowHeight, boxY - arrowHeight);
|
|
605
|
-
this.context.lineTo(boxX + 4 * arrowHeight, boxY);
|
|
606
|
-
}
|
|
607
|
-
this.context.lineTo(boxX + titleWidth, boxY);
|
|
608
|
-
this.context.lineTo(boxX + titleWidth, boxY + titleHeight);
|
|
609
|
-
if (renderArrowDown) {
|
|
610
|
-
this.context.lineTo(boxX + 4 * arrowHeight, boxY + titleHeight);
|
|
611
|
-
this.context.lineTo(boxX + 3 * arrowHeight, boxY + titleHeight + arrowHeight);
|
|
612
|
-
this.context.lineTo(boxX + 2 * arrowHeight, boxY + titleHeight);
|
|
613
|
-
}
|
|
614
|
-
this.context.lineTo(boxX, boxY + titleHeight);
|
|
615
|
-
this.context.closePath();
|
|
616
|
-
this.context.fillStyle = 'var(--sys-color-yellow-container)';
|
|
617
|
-
this.context.fill();
|
|
618
|
-
this.context.strokeStyle = 'var(--sys-color-outline)';
|
|
619
|
-
this.context.stroke();
|
|
620
|
-
|
|
621
|
-
this.context.restore();
|
|
622
|
-
|
|
623
|
-
this.titleElement.style.top = (boxY + 3) + 'px';
|
|
624
|
-
this.titleElement.style.left = (boxX + 3) + 'px';
|
|
814
|
+
titleElement.style.top = `${boxY}px`;
|
|
815
|
+
titleElement.style.left = `${boxX}px`;
|
|
816
|
+
titleElement.classList.toggle('arrow-up', arrowDirection === 'up');
|
|
817
|
+
titleElement.classList.toggle('arrow-down', arrowDirection === 'down');
|
|
625
818
|
}
|
|
626
819
|
|
|
627
820
|
private viewportDimensions(): {width: number, height: number} {
|
|
@@ -640,69 +833,21 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
640
833
|
highlightFrame(_frameId: string): void {
|
|
641
834
|
}
|
|
642
835
|
|
|
643
|
-
private createCheckerboardPattern(context: CanvasRenderingContext2D): CanvasPattern|null {
|
|
644
|
-
const size = 32;
|
|
645
|
-
const pattern = new OffscreenCanvas(size * 2, size * 2);
|
|
646
|
-
const pctx = pattern.getContext('2d', {willReadFrequently: true}) as OffscreenCanvasRenderingContext2D;
|
|
647
|
-
|
|
648
|
-
pctx.fillStyle = 'var(--sys-color-neutral-outline)';
|
|
649
|
-
pctx.fillRect(0, 0, size * 2, size * 2);
|
|
650
|
-
|
|
651
|
-
pctx.fillStyle = 'var(--sys-color-surface-variant)';
|
|
652
|
-
pctx.fillRect(0, 0, size, size);
|
|
653
|
-
pctx.fillRect(size, size, size, size);
|
|
654
|
-
return context.createPattern(pattern, 'repeat');
|
|
655
|
-
}
|
|
656
|
-
|
|
657
836
|
private createNavigationBar(): void {
|
|
658
|
-
this.
|
|
659
|
-
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
this.navigationForward = this.navigationBar.createChild('button', 'navigation');
|
|
666
|
-
this.navigationForward.appendChild(createIcon('arrow-forward'));
|
|
667
|
-
this.navigationForward.disabled = true;
|
|
668
|
-
UI.ARIAUtils.setLabel(this.navigationForward, i18nString(UIStrings.forward));
|
|
669
|
-
|
|
670
|
-
this.navigationReload = this.navigationBar.createChild('button', 'navigation');
|
|
671
|
-
this.navigationReload.appendChild(createIcon('refresh'));
|
|
672
|
-
UI.ARIAUtils.setLabel(this.navigationReload, i18nString(UIStrings.reload));
|
|
673
|
-
|
|
674
|
-
this.navigationUrl = this.navigationBar.appendChild(UI.UIUtils.createInput());
|
|
675
|
-
this.navigationUrl.type = 'text';
|
|
676
|
-
UI.ARIAUtils.setLabel(this.navigationUrl, i18nString(UIStrings.addressBar));
|
|
677
|
-
|
|
678
|
-
this.mouseInputToggle = this.navigationBar.createChild('button');
|
|
679
|
-
this.mouseInputToggle.disabled = true;
|
|
680
|
-
{
|
|
681
|
-
this.mouseInputToggleIcon = this.mouseInputToggle.appendChild(new Icon());
|
|
682
|
-
this.mouseInputToggleIcon.name = 'mouse';
|
|
683
|
-
this.mouseInputToggleIcon.classList.toggle('toggled', true);
|
|
684
|
-
}
|
|
685
|
-
UI.ARIAUtils.setLabel(this.mouseInputToggle, i18nString(UIStrings.mouseInput));
|
|
686
|
-
|
|
687
|
-
this.touchInputToggle = this.navigationBar.createChild('button');
|
|
688
|
-
this.touchInputToggleIcon = this.touchInputToggle.appendChild(createIcon('touch-app'));
|
|
689
|
-
UI.ARIAUtils.setLabel(this.touchInputToggle, i18nString(UIStrings.touchInput));
|
|
690
|
-
|
|
691
|
-
this.navigationProgressBar = new ProgressTracker(
|
|
692
|
-
this.resourceTreeModel, this.networkManager, this.navigationBar.createChild('div', 'progress'));
|
|
837
|
+
this.navigationProgressBar =
|
|
838
|
+
new ProgressTracker(this.resourceTreeModel, this.networkManager, (progress: number) => {
|
|
839
|
+
if (this.#progressPercent !== progress) {
|
|
840
|
+
this.#progressPercent = progress;
|
|
841
|
+
this.requestUpdate();
|
|
842
|
+
}
|
|
843
|
+
});
|
|
693
844
|
|
|
694
845
|
if (this.resourceTreeModel) {
|
|
695
|
-
this.navigationBack.addEventListener('click', this.navigateToHistoryEntry.bind(this, -1), false);
|
|
696
|
-
this.navigationForward.addEventListener('click', this.navigateToHistoryEntry.bind(this, 1), false);
|
|
697
|
-
this.navigationReload.addEventListener('click', this.navigateReload.bind(this), false);
|
|
698
|
-
this.navigationUrl.addEventListener('keyup', this.navigationUrlKeyUp.bind(this), true);
|
|
699
|
-
this.touchInputToggle.addEventListener('click', this.#toggleTouchEmulation.bind(this, true), false);
|
|
700
|
-
this.mouseInputToggle.addEventListener('click', this.#toggleTouchEmulation.bind(this, false), false);
|
|
701
846
|
void this.requestNavigationHistory();
|
|
702
|
-
this.resourceTreeModel.addEventListener(
|
|
703
|
-
|
|
704
|
-
this.resourceTreeModel.addEventListener(
|
|
705
|
-
|
|
847
|
+
this.resourceTreeModel.addEventListener(SDK.ResourceTreeModel.Events.PrimaryPageChanged,
|
|
848
|
+
this.requestNavigationHistoryEvent, this);
|
|
849
|
+
this.resourceTreeModel.addEventListener(SDK.ResourceTreeModel.Events.CachedResourcesLoaded,
|
|
850
|
+
this.requestNavigationHistoryEvent, this);
|
|
706
851
|
}
|
|
707
852
|
}
|
|
708
853
|
|
|
@@ -729,7 +874,8 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
729
874
|
if (event.key !== 'Enter') {
|
|
730
875
|
return;
|
|
731
876
|
}
|
|
732
|
-
|
|
877
|
+
const inputElement = event.target as HTMLInputElement;
|
|
878
|
+
let url: string = inputElement.value;
|
|
733
879
|
if (!url) {
|
|
734
880
|
return;
|
|
735
881
|
}
|
|
@@ -739,23 +885,19 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
739
885
|
if (this.resourceTreeModel) {
|
|
740
886
|
void this.resourceTreeModel.navigate(url as Platform.DevToolsPath.UrlString);
|
|
741
887
|
}
|
|
742
|
-
this.
|
|
888
|
+
this.#viewOutput.focusCanvas?.();
|
|
743
889
|
}
|
|
744
890
|
|
|
745
891
|
#toggleTouchEmulation(value: boolean): void {
|
|
746
|
-
if (!this.
|
|
747
|
-
!this.mouseInputToggleIcon || !this.touchInputToggleIcon) {
|
|
892
|
+
if (!this.isCasting) {
|
|
748
893
|
return;
|
|
749
894
|
}
|
|
750
895
|
const models = SDK.TargetManager.TargetManager.instance().models(SDK.EmulationModel.EmulationModel);
|
|
751
896
|
for (const model of models) {
|
|
752
897
|
void model.overrideEmulateTouch(value);
|
|
753
898
|
}
|
|
754
|
-
this
|
|
755
|
-
this.
|
|
756
|
-
this.mouseInputToggleIcon.classList.toggle('toggled', this.mouseInputToggle.disabled);
|
|
757
|
-
this.touchInputToggleIcon.classList.toggle('toggled', this.touchInputToggle.disabled);
|
|
758
|
-
this.canvasContainerElement.classList.toggle('touchable', value);
|
|
899
|
+
this.#isTouchEmulated = value;
|
|
900
|
+
this.requestUpdate();
|
|
759
901
|
}
|
|
760
902
|
|
|
761
903
|
private requestNavigationHistoryEvent(): void {
|
|
@@ -771,8 +913,8 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
771
913
|
this.historyIndex = history.currentIndex;
|
|
772
914
|
this.historyEntries = history.entries;
|
|
773
915
|
|
|
774
|
-
this
|
|
775
|
-
this
|
|
916
|
+
this.#canGoBack = this.historyIndex > 0;
|
|
917
|
+
this.#canGoForward = this.historyIndex < (this.historyEntries.length - 1);
|
|
776
918
|
|
|
777
919
|
let url: string = this.historyEntries[this.historyIndex].url;
|
|
778
920
|
const match = url.match(HTTP_REGEX);
|
|
@@ -781,12 +923,12 @@ export class ScreencastView extends UI.Widget.VBox implements SDK.OverlayModel.H
|
|
|
781
923
|
}
|
|
782
924
|
Host.InspectorFrontendHost.InspectorFrontendHostInstance.inspectedURLChanged(
|
|
783
925
|
url as Platform.DevToolsPath.UrlString);
|
|
784
|
-
this
|
|
926
|
+
this.#navigationUrlText = decodeURI(url);
|
|
927
|
+
this.requestUpdate();
|
|
785
928
|
}
|
|
786
929
|
|
|
787
930
|
private focusNavigationBar(): boolean {
|
|
788
|
-
this.
|
|
789
|
-
this.navigationUrl.select();
|
|
931
|
+
this.#viewOutput.focusUrlInput?.();
|
|
790
932
|
return true;
|
|
791
933
|
}
|
|
792
934
|
}
|
|
@@ -799,18 +941,17 @@ export const SCHEME_REGEX = /^(https?|about|chrome):/;
|
|
|
799
941
|
export class ProgressTracker {
|
|
800
942
|
private readonly resourceTreeModel: SDK.ResourceTreeModel.ResourceTreeModel|null;
|
|
801
943
|
private readonly networkManager: SDK.NetworkManager.NetworkManager|null;
|
|
802
|
-
private element: HTMLElement;
|
|
803
944
|
private requestIds: Map<string, SDK.NetworkRequest.NetworkRequest>|null;
|
|
804
945
|
private startedRequests: number;
|
|
805
946
|
private finishedRequests: number;
|
|
806
947
|
private maxDisplayedProgress: number;
|
|
948
|
+
private readonly onProgressUpdate?: (progress: number) => void;
|
|
807
949
|
|
|
808
|
-
constructor(
|
|
809
|
-
|
|
810
|
-
networkManager: SDK.NetworkManager.NetworkManager|null, element: HTMLElement) {
|
|
811
|
-
this.element = element;
|
|
950
|
+
constructor(resourceTreeModel: SDK.ResourceTreeModel.ResourceTreeModel|null,
|
|
951
|
+
networkManager: SDK.NetworkManager.NetworkManager|null, onProgressUpdate?: (progress: number) => void) {
|
|
812
952
|
this.resourceTreeModel = resourceTreeModel;
|
|
813
953
|
this.networkManager = networkManager;
|
|
954
|
+
this.onProgressUpdate = onProgressUpdate;
|
|
814
955
|
if (this.resourceTreeModel) {
|
|
815
956
|
this.resourceTreeModel.addEventListener(SDK.ResourceTreeModel.Events.PrimaryPageChanged,
|
|
816
957
|
this.onPrimaryPageChanged, this);
|
|
@@ -902,7 +1043,7 @@ export class ProgressTracker {
|
|
|
902
1043
|
}
|
|
903
1044
|
|
|
904
1045
|
private displayProgress(progress: number): void {
|
|
905
|
-
this.
|
|
1046
|
+
this.onProgressUpdate?.(progress);
|
|
906
1047
|
}
|
|
907
1048
|
}
|
|
908
1049
|
|