| OLD | NEW |
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 |
| 5 /** @typedef {!{range: !Protocol.CSS.SourceRange, styleSheetId: !Protocol.CSS.St
yleSheetId, wasUsed: boolean}} */ |
| 6 WebInspector.CSSModel.RuleUsage; |
| 7 |
| 4 /** | 8 /** |
| 5 * @implements {WebInspector.TargetManager.Observer} | 9 * @implements {WebInspector.TargetManager.Observer} |
| 6 * @implements {WebInspector.TracingManagerClient} | 10 * @implements {WebInspector.TracingManagerClient} |
| 7 * @unrestricted | 11 * @unrestricted |
| 8 */ | 12 */ |
| 9 WebInspector.TimelineController = class { | 13 WebInspector.TimelineController = class { |
| 10 /** | 14 /** |
| 11 * @param {!WebInspector.Target} target | 15 * @param {!WebInspector.Target} target |
| 12 * @param {!WebInspector.TimelineLifecycleDelegate} delegate | 16 * @param {!WebInspector.TimelineLifecycleDelegate} delegate |
| 13 * @param {!WebInspector.TracingModel} tracingModel | 17 * @param {!WebInspector.TracingModel} tracingModel |
| 14 */ | 18 */ |
| 15 constructor(target, delegate, tracingModel) { | 19 constructor(target, delegate, tracingModel) { |
| 16 this._delegate = delegate; | 20 this._delegate = delegate; |
| 17 this._target = target; | 21 this._target = target; |
| 18 this._tracingModel = tracingModel; | 22 this._tracingModel = tracingModel; |
| 19 this._targets = []; | 23 this._targets = []; |
| 20 WebInspector.targetManager.observeTargets(this); | 24 WebInspector.targetManager.observeTargets(this); |
| 25 |
| 26 if (Runtime.experiments.isEnabled('timelineRuleUsageRecording')) |
| 27 this._markUnusedCSS = WebInspector.settings.createSetting('timelineMarkUnu
sedCSS', false); |
| 21 } | 28 } |
| 22 | 29 |
| 23 /** | 30 /** |
| 24 * @param {boolean} captureCauses | 31 * @param {boolean} captureCauses |
| 25 * @param {boolean} enableJSSampling | 32 * @param {boolean} enableJSSampling |
| 26 * @param {boolean} captureMemory | 33 * @param {boolean} captureMemory |
| 27 * @param {boolean} capturePictures | 34 * @param {boolean} capturePictures |
| 28 * @param {boolean} captureFilmStrip | 35 * @param {boolean} captureFilmStrip |
| 29 */ | 36 */ |
| 30 startRecording(captureCauses, enableJSSampling, captureMemory, capturePictures
, captureFilmStrip) { | 37 startRecording(captureCauses, enableJSSampling, captureMemory, capturePictures
, captureFilmStrip) { |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 67 | 74 |
| 68 var categories = categoriesArray.join(','); | 75 var categories = categoriesArray.join(','); |
| 69 this._startRecordingWithCategories(categories, enableJSSampling); | 76 this._startRecordingWithCategories(categories, enableJSSampling); |
| 70 } | 77 } |
| 71 | 78 |
| 72 stopRecording() { | 79 stopRecording() { |
| 73 var tracingStoppedPromises = []; | 80 var tracingStoppedPromises = []; |
| 74 tracingStoppedPromises.push(new Promise(resolve => this._tracingCompleteCall
back = resolve)); | 81 tracingStoppedPromises.push(new Promise(resolve => this._tracingCompleteCall
back = resolve)); |
| 75 tracingStoppedPromises.push(this._stopProfilingOnAllTargets()); | 82 tracingStoppedPromises.push(this._stopProfilingOnAllTargets()); |
| 76 this._target.tracingManager.stop(); | 83 this._target.tracingManager.stop(); |
| 77 tracingStoppedPromises.push(WebInspector.targetManager.resumeAllTargets()); | 84 |
| 85 if (!Runtime.experiments.isEnabled('timelineRuleUsageRecording') || !this._m
arkUnusedCSS.get()) |
| 86 tracingStoppedPromises.push(WebInspector.targetManager.resumeAllTargets())
; |
| 87 else |
| 88 this._addUnusedRulesToCoverage(); |
| 89 |
| 78 Promise.all(tracingStoppedPromises).then(() => this._allSourcesFinished()); | 90 Promise.all(tracingStoppedPromises).then(() => this._allSourcesFinished()); |
| 79 | 91 |
| 80 this._delegate.loadingStarted(); | 92 this._delegate.loadingStarted(); |
| 81 | 93 |
| 82 for (var traceProvider of this._extensionTraceProviders) | 94 for (var traceProvider of this._extensionTraceProviders) |
| 83 traceProvider.stop(); | 95 traceProvider.stop(); |
| 84 } | 96 } |
| 85 | 97 |
| 86 /** | 98 /** |
| 87 * @override | 99 * @override |
| 88 * @param {!WebInspector.Target} target | 100 * @param {!WebInspector.Target} target |
| 89 */ | 101 */ |
| 90 targetAdded(target) { | 102 targetAdded(target) { |
| 91 this._targets.push(target); | 103 this._targets.push(target); |
| 92 if (this._profiling) | 104 if (this._profiling) |
| 93 this._startProfilingOnTarget(target); | 105 this._startProfilingOnTarget(target); |
| 94 } | 106 } |
| 95 | 107 |
| 96 /** | 108 /** |
| 97 * @override | 109 * @override |
| 98 * @param {!WebInspector.Target} target | 110 * @param {!WebInspector.Target} target |
| 99 */ | 111 */ |
| 100 targetRemoved(target) { | 112 targetRemoved(target) { |
| 101 this._targets.remove(target, true); | 113 this._targets.remove(target, true); |
| 102 // FIXME: We'd like to stop profiling on the target and retrieve a profile | 114 // FIXME: We'd like to stop profiling on the target and retrieve a profile |
| 103 // but it's too late. Backend connection is closed. | 115 // but it's too late. Backend connection is closed. |
| 104 } | 116 } |
| 105 | 117 |
| 118 _addUnusedRulesToCoverage() { |
| 119 var mainTarget = WebInspector.targetManager.mainTarget(); |
| 120 if (!mainTarget) |
| 121 return; |
| 122 var cssModel = WebInspector.CSSModel.fromTarget(mainTarget); |
| 123 |
| 124 /** |
| 125 * @param {!Array<!WebInspector.CSSModel.RuleUsage>} ruleUsageList |
| 126 */ |
| 127 function ruleListReceived(ruleUsageList) { |
| 128 |
| 129 for (var rule of ruleUsageList) { |
| 130 if (rule.wasUsed) |
| 131 continue; |
| 132 |
| 133 var styleSheetHeader = cssModel.styleSheetHeaderForId(rule.styleSheetId)
; |
| 134 var url = styleSheetHeader.sourceURL; |
| 135 |
| 136 WebInspector.CoverageProfile.instance().appendUnusedRule(url, rule.range
); |
| 137 } |
| 138 } |
| 139 |
| 140 cssModel.ruleListPromise().then(ruleListReceived); |
| 141 } |
| 142 |
| 106 /** | 143 /** |
| 107 * @param {!WebInspector.Target} target | 144 * @param {!WebInspector.Target} target |
| 108 * @return {!Promise} | 145 * @return {!Promise} |
| 109 */ | 146 */ |
| 110 _startProfilingOnTarget(target) { | 147 _startProfilingOnTarget(target) { |
| 111 return target.hasJSCapability() ? target.profilerAgent().start() : Promise.r
esolve(); | 148 return target.hasJSCapability() ? target.profilerAgent().start() : Promise.r
esolve(); |
| 112 } | 149 } |
| 113 | 150 |
| 114 /** | 151 /** |
| 115 * @return {!Promise} | 152 * @return {!Promise} |
| (...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 153 this._profiling = false; | 190 this._profiling = false; |
| 154 return Promise.all(targets.map(this._stopProfilingOnTarget, this)); | 191 return Promise.all(targets.map(this._stopProfilingOnTarget, this)); |
| 155 } | 192 } |
| 156 | 193 |
| 157 /** | 194 /** |
| 158 * @param {string} categories | 195 * @param {string} categories |
| 159 * @param {boolean=} enableJSSampling | 196 * @param {boolean=} enableJSSampling |
| 160 * @param {function(?string)=} callback | 197 * @param {function(?string)=} callback |
| 161 */ | 198 */ |
| 162 _startRecordingWithCategories(categories, enableJSSampling, callback) { | 199 _startRecordingWithCategories(categories, enableJSSampling, callback) { |
| 163 WebInspector.targetManager.suspendAllTargets(); | 200 |
| 201 if (!Runtime.experiments.isEnabled('timelineRuleUsageRecording') || !this._m
arkUnusedCSS.get()) |
| 202 WebInspector.targetManager.suspendAllTargets(); |
| 203 |
| 164 var profilingStartedPromise = enableJSSampling && !Runtime.experiments.isEna
bled('timelineTracingJSProfile') ? | 204 var profilingStartedPromise = enableJSSampling && !Runtime.experiments.isEna
bled('timelineTracingJSProfile') ? |
| 165 this._startProfilingOnAllTargets() : | 205 this._startProfilingOnAllTargets() : |
| 166 Promise.resolve(); | 206 Promise.resolve(); |
| 167 var samplingFrequencyHz = WebInspector.moduleSetting('highResolutionCpuProfi
ling').get() ? 10000 : 1000; | 207 var samplingFrequencyHz = WebInspector.moduleSetting('highResolutionCpuProfi
ling').get() ? 10000 : 1000; |
| 168 var options = 'sampling-frequency=' + samplingFrequencyHz; | 208 var options = 'sampling-frequency=' + samplingFrequencyHz; |
| 169 var target = this._target; | 209 var target = this._target; |
| 170 var tracingManager = target.tracingManager; | 210 var tracingManager = target.tracingManager; |
| 171 WebInspector.targetManager.suspendReload(target); | 211 WebInspector.targetManager.suspendReload(target); |
| 172 profilingStartedPromise.then(tracingManager.start.bind(tracingManager, this,
categories, options, onTraceStarted)); | 212 profilingStartedPromise.then(tracingManager.start.bind(tracingManager, this,
categories, options, onTraceStarted)); |
| 173 /** | 213 /** |
| (...skipping 91 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 265 this._delegate.recordingProgress(usage); | 305 this._delegate.recordingProgress(usage); |
| 266 } | 306 } |
| 267 | 307 |
| 268 /** | 308 /** |
| 269 * @param {number} progress | 309 * @param {number} progress |
| 270 * @override | 310 * @override |
| 271 */ | 311 */ |
| 272 eventsRetrievalProgress(progress) { | 312 eventsRetrievalProgress(progress) { |
| 273 this._delegate.loadingProgress(progress); | 313 this._delegate.loadingProgress(progress); |
| 274 } | 314 } |
| 275 }; | 315 }; |
| OLD | NEW |