chrome-devtools-frontend 1.0.1516909 → 1.0.1519267

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.
Files changed (162) hide show
  1. package/config/owner/COMMON_OWNERS +2 -2
  2. package/docs/checklist/README.md +2 -2
  3. package/docs/checklist/javascript.md +1 -1
  4. package/docs/contributing/README.md +1 -1
  5. package/docs/contributing/settings-experiments-features.md +9 -8
  6. package/docs/cookbook/devtools_on_devtools.md +2 -2
  7. package/docs/cookbook/localization.md +10 -10
  8. package/docs/devtools-protocol.md +9 -8
  9. package/docs/ecosystem/automatic_workspace_folders.md +3 -3
  10. package/docs/get_the_code.md +0 -2
  11. package/docs/styleguide/ux/components.md +166 -85
  12. package/docs/styleguide/ux/numbers.md +3 -4
  13. package/eslint.config.mjs +1 -0
  14. package/front_end/core/common/README.md +13 -12
  15. package/front_end/core/host/GdpClient.ts +16 -1
  16. package/front_end/core/host/UserMetrics.ts +4 -2
  17. package/front_end/core/root/Runtime.ts +13 -0
  18. package/front_end/core/sdk/CSSMatchedStyles.ts +5 -1
  19. package/front_end/core/sdk/EnhancedTracesParser.ts +5 -5
  20. package/front_end/core/sdk/RehydratingConnection.snapshot.txt +211 -0
  21. package/front_end/core/sdk/TargetManager.ts +4 -0
  22. package/front_end/entrypoints/main/MainImpl.ts +6 -3
  23. package/front_end/generated/InspectorBackendCommands.js +10 -7
  24. package/front_end/generated/SupportedCSSProperties.js +40 -11
  25. package/front_end/generated/protocol-mapping.d.ts +16 -1
  26. package/front_end/generated/protocol-proxy-api.d.ts +13 -1
  27. package/front_end/generated/protocol.ts +95 -0
  28. package/front_end/models/ai_assistance/agents/AiAgent.ts +57 -10
  29. package/front_end/models/ai_assistance/agents/PerformanceAgent.ts +119 -51
  30. package/front_end/models/ai_assistance/agents/StylingAgent.ts +0 -31
  31. package/front_end/models/ai_assistance/data_formatters/PerformanceInsightFormatter.snapshot.txt +14 -181
  32. package/front_end/models/ai_assistance/data_formatters/PerformanceInsightFormatter.ts +19 -315
  33. package/front_end/models/ai_assistance/data_formatters/PerformanceTraceFormatter.snapshot.txt +224 -50
  34. package/front_end/models/ai_assistance/data_formatters/PerformanceTraceFormatter.ts +310 -11
  35. package/front_end/models/ai_assistance/performance/AIContext.ts +15 -2
  36. package/front_end/models/ai_code_completion/AiCodeCompletion.ts +22 -11
  37. package/front_end/models/badges/AiExplorerBadge.ts +19 -3
  38. package/front_end/models/badges/Badge.ts +10 -3
  39. package/front_end/models/badges/CodeWhispererBadge.ts +3 -4
  40. package/front_end/models/badges/DOMDetectiveBadge.ts +1 -0
  41. package/front_end/models/badges/SpeedsterBadge.ts +1 -0
  42. package/front_end/models/badges/StarterBadge.ts +3 -2
  43. package/front_end/models/badges/UserBadges.ts +21 -3
  44. package/front_end/models/badges/badges.ts +1 -0
  45. package/front_end/models/javascript_metadata/NativeFunctions.js +2 -2
  46. package/front_end/models/trace/EventsSerializer.ts +4 -3
  47. package/front_end/models/trace/README.md +28 -1
  48. package/front_end/models/trace/handlers/UserInteractionsHandler.ts +101 -73
  49. package/front_end/models/trace/handlers/UserTimingsHandler.ts +1 -1
  50. package/front_end/models/trace/helpers/Timing.ts +1 -1
  51. package/front_end/models/trace/helpers/Trace.ts +99 -43
  52. package/front_end/models/trace/types/TraceEvents.ts +9 -0
  53. package/front_end/panels/accessibility/ARIAAttributesView.ts +113 -191
  54. package/front_end/panels/accessibility/AccessibilityNodeView.ts +9 -9
  55. package/front_end/panels/accessibility/AccessibilitySubPane.ts +6 -4
  56. package/front_end/panels/accessibility/accessibilityProperties.css +2 -0
  57. package/front_end/panels/ai_assistance/AiAssistancePanel.ts +20 -3
  58. package/front_end/panels/ai_assistance/components/ChatView.ts +9 -10
  59. package/front_end/panels/ai_assistance/components/PerformanceAgentMarkdownRenderer.ts +44 -0
  60. package/front_end/panels/application/components/BounceTrackingMitigationsView.ts +2 -2
  61. package/front_end/panels/common/AiCodeCompletionDisclaimer.ts +32 -9
  62. package/front_end/panels/common/AiCodeCompletionSummaryToolbar.ts +7 -1
  63. package/front_end/panels/common/BadgeNotification.ts +21 -5
  64. package/front_end/panels/common/GdpSignUpDialog.ts +20 -12
  65. package/front_end/panels/console/ConsolePrompt.ts +1 -1
  66. package/front_end/panels/console/ConsoleView.ts +6 -2
  67. package/front_end/panels/css_overview/CSSOverviewCompletedView.ts +5 -5
  68. package/front_end/panels/elements/ElementsPanel.ts +4 -0
  69. package/front_end/panels/elements/ElementsTreeElement.ts +18 -0
  70. package/front_end/panels/elements/ElementsTreeOutline.ts +13 -0
  71. package/front_end/panels/elements/StylePropertyTreeElement.ts +21 -6
  72. package/front_end/panels/media/TickingFlameChart.ts +1 -1
  73. package/front_end/panels/profiler/HeapSnapshotView.ts +34 -19
  74. package/front_end/panels/recorder/components/RecordingView.ts +2 -2
  75. package/front_end/panels/search/SearchResultsPane.ts +167 -152
  76. package/front_end/panels/search/SearchView.ts +36 -26
  77. package/front_end/panels/search/searchResultsPane.css +9 -0
  78. package/front_end/panels/security/CookieControlsView.ts +2 -1
  79. package/front_end/panels/settings/AISettingsTab.ts +6 -3
  80. package/front_end/panels/settings/components/SyncSection.ts +39 -17
  81. package/front_end/panels/settings/emulation/components/UserAgentClientHintsForm.ts +1 -1
  82. package/front_end/panels/sources/AiCodeCompletionPlugin.ts +9 -1
  83. package/front_end/panels/sources/SourcesPanel.ts +4 -1
  84. package/front_end/panels/sources/sourcesView.css +6 -1
  85. package/front_end/panels/timeline/AppenderUtils.ts +2 -2
  86. package/front_end/panels/timeline/ExtensionTrackAppender.ts +13 -4
  87. package/front_end/panels/timeline/GPUTrackAppender.ts +2 -1
  88. package/front_end/panels/timeline/InteractionsTrackAppender.ts +5 -1
  89. package/front_end/panels/timeline/LayoutShiftsTrackAppender.ts +2 -1
  90. package/front_end/panels/timeline/ThreadAppender.ts +12 -3
  91. package/front_end/panels/timeline/TimelineFlameChartDataProvider.ts +9 -4
  92. package/front_end/panels/timeline/TimelinePanel.ts +3 -2
  93. package/front_end/panels/timeline/TimelineUIUtils.ts +5 -4
  94. package/front_end/panels/timeline/TimingsTrackAppender.ts +6 -1
  95. package/front_end/panels/timeline/components/CPUThrottlingSelector.ts +95 -82
  96. package/front_end/panels/timeline/components/LayoutShiftDetails.ts +1 -1
  97. package/front_end/panels/timeline/components/LiveMetricsView.ts +2 -2
  98. package/front_end/panels/timeline/components/NetworkRequestDetails.ts +1 -1
  99. package/front_end/panels/timeline/components/RelatedInsightChips.ts +1 -1
  100. package/front_end/panels/timeline/components/SidebarSingleInsightSet.ts +1 -1
  101. package/front_end/panels/timeline/components/cpuThrottlingSelector.css +17 -15
  102. package/front_end/panels/timeline/components/insights/BaseInsightComponent.ts +3 -0
  103. package/front_end/third_party/chromium/README.chromium +1 -1
  104. package/front_end/third_party/codemirror.next/chunk/codemirror.js +1 -1
  105. package/front_end/third_party/codemirror.next/chunk/codemirror.js.map +1 -1
  106. package/front_end/third_party/codemirror.next/codemirror.next.d.ts +6 -9
  107. package/front_end/third_party/codemirror.next/package.json +2 -1
  108. package/front_end/third_party/diff/README.chromium +1 -0
  109. package/front_end/third_party/puppeteer/README.chromium +2 -2
  110. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/bidi/core/Realm.d.ts +2 -2
  111. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/generated/injected.d.ts +1 -1
  112. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/generated/injected.js +1 -1
  113. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/generated/version.d.ts +1 -1
  114. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/generated/version.js +1 -1
  115. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/injected/injected.d.ts +1 -1
  116. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/node/ChromeLauncher.d.ts.map +1 -1
  117. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/node/ChromeLauncher.js +1 -0
  118. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/node/ChromeLauncher.js.map +1 -1
  119. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/revisions.d.ts +3 -3
  120. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/revisions.js +3 -3
  121. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/revisions.js.map +1 -1
  122. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/util/Function.d.ts.map +1 -1
  123. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/util/Function.js +16 -25
  124. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/util/Function.js.map +1 -1
  125. package/front_end/third_party/puppeteer/package/lib/cjs/puppeteer/util/Mutex.d.ts +2 -2
  126. package/front_end/third_party/puppeteer/package/lib/es5-iife/puppeteer-core-browser.js +19 -28
  127. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/generated/injected.d.ts +1 -1
  128. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/generated/injected.js +1 -1
  129. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/generated/version.d.ts +1 -1
  130. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/generated/version.js +1 -1
  131. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/node/ChromeLauncher.d.ts.map +1 -1
  132. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/node/ChromeLauncher.js +1 -0
  133. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/node/ChromeLauncher.js.map +1 -1
  134. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/revisions.d.ts +3 -3
  135. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/revisions.js +3 -3
  136. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/revisions.js.map +1 -1
  137. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/util/Function.d.ts.map +1 -1
  138. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/util/Function.js +16 -25
  139. package/front_end/third_party/puppeteer/package/lib/esm/puppeteer/util/Function.js.map +1 -1
  140. package/front_end/third_party/puppeteer/package/package.json +10 -3
  141. package/front_end/third_party/puppeteer/package/src/generated/injected.ts +1 -1
  142. package/front_end/third_party/puppeteer/package/src/generated/version.ts +1 -1
  143. package/front_end/third_party/puppeteer/package/src/node/ChromeLauncher.ts +1 -0
  144. package/front_end/third_party/puppeteer/package/src/revisions.ts +3 -3
  145. package/front_end/third_party/puppeteer/package/src/util/Function.ts +22 -30
  146. package/front_end/ui/components/dialogs/Dialog.ts +1 -1
  147. package/front_end/ui/components/markdown_view/MarkdownImage.ts +4 -5
  148. package/front_end/ui/components/switch/SwitchImpl.ts +12 -1
  149. package/front_end/ui/components/text_editor/config.ts +22 -9
  150. package/front_end/ui/components/tooltips/Tooltip.ts +70 -31
  151. package/front_end/ui/legacy/README.md +33 -24
  152. package/front_end/ui/legacy/SearchableView.ts +19 -26
  153. package/front_end/ui/legacy/TextPrompt.ts +166 -1
  154. package/front_end/ui/legacy/Treeoutline.ts +19 -3
  155. package/front_end/ui/legacy/UIUtils.ts +15 -2
  156. package/front_end/ui/legacy/XElement.ts +0 -43
  157. package/front_end/ui/legacy/components/perf_ui/FlameChart.ts +20 -4
  158. package/front_end/ui/legacy/components/source_frame/XMLView.ts +12 -11
  159. package/front_end/ui/lit/i18n-template.ts +5 -2
  160. package/front_end/ui/visual_logging/KnownContextValues.ts +23 -6
  161. package/front_end/ui/visual_logging/README.md +43 -27
  162. package/package.json +1 -1
@@ -106,12 +106,11 @@ const UIStrings = {
106
106
  } as const;
107
107
  const str_ = i18n.i18n.registerUIStrings('panels/search/SearchView.ts', UIStrings);
108
108
  const i18nString = i18n.i18n.getLocalizedString.bind(undefined, str_);
109
- const {ref} = Directives;
109
+ const {ref, live} = Directives;
110
110
  const {widgetConfig} = UI.Widget;
111
111
 
112
112
  interface SearchViewInput {
113
113
  query: string;
114
- focusSearchInput: boolean;
115
114
  matchCase: boolean;
116
115
  isRegex: boolean;
117
116
  searchMessage: string;
@@ -128,12 +127,15 @@ interface SearchViewInput {
128
127
  onClearSearch: () => void;
129
128
  }
130
129
 
131
- type View = (input: SearchViewInput, output: object, target: HTMLElement) => void;
130
+ interface SearchViewOutput {
131
+ focusSearchInput: () => void;
132
+ }
133
+
134
+ type View = (input: SearchViewInput, output: SearchViewOutput, target: HTMLElement) => void;
132
135
 
133
136
  export const DEFAULT_VIEW: View = (input, output, target) => {
134
137
  const {
135
138
  query,
136
- focusSearchInput,
137
139
  matchCase,
138
140
  isRegex,
139
141
  searchMessage,
@@ -175,14 +177,16 @@ export const DEFAULT_VIEW: View = (input, output, target) => {
175
177
  change: true, keydown: 'ArrowUp|ArrowDown|Enter'})}
176
178
  aria-label=${i18nString(UIStrings.find)}
177
179
  size="100" results="0"
178
- .value=${query}
180
+ .value=${live(query)}
179
181
  @keydown=${onQueryKeyDown}
180
182
  @input=${(e: Event) => onQueryChange((e.target as HTMLInputElement).value)}
181
183
  ${ref(e => {
182
- if (e instanceof HTMLInputElement && focusSearchInput) {
183
- e.focus();
184
- e.select();
185
- }
184
+ output.focusSearchInput = () => {
185
+ if (e instanceof HTMLInputElement) {
186
+ e.focus();
187
+ e.select();
188
+ }
189
+ };
186
190
  })}>
187
191
  <devtools-button class="clear-button" tabindex="-1"
188
192
  @click=${onClearSearchInput}
@@ -258,7 +262,7 @@ export const DEFAULT_VIEW: View = (input, output, target) => {
258
262
 
259
263
  export class SearchView extends UI.Widget.VBox {
260
264
  readonly #view: View;
261
- #focusSearchInput: boolean;
265
+ #focusSearchInput = (): void => {};
262
266
  #isIndexing: boolean;
263
267
  #searchId: number;
264
268
  #searchMatchesCount: number;
@@ -284,7 +288,7 @@ export class SearchView extends UI.Widget.VBox {
284
288
  // We throttle adding search results, otherwise we trigger DOM layout for each
285
289
  // result added.
286
290
  #throttler: Common.Throttler.Throttler;
287
- #pendingSearchResults: SearchResult[] = [];
291
+ #searchResults: SearchResult[] = [];
288
292
 
289
293
  constructor(settingKey: string, throttler: Common.Throttler.Throttler, view = DEFAULT_VIEW) {
290
294
  super({
@@ -294,7 +298,6 @@ export class SearchView extends UI.Widget.VBox {
294
298
  this.#view = view;
295
299
  this.setMinimumSize(0, 40);
296
300
 
297
- this.#focusSearchInput = false;
298
301
  this.#isIndexing = false;
299
302
  this.#searchId = 1;
300
303
  this.#query = '';
@@ -320,7 +323,6 @@ export class SearchView extends UI.Widget.VBox {
320
323
  override performUpdate(): void {
321
324
  const input: SearchViewInput = {
322
325
  query: this.#query,
323
- focusSearchInput: this.#focusSearchInput,
324
326
  matchCase: this.#matchCase,
325
327
  isRegex: this.#isRegex,
326
328
  searchMessage: this.#searchMessage,
@@ -338,9 +340,13 @@ export class SearchView extends UI.Widget.VBox {
338
340
  onRefresh: this.#onRefresh.bind(this),
339
341
  onClearSearch: this.#onClearSearch.bind(this),
340
342
  };
341
- const output = {};
343
+ const that = this;
344
+ const output: SearchViewOutput = {
345
+ set focusSearchInput(value: () => void) {
346
+ that.#focusSearchInput = value;
347
+ }
348
+ };
342
349
  this.#view(input, output, this.contentElement);
343
- this.#focusSearchInput = false;
344
350
  }
345
351
 
346
352
  #onToggleRegex(): void {
@@ -360,7 +366,9 @@ export class SearchView extends UI.Widget.VBox {
360
366
  toggle(queryCandidate: string, searchImmediately?: boolean): void {
361
367
  this.#query = queryCandidate;
362
368
  this.requestUpdate();
363
- this.focus();
369
+ void this.updateComplete.then(() => {
370
+ this.focus();
371
+ });
364
372
 
365
373
  this.#initScope();
366
374
  if (searchImmediately) {
@@ -431,22 +439,24 @@ export class SearchView extends UI.Widget.VBox {
431
439
  if (!this.#searchResultsPane) {
432
440
  this.#searchResultsPane = this.createSearchResultsPane();
433
441
  }
434
- this.#pendingSearchResults.push(searchResult);
435
- void this.#throttler.schedule(async () => this.#addPendingSearchResults());
442
+ this.#searchResults.push(searchResult);
443
+ void this.#throttler.schedule(async () => this.#setSearchResults());
436
444
  }
437
445
 
438
446
  protected createSearchResultsPane(): SearchResultsPane {
439
447
  return new SearchResultsPane((this.#searchConfig as Workspace.SearchConfig.SearchConfig));
440
448
  }
441
449
 
442
- #addPendingSearchResults(): void {
443
- for (const searchResult of this.#pendingSearchResults) {
450
+ #setSearchResults(): void {
451
+ this.#searchMatchesCount = 0;
452
+ this.#searchResultsCount = 0;
453
+ this.#nonEmptySearchResultsCount = 0;
454
+ for (const searchResult of this.#searchResults) {
444
455
  this.#addSearchResult(searchResult);
445
- if (searchResult.matchesCount()) {
446
- this.#searchResultsPane?.addSearchResult(searchResult);
447
- }
448
456
  }
449
- this.#pendingSearchResults = [];
457
+ if (this.#searchResultsPane) {
458
+ this.#searchResultsPane.searchResults = this.#searchResults.filter(searchResult => searchResult.matchesCount());
459
+ }
450
460
  }
451
461
 
452
462
  #onSearchFinished(searchId: number, finished: boolean): void {
@@ -495,6 +505,7 @@ export class SearchView extends UI.Widget.VBox {
495
505
  #searchStarted(): void {
496
506
  this.#searchMatchesCount = 0;
497
507
  this.#searchResultsCount = 0;
508
+ this.#searchResults = [];
498
509
  this.#nonEmptySearchResultsCount = 0;
499
510
  if (!this.#searchingView) {
500
511
  this.#searchingView = new UI.EmptyWidget.EmptyWidget(i18nString(UIStrings.searching), '');
@@ -537,8 +548,7 @@ export class SearchView extends UI.Widget.VBox {
537
548
  }
538
549
 
539
550
  override focus(): void {
540
- this.#focusSearchInput = true;
541
- this.requestUpdate();
551
+ this.#focusSearchInput();
542
552
  }
543
553
 
544
554
  override willHide(): void {
@@ -31,6 +31,11 @@ li.search-result {
31
31
  white-space: pre;
32
32
  }
33
33
 
34
+ li.search-result .tree-element-title {
35
+ display: flex;
36
+ width: 100%;
37
+ }
38
+
34
39
  li.search-result:hover {
35
40
  background-color: var(--sys-color-state-hover-on-subtle);
36
41
  }
@@ -68,6 +73,10 @@ li.search-match {
68
73
  white-space: pre;
69
74
  }
70
75
 
76
+ li.search-match .tree-element-title {
77
+ display: flex;
78
+ }
79
+
71
80
  li.search-match.selected:focus-visible {
72
81
  background: var(--sys-color-tonal-container);
73
82
  }
@@ -186,8 +186,9 @@ export class CookieControlsView extends UI.Widget.VBox {
186
186
  <devtools-switch
187
187
  .checked=${Boolean(toggleEnabledSetting.get())}
188
188
  .disabled=${Boolean(enterpriseEnabledSetting.get())}
189
+ .label=${'Temporarily limit third-party cookies, only when DevTools is open'}
190
+ data-testid="cookie-control-override"
189
191
  @switchchange=${()=>{input.inputChanged(!toggleEnabledSetting.get(), toggleEnabledSetting);}}
190
- aria-label="Temporarily limit third-party cookies, only when DevTools is open"
191
192
  jslog=${VisualLogging.toggle(toggleEnabledSetting.name).track({click: true})}
192
193
  >
193
194
  </devtools-switch>
@@ -381,8 +381,10 @@ export class AISettingsTab extends LegacyWrapper.LegacyWrapper.WrappableComponen
381
381
  text: noLogging ? i18nString(UIStrings.codeSuggestionsSendDataNoLogging) :
382
382
  i18nString(UIStrings.codeSuggestionsSendData)
383
383
  }],
384
- // TODO: Add a relevant link
385
- learnMoreLink: {url: '', linkJSLogContext: 'learn-more.code-completion'},
384
+ learnMoreLink: {
385
+ url: ' https://developers.chrome.com/docs/devtools/ai-assistance/code-completion',
386
+ linkJSLogContext: 'learn-more.code-completion'
387
+ },
386
388
  settingExpandState: {
387
389
  isSettingExpanded: false,
388
390
  expandSettingJSLogContext: 'code-completion.accordion',
@@ -590,8 +592,9 @@ export class AISettingsTab extends LegacyWrapper.LegacyWrapper.WrappableComponen
590
592
  .checked=${Boolean(setting.get()) && !isDisabled}
591
593
  .jslogContext=${setting.name || ''}
592
594
  .disabled=${isDisabled}
595
+ .label=${disabledReasonsJoined || settingData.enableSettingText}
596
+ data-testid=${settingData.enableSettingText}
593
597
  @switchchange=${this.#toggleSetting.bind(this, setting)}
594
- aria-label=${disabledReasonsJoined || settingData.enableSettingText}
595
598
  ></devtools-switch>
596
599
  </div>
597
600
  <div class=${classMap(detailsClasses)}>
@@ -12,11 +12,13 @@ import * as Host from '../../../core/host/host.js';
12
12
  import * as i18n from '../../../core/i18n/i18n.js';
13
13
  import type * as Platform from '../../../core/platform/platform.js';
14
14
  import * as Root from '../../../core/root/root.js';
15
+ import * as SDK from '../../../core/sdk/sdk.js';
15
16
  import * as Badges from '../../../models/badges/badges.js';
16
17
  import * as Buttons from '../../../ui/components/buttons/buttons.js';
17
18
  import * as ComponentHelpers from '../../../ui/components/helpers/helpers.js';
18
19
  import type * as SettingsComponents from '../../../ui/components/settings/settings.js';
19
20
  import * as Lit from '../../../ui/lit/lit.js';
21
+ import * as VisualLogging from '../../../ui/visual_logging/visual_logging.js';
20
22
  import * as PanelCommon from '../../common/common.js';
21
23
  import * as PanelUtils from '../../utils/utils.js';
22
24
 
@@ -212,7 +214,7 @@ export class SyncSection extends HTMLElement {
212
214
  }
213
215
 
214
216
  async #fetchGdpDetails(): Promise<void> {
215
- if (!Root.Runtime.hostConfig.devToolsGdpProfiles?.enabled || Root.Runtime.hostConfig.isOffTheRecord) {
217
+ if (!Host.GdpClient.isGdpProfilesAvailable()) {
216
218
  return;
217
219
  }
218
220
 
@@ -251,16 +253,29 @@ function renderWarningIfNeeded(syncInfo: Host.InspectorFrontendHostAPI.SyncInfor
251
253
  'chrome://settings/syncSetup/advanced' as Platform.DevToolsPath.UrlString;
252
254
  const warningText =
253
255
  !syncInfo.isSyncActive ? i18nString(UIStrings.syncDisabled) : i18nString(UIStrings.preferencesSyncDisabled);
256
+ const handleClick = (event: Event): void => {
257
+ const rootTarget = SDK.TargetManager.TargetManager.instance().rootTarget();
258
+ if (rootTarget === null) {
259
+ return;
260
+ }
261
+
262
+ void rootTarget.targetAgent().invoke_createTarget({url: warningLink}).then(result => {
263
+ if (result.getError()) {
264
+ Host.InspectorFrontendHost.InspectorFrontendHostInstance.openInNewTab(warningLink);
265
+ }
266
+ });
267
+ event.consume();
268
+ };
254
269
  // clang-format off
255
270
  return html`
256
- <devtools-chrome-link .href=${warningLink}>
257
- <devtools-button
258
- aria-describedby=settings-sync-info
259
- .iconName=${'info'}
260
- .variant=${Buttons.Button.Variant.ICON}
261
- .size=${Buttons.Button.Size.SMALL}>
262
- </devtools-button>
263
- </devtools-chrome-link>
271
+ <devtools-button
272
+ aria-describedby=settings-sync-info
273
+ aria-label=${warningText}
274
+ .iconName=${'info'}
275
+ .variant=${Buttons.Button.Variant.ICON}
276
+ .size=${Buttons.Button.Size.SMALL}
277
+ @click=${handleClick}>
278
+ </devtools-button>
264
279
  <devtools-tooltip
265
280
  id=settings-sync-info
266
281
  variant=simple>
@@ -304,21 +319,25 @@ function renderGdpSectionIfNeeded({
304
319
  gdpProfile?: Host.GdpClient.Profile,
305
320
  isEligibleToCreateProfile?: boolean,
306
321
  }): Lit.LitTemplate {
307
- // clang-format off
308
- if (!Root.Runtime.hostConfig.devToolsGdpProfiles?.enabled || (!gdpProfile && !isEligibleToCreateProfile)) {
322
+ if (!Host.GdpClient.isGdpProfilesAvailable() || (!gdpProfile && !isEligibleToCreateProfile)) {
309
323
  return Lit.nothing;
310
324
  }
325
+ const hasReceiveBadgesCheckbox = receiveBadgesSetting &&
326
+ Host.GdpClient.getGdpProfilesEnterprisePolicy() === Root.Runtime.GdpProfilesEnterprisePolicyValue.ENABLED;
311
327
 
312
328
  function renderBrand(): Lit.LitTemplate {
329
+ // clang-format off
313
330
  return html`
314
331
  <div class="gdp-profile-header">
315
- <div class="gdp-logo" role="img" tabindex="0" aria-label="Google Developer Program"></div>
332
+ <div class="gdp-logo" role="img" aria-label="Google Developer Program"></div>
316
333
  </div>
317
334
  `;
335
+ // clang-format on
318
336
  }
319
337
 
338
+ // clang-format off
320
339
  return html`
321
- <div class="gdp-profile-container">
340
+ <div class="gdp-profile-container" jslog=${VisualLogging.section().context('gdp-profile')}>
322
341
  <div class="divider"></div>
323
342
  ${gdpProfile ? html`
324
343
  <div class="gdp-profile-details-content">
@@ -326,10 +345,13 @@ function renderGdpSectionIfNeeded({
326
345
  <div class="plan-details">
327
346
  ${getGdpSubscriptionText(gdpProfile)}
328
347
  &nbsp;·&nbsp;
329
- <x-link class="link" href=${Host.GdpClient.GOOGLE_DEVELOPER_PROGRAM_PROFILE_LINK}>
348
+ <x-link
349
+ jslog=${VisualLogging.link().track({click: true, keydown:'Enter|Space'}).context('view-profile')}
350
+ class="link"
351
+ href=${Host.GdpClient.GOOGLE_DEVELOPER_PROGRAM_PROFILE_LINK}>
330
352
  ${i18nString(UIStrings.viewProfile)}
331
353
  </x-link></div>
332
- ${receiveBadgesSetting ? html`
354
+ ${hasReceiveBadgesCheckbox ? html`
333
355
  <div class="setting-container" ${ref(receiveBadgesSettingContainerRef)}>
334
356
  <setting-checkbox class="setting-checkbox" .data=${{setting: receiveBadgesSetting}} @change=${(e: Event) => {
335
357
  const settingCheckbox = e.target as SettingsComponents.SettingCheckbox.SettingCheckbox;
@@ -351,7 +373,7 @@ function renderGdpSectionIfNeeded({
351
373
  @click=${() => PanelCommon.GdpSignUpDialog.show({
352
374
  onSuccess: onSignUpSuccess
353
375
  })}
354
- .jslogContext=${'gdp.sign-up-dialog-open'}
376
+ .jslogContext=${'open-sign-up-dialog'}
355
377
  .variant=${Buttons.Button.Variant.OUTLINED}>
356
378
  ${i18nString(UIStrings.signUp)}
357
379
  </devtools-button>
@@ -359,8 +381,8 @@ function renderGdpSectionIfNeeded({
359
381
  `}
360
382
  </div>
361
383
  `;
384
+ // clang-format on
362
385
  }
363
- // clang-format on
364
386
 
365
387
  customElements.define('devtools-sync-section', SyncSection);
366
388
 
@@ -585,7 +585,7 @@ export class UserAgentClientHintsForm extends HTMLElement {
585
585
  ${i18nString(UIStrings.mobileCheckboxLabel)}
586
586
  </label>
587
587
  ` :
588
- html``;
588
+ Lit.nothing;
589
589
  return html`
590
590
  <span class="full-row label">${i18nString(UIStrings.deviceModel)}</span>
591
591
  <div class="full-row brand-row" aria-label=${i18nString(UIStrings.deviceProperties)} role="group">
@@ -18,6 +18,7 @@ import {Plugin} from './Plugin.js';
18
18
 
19
19
  const AI_CODE_COMPLETION_CHARACTER_LIMIT = 20_000;
20
20
  const DISCLAIMER_TOOLTIP_ID = 'sources-ai-code-completion-disclaimer-tooltip';
21
+ const SPINNER_TOOLTIP_ID = 'sources-ai-code-completion-spinner-tooltip';
21
22
  const CITATIONS_TOOLTIP_ID = 'sources-ai-code-completion-citations-tooltip';
22
23
 
23
24
  export class AiCodeCompletionPlugin extends Plugin {
@@ -58,6 +59,9 @@ export class AiCodeCompletionPlugin extends Plugin {
58
59
  if (showTeaser) {
59
60
  this.#teaser = new PanelCommon.AiCodeCompletionTeaser({onDetach: this.#detachAiCodeCompletionTeaser.bind(this)});
60
61
  }
62
+
63
+ this.#aiCodeCompletionDisclaimerContainer.classList.add('ai-code-completion-disclaimer-container');
64
+ this.#aiCodeCompletionDisclaimerContainer.style.paddingInline = 'var(--sys-size-3)';
61
65
  }
62
66
 
63
67
  static override accepts(uiSourceCode: Workspace.UISourceCode.UISourceCode): boolean {
@@ -212,8 +216,11 @@ export class AiCodeCompletionPlugin extends Plugin {
212
216
  this.#teaser = undefined;
213
217
  }
214
218
  if (!this.#aiCodeCompletion) {
219
+ const contextFlavor = this.uiSourceCode.url().startsWith('snippet://') ?
220
+ AiCodeCompletion.AiCodeCompletion.ContextFlavor.CONSOLE :
221
+ AiCodeCompletion.AiCodeCompletion.ContextFlavor.SOURCES;
215
222
  this.#aiCodeCompletion = new AiCodeCompletion.AiCodeCompletion.AiCodeCompletion(
216
- {aidaClient: this.#aidaClient}, this.#editor, AiCodeCompletion.AiCodeCompletion.Panel.SOURCES);
223
+ {aidaClient: this.#aidaClient}, this.#editor, contextFlavor);
217
224
  this.#aiCodeCompletion.addEventListener(
218
225
  AiCodeCompletion.AiCodeCompletion.Events.REQUEST_TRIGGERED, this.#onAiRequestTriggered, this);
219
226
  this.#aiCodeCompletion.addEventListener(
@@ -229,6 +236,7 @@ export class AiCodeCompletionPlugin extends Plugin {
229
236
  }
230
237
  this.#aiCodeCompletionDisclaimer = new PanelCommon.AiCodeCompletionDisclaimer();
231
238
  this.#aiCodeCompletionDisclaimer.disclaimerTooltipId = DISCLAIMER_TOOLTIP_ID;
239
+ this.#aiCodeCompletionDisclaimer.spinnerTooltipId = SPINNER_TOOLTIP_ID;
232
240
  this.#aiCodeCompletionDisclaimer.show(this.#aiCodeCompletionDisclaimerContainer, undefined, true);
233
241
  }
234
242
 
@@ -38,6 +38,7 @@ import * as Platform from '../../core/platform/platform.js';
38
38
  import * as Root from '../../core/root/root.js';
39
39
  import * as SDK from '../../core/sdk/sdk.js';
40
40
  import * as Protocol from '../../generated/protocol.js';
41
+ import * as Badges from '../../models/badges/badges.js';
41
42
  import * as Bindings from '../../models/bindings/bindings.js';
42
43
  import * as Breakpoints from '../../models/breakpoints/breakpoints.js';
43
44
  import * as Extensions from '../../models/extensions/extensions.js';
@@ -484,6 +485,8 @@ export class SourcesPanel extends UI.Panel.Panel implements
484
485
  } else if (!this.#paused) {
485
486
  UI.Context.Context.instance().setFlavor(SDK.Target.Target, debuggerModel.target());
486
487
  }
488
+
489
+ Badges.UserBadges.instance().recordAction(Badges.BadgeAction.DEBUGGER_PAUSED);
487
490
  }
488
491
 
489
492
  private debugInfoAttached(event: Common.EventTarget.EventTargetEvent<SDK.Script.Script>): void {
@@ -1194,7 +1197,7 @@ export class SourcesPanel extends UI.Panel.Panel implements
1194
1197
  } else if (position === 'bottom') {
1195
1198
  vertically = true;
1196
1199
  } else {
1197
- vertically = UI.InspectorView.InspectorView.instance().element.offsetWidth < 680;
1200
+ vertically = this.splitWidget.element.offsetWidth < 680;
1198
1201
  }
1199
1202
 
1200
1203
  if (this.sidebarPaneView && vertically === !this.splitWidget.isVertical()) {
@@ -14,11 +14,16 @@
14
14
 
15
15
  #sources-panel-sources-view .sources-toolbar {
16
16
  display: flex;
17
- flex: 0 0 27px;
17
+ flex: 0 0 auto;
18
18
  background-color: var(--sys-color-cdt-base-container);
19
19
  border-top: 1px solid var(--sys-color-divider);
20
20
  overflow: hidden;
21
21
  z-index: 0;
22
+ align-items: flex-end;
23
+
24
+ devtools-toolbar:first-of-type {
25
+ flex-wrap: wrap;
26
+ }
22
27
  }
23
28
 
24
29
  .source-frame-debugger-script {
@@ -4,7 +4,7 @@
4
4
  import type * as Common from '../../core/common/common.js';
5
5
  import * as i18n from '../../core/i18n/i18n.js';
6
6
  import * as Trace from '../../models/trace/trace.js';
7
- import type * as PerfUI from '../../ui/legacy/components/perf_ui/perf_ui.js';
7
+ import * as PerfUI from '../../ui/legacy/components/perf_ui/perf_ui.js';
8
8
  import * as ThemeSupport from '../../ui/legacy/theme_support/theme_support.js';
9
9
 
10
10
  import type {VisualLoggingTrackName} from './CompatibilityTracksAppender.js';
@@ -36,7 +36,7 @@ export function buildGroupStyle(extra?: Partial<PerfUI.FlameChart.GroupStyle>):
36
36
  const defaultGroupStyle: PerfUI.FlameChart.GroupStyle = {
37
37
  padding: 4,
38
38
  height: 17,
39
- collapsible: true,
39
+ collapsible: PerfUI.FlameChart.GroupCollapsibleState.ALWAYS,
40
40
  color: ThemeSupport.ThemeSupport.instance().getComputedValue('--sys-color-on-surface'),
41
41
  backgroundColor: ThemeSupport.ThemeSupport.instance().getComputedValue('--sys-color-cdt-base-container'),
42
42
  nestingLevel: 0,
@@ -3,6 +3,7 @@
3
3
  // found in the LICENSE file.
4
4
  import * as i18n from '../../core/i18n/i18n.js';
5
5
  import * as Trace from '../../models/trace/trace.js';
6
+ import * as PerfUI from '../../ui/legacy/components/perf_ui/perf_ui.js';
6
7
  import * as ThemeSupport from '../../ui/legacy/theme_support/theme_support.js';
7
8
 
8
9
  import {buildGroupStyle, buildTrackHeader, getDurationString} from './AppenderUtils.js';
@@ -42,7 +43,8 @@ export class ExtensionTrackAppender implements TrackAppender {
42
43
  if (totalEntryCount === 0) {
43
44
  return trackStartLevel;
44
45
  }
45
- this.#appendTopLevelHeaderAtLevel(trackStartLevel, expanded);
46
+ const compact = !this.#extensionTopLevelTrack.isTrackGroup && totalEntryCount < 2;
47
+ this.#appendTopLevelHeaderAtLevel(trackStartLevel, compact, expanded);
46
48
  return this.#appendExtensionTrackData(trackStartLevel);
47
49
  }
48
50
 
@@ -52,8 +54,10 @@ export class ExtensionTrackAppender implements TrackAppender {
52
54
  * header corresponds to the track name, in the latter it corresponds
53
55
  * to the track group name.
54
56
  */
55
- #appendTopLevelHeaderAtLevel(currentLevel: number, expanded?: boolean): void {
56
- const style = buildGroupStyle({shareHeaderLine: false, collapsible: true});
57
+ #appendTopLevelHeaderAtLevel(currentLevel: number, compact: boolean, expanded?: boolean): void {
58
+ const style = compact ?
59
+ buildGroupStyle({shareHeaderLine: true, collapsible: PerfUI.FlameChart.GroupCollapsibleState.NEVER}) :
60
+ buildGroupStyle({shareHeaderLine: false, collapsible: PerfUI.FlameChart.GroupCollapsibleState.ALWAYS});
57
61
  const headerTitle = this.#extensionTopLevelTrack.name;
58
62
  const jsLogContext = this.#extensionTopLevelTrack.name === '🅰️ Angular' ? VisualLoggingTrackName.ANGULAR_TRACK :
59
63
  VisualLoggingTrackName.EXTENSION;
@@ -69,7 +73,12 @@ export class ExtensionTrackAppender implements TrackAppender {
69
73
  * corresponds to the track name itself, instead of the track name.
70
74
  */
71
75
  #appendSecondLevelHeader(trackStartLevel: number, headerTitle: string): void {
72
- const style = buildGroupStyle({shareHeaderLine: false, padding: 2, nestingLevel: 1, collapsible: true});
76
+ const style = buildGroupStyle({
77
+ shareHeaderLine: false,
78
+ padding: 2,
79
+ nestingLevel: 1,
80
+ collapsible: PerfUI.FlameChart.GroupCollapsibleState.ALWAYS
81
+ });
73
82
  const group = buildTrackHeader(
74
83
  VisualLoggingTrackName.EXTENSION, trackStartLevel, headerTitle, style,
75
84
  /* selectable= */ true);
@@ -3,6 +3,7 @@
3
3
  // found in the LICENSE file.
4
4
  import * as i18n from '../../core/i18n/i18n.js';
5
5
  import * as Trace from '../../models/trace/trace.js';
6
+ import * as PerfUI from '../../ui/legacy/components/perf_ui/perf_ui.js';
6
7
  import * as ThemeSupport from '../../ui/legacy/theme_support/theme_support.js';
7
8
 
8
9
  import {buildGroupStyle, buildTrackHeader} from './AppenderUtils.js';
@@ -63,7 +64,7 @@ export class GPUTrackAppender implements TrackAppender {
63
64
  * @param expanded whether the track should be rendered expanded.
64
65
  */
65
66
  #appendTrackHeaderAtLevel(currentLevel: number, expanded?: boolean): void {
66
- const style = buildGroupStyle({collapsible: false});
67
+ const style = buildGroupStyle({collapsible: PerfUI.FlameChart.GroupCollapsibleState.NEVER});
67
68
  const group = buildTrackHeader(
68
69
  VisualLoggingTrackName.GPU, currentLevel, i18nString(UIStrings.gpu), style, /* selectable= */ true, expanded);
69
70
  this.#compatibilityBuilder.registerTrackForGroup(group, this);
@@ -69,7 +69,11 @@ export class InteractionsTrackAppender implements TrackAppender {
69
69
  */
70
70
  #appendTrackHeaderAtLevel(currentLevel: number, expanded?: boolean): void {
71
71
  const trackIsCollapsible = this.#parsedTrace.data.UserInteractions.interactionEvents.length > 0;
72
- const style = buildGroupStyle({collapsible: trackIsCollapsible, useDecoratorsForOverview: true});
72
+ const style = buildGroupStyle({
73
+ collapsible: trackIsCollapsible ? PerfUI.FlameChart.GroupCollapsibleState.ALWAYS :
74
+ PerfUI.FlameChart.GroupCollapsibleState.NEVER,
75
+ useDecoratorsForOverview: true,
76
+ });
73
77
  const group = buildTrackHeader(
74
78
  VisualLoggingTrackName.INTERACTIONS, currentLevel, i18nString(UIStrings.interactions), style,
75
79
  /* selectable= */ true, expanded);
@@ -8,6 +8,7 @@ import * as i18n from '../../core/i18n/i18n.js';
8
8
  import * as Geometry from '../../models/geometry/geometry.js';
9
9
  import * as Trace from '../../models/trace/trace.js';
10
10
  import * as ComponentHelpers from '../../ui/components/helpers/helpers.js';
11
+ import * as PerfUI from '../../ui/legacy/components/perf_ui/perf_ui.js';
11
12
  import * as ThemeSupport from '../../ui/legacy/theme_support/theme_support.js';
12
13
 
13
14
  import {buildGroupStyle, buildTrackHeader} from './AppenderUtils.js';
@@ -85,7 +86,7 @@ export class LayoutShiftsTrackAppender implements TrackAppender {
85
86
  * appended.
86
87
  */
87
88
  #appendTrackHeaderAtLevel(currentLevel: number, expanded?: boolean): void {
88
- const style = buildGroupStyle({collapsible: false});
89
+ const style = buildGroupStyle({collapsible: PerfUI.FlameChart.GroupCollapsibleState.NEVER});
89
90
  const group = buildTrackHeader(
90
91
  VisualLoggingTrackName.LAYOUT_SHIFTS, currentLevel, i18nString(UIStrings.layoutShifts), style,
91
92
  /* selectable= */ true, expanded);
@@ -262,7 +262,11 @@ export class ThreadAppender implements TrackAppender {
262
262
  */
263
263
  #appendTrackHeaderAtLevel(currentLevel: number): void {
264
264
  const trackIsCollapsible = this.#entries.length > 0;
265
- const style = buildGroupStyle({shareHeaderLine: false, collapsible: trackIsCollapsible});
265
+ const style = buildGroupStyle({
266
+ shareHeaderLine: false,
267
+ collapsible: trackIsCollapsible ? PerfUI.FlameChart.GroupCollapsibleState.ALWAYS :
268
+ PerfUI.FlameChart.GroupCollapsibleState.NEVER,
269
+ });
266
270
  if (this.#headerNestingLevel !== null) {
267
271
  style.nestingLevel = this.#headerNestingLevel;
268
272
  }
@@ -304,7 +308,11 @@ export class ThreadAppender implements TrackAppender {
304
308
  const currentTrackCount = this.#compatibilityBuilder.getCurrentTrackCountForThreadType(threadType);
305
309
  if (currentTrackCount === 0) {
306
310
  const trackIsCollapsible = this.#entries.length > 0;
307
- const headerStyle = buildGroupStyle({shareHeaderLine: false, collapsible: trackIsCollapsible});
311
+ const headerStyle = buildGroupStyle({
312
+ shareHeaderLine: false,
313
+ collapsible: trackIsCollapsible ? PerfUI.FlameChart.GroupCollapsibleState.ALWAYS :
314
+ PerfUI.FlameChart.GroupCollapsibleState.NEVER,
315
+ });
308
316
 
309
317
  // Don't set any jslogcontext (first argument) because this is a shared
310
318
  // header group. Each child will have its context set.
@@ -315,7 +323,8 @@ export class ThreadAppender implements TrackAppender {
315
323
 
316
324
  // Nesting is set to 1 because the track is appended inside the
317
325
  // header for all raster threads.
318
- const titleStyle = buildGroupStyle({padding: 2, nestingLevel: 1, collapsible: false});
326
+ const titleStyle =
327
+ buildGroupStyle({padding: 2, nestingLevel: 1, collapsible: PerfUI.FlameChart.GroupCollapsibleState.NEVER});
319
328
  const rasterizerTitle = this.threadType === Trace.Handlers.Threads.ThreadType.RASTERIZER ?
320
329
  i18nString(UIStrings.rasterizerThreadS, {PH1: currentTrackCount + 1}) :
321
330
  i18nString(UIStrings.threadPoolThreadS, {PH1: currentTrackCount + 1});
@@ -152,8 +152,12 @@ export class TimelineFlameChartDataProvider extends Common.ObjectWrapper.ObjectW
152
152
  [this.droppedFramePattern, this.partialFramePattern] = this.preparePatternCanvas();
153
153
 
154
154
  this.framesGroupStyle = this.buildGroupStyle({useFirstLineForOverview: true});
155
- this.screenshotsGroupStyle =
156
- this.buildGroupStyle({useFirstLineForOverview: true, nestingLevel: 1, collapsible: false, itemsHeight: 150});
155
+ this.screenshotsGroupStyle = this.buildGroupStyle({
156
+ useFirstLineForOverview: true,
157
+ nestingLevel: 1,
158
+ collapsible: PerfUI.FlameChart.GroupCollapsibleState.NEVER,
159
+ itemsHeight: 150
160
+ });
157
161
 
158
162
  ThemeSupport.ThemeSupport.instance().addEventListener(ThemeSupport.ThemeChangeEvent.eventName, () => {
159
163
  const headers = [
@@ -427,7 +431,7 @@ export class TimelineFlameChartDataProvider extends Common.ObjectWrapper.ObjectW
427
431
  const defaultGroupStyle = {
428
432
  padding: 4,
429
433
  height: 17,
430
- collapsible: true,
434
+ collapsible: PerfUI.FlameChart.GroupCollapsibleState.ALWAYS,
431
435
  color: ThemeSupport.ThemeSupport.instance().getComputedValue('--sys-color-on-surface'),
432
436
  backgroundColor: ThemeSupport.ThemeSupport.instance().getComputedValue('--sys-color-cdt-base-container'),
433
437
  nestingLevel: 0,
@@ -774,7 +778,8 @@ export class TimelineFlameChartDataProvider extends Common.ObjectWrapper.ObjectW
774
778
  return;
775
779
  }
776
780
 
777
- this.framesGroupStyle.collapsible = hasScreenshots;
781
+ this.framesGroupStyle.collapsible =
782
+ hasScreenshots ? PerfUI.FlameChart.GroupCollapsibleState.ALWAYS : PerfUI.FlameChart.GroupCollapsibleState.NEVER;
778
783
  const expanded = Root.Runtime.Runtime.queryParam('flamechart-force-expand') === 'frames';
779
784
 
780
785
  this.appendHeader(i18nString(UIStrings.frames), this.framesGroupStyle, false /* selectable */, expanded);
@@ -2242,7 +2242,7 @@ export class TimelinePanel extends Common.ObjectWrapper.eventMixin<EventTypes, t
2242
2242
  }
2243
2243
 
2244
2244
  UI.Context.Context.instance().setFlavor(
2245
- AiAssistanceModel.AgentFocus, AiAssistanceModel.AgentFocus.full(parsedTrace));
2245
+ AiAssistanceModel.AgentFocus, AiAssistanceModel.AgentFocus.fromParsedTrace(parsedTrace));
2246
2246
  }
2247
2247
 
2248
2248
  #onAnnotationModifiedEvent(e: Event): void {
@@ -3079,7 +3079,8 @@ export class TimelinePanel extends Common.ObjectWrapper.eventMixin<EventTypes, t
3079
3079
  for (const modelName in insightsForNav.model) {
3080
3080
  const model = modelName as keyof Trace.Insights.Types.InsightModelsType;
3081
3081
  const insight = insightsForNav.model[model];
3082
- const formatter = new AiAssistanceModel.PerformanceInsightFormatter(parsedTrace, insight);
3082
+ const focus = AiAssistanceModel.AgentFocus.fromParsedTrace(parsedTrace);
3083
+ const formatter = new AiAssistanceModel.PerformanceInsightFormatter(focus, insight);
3083
3084
  if (!formatter.insightIsSupported()) {
3084
3085
  // Not all Insights are integrated with "Ask AI" yet, let's avoid
3085
3086
  // filling up the response with those ones because there will be no