Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 1 | // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 | // Use of this source code is governed by a BSD-style license that can be |
| 3 | // found in the LICENSE file. |
| 4 | |
Rob Paveza | 96705c6 | 2020-01-08 01:37:48 | [diff] [blame] | 5 | Timeline.TimelinePaintProfilerView = class extends UI.SplitWidget { |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 6 | /** |
| 7 | * @param {!TimelineModel.TimelineFrameModel} frameModel |
| 8 | */ |
| 9 | constructor(frameModel) { |
| 10 | super(false, false); |
| 11 | this.element.classList.add('timeline-paint-profiler-view'); |
| 12 | this.setSidebarSize(60); |
| 13 | this.setResizable(false); |
| 14 | |
| 15 | this._frameModel = frameModel; |
| 16 | this._logAndImageSplitWidget = new UI.SplitWidget(true, false); |
| 17 | this._logAndImageSplitWidget.element.classList.add('timeline-paint-profiler-log-split'); |
| 18 | this.setMainWidget(this._logAndImageSplitWidget); |
Rob Paveza | 96705c6 | 2020-01-08 01:37:48 | [diff] [blame] | 19 | this._imageView = new Timeline.TimelinePaintImageView(); |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 20 | this._logAndImageSplitWidget.setMainWidget(this._imageView); |
| 21 | |
| 22 | this._paintProfilerView = new LayerViewer.PaintProfilerView(this._imageView.showImage.bind(this._imageView)); |
| 23 | this._paintProfilerView.addEventListener( |
| 24 | LayerViewer.PaintProfilerView.Events.WindowChanged, this._onWindowChanged, this); |
| 25 | this.setSidebarWidget(this._paintProfilerView); |
| 26 | |
| 27 | this._logTreeView = new LayerViewer.PaintProfilerCommandLogView(); |
| 28 | this._logAndImageSplitWidget.setSidebarWidget(this._logTreeView); |
| 29 | |
| 30 | this._needsUpdateWhenVisible = false; |
| 31 | /** @type {?SDK.PaintProfilerSnapshot} */ |
| 32 | this._pendingSnapshot = null; |
| 33 | /** @type {?SDK.TracingModel.Event} */ |
| 34 | this._event = null; |
| 35 | /** @type {?SDK.PaintProfilerModel} */ |
| 36 | this._paintProfilerModel = null; |
| 37 | /** @type {?SDK.PaintProfilerSnapshot} */ |
| 38 | this._lastLoadedSnapshot = null; |
| 39 | } |
| 40 | |
| 41 | /** |
| 42 | * @override |
| 43 | */ |
| 44 | wasShown() { |
| 45 | if (this._needsUpdateWhenVisible) { |
| 46 | this._needsUpdateWhenVisible = false; |
| 47 | this._update(); |
| 48 | } |
| 49 | } |
| 50 | |
| 51 | /** |
| 52 | * @param {!SDK.PaintProfilerSnapshot} snapshot |
| 53 | */ |
| 54 | setSnapshot(snapshot) { |
| 55 | this._releaseSnapshot(); |
| 56 | this._pendingSnapshot = snapshot; |
| 57 | this._event = null; |
| 58 | this._updateWhenVisible(); |
| 59 | } |
| 60 | |
| 61 | /** |
| 62 | * @param {!SDK.PaintProfilerModel} paintProfilerModel |
| 63 | * @param {!SDK.TracingModel.Event} event |
| 64 | * @return {boolean} |
| 65 | */ |
| 66 | setEvent(paintProfilerModel, event) { |
| 67 | this._releaseSnapshot(); |
| 68 | this._paintProfilerModel = paintProfilerModel; |
| 69 | this._pendingSnapshot = null; |
| 70 | this._event = event; |
| 71 | |
| 72 | this._updateWhenVisible(); |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 73 | if (this._event.name === TimelineModel.TimelineModel.RecordType.Paint) { |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 74 | return !!TimelineModel.TimelineData.forEvent(event).picture; |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 75 | } |
| 76 | if (this._event.name === TimelineModel.TimelineModel.RecordType.RasterTask) { |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 77 | return this._frameModel.hasRasterTile(this._event); |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 78 | } |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 79 | return false; |
| 80 | } |
| 81 | |
| 82 | _updateWhenVisible() { |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 83 | if (this.isShowing()) { |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 84 | this._update(); |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 85 | } else { |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 86 | this._needsUpdateWhenVisible = true; |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 87 | } |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 88 | } |
| 89 | |
| 90 | _update() { |
| 91 | this._logTreeView.setCommandLog([]); |
| 92 | this._paintProfilerView.setSnapshotAndLog(null, [], null); |
| 93 | |
| 94 | let snapshotPromise; |
| 95 | if (this._pendingSnapshot) { |
| 96 | snapshotPromise = Promise.resolve({rect: null, snapshot: this._pendingSnapshot}); |
| 97 | } else if (this._event.name === TimelineModel.TimelineModel.RecordType.Paint) { |
| 98 | const picture = TimelineModel.TimelineData.forEvent(this._event).picture; |
| 99 | snapshotPromise = picture.objectPromise() |
| 100 | .then(data => this._paintProfilerModel.loadSnapshot(data['skp64'])) |
| 101 | .then(snapshot => snapshot && {rect: null, snapshot: snapshot}); |
| 102 | } else if (this._event.name === TimelineModel.TimelineModel.RecordType.RasterTask) { |
| 103 | snapshotPromise = this._frameModel.rasterTilePromise(this._event); |
| 104 | } else { |
| 105 | console.assert(false, 'Unexpected event type or no snapshot'); |
| 106 | return; |
| 107 | } |
| 108 | snapshotPromise.then(snapshotWithRect => { |
| 109 | this._releaseSnapshot(); |
| 110 | if (!snapshotWithRect) { |
| 111 | this._imageView.showImage(); |
| 112 | return; |
| 113 | } |
| 114 | const snapshot = snapshotWithRect.snapshot; |
| 115 | this._lastLoadedSnapshot = snapshot; |
| 116 | this._imageView.setMask(snapshotWithRect.rect); |
| 117 | snapshot.commandLog().then(log => onCommandLogDone.call(this, snapshot, snapshotWithRect.rect, log)); |
| 118 | }); |
| 119 | |
| 120 | /** |
| 121 | * @param {!SDK.PaintProfilerSnapshot} snapshot |
| 122 | * @param {?Protocol.DOM.Rect} clipRect |
| 123 | * @param {!Array.<!SDK.PaintProfilerLogItem>=} log |
Rob Paveza | 96705c6 | 2020-01-08 01:37:48 | [diff] [blame] | 124 | * @this {Timeline.TimelinePaintProfilerView} |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 125 | */ |
| 126 | function onCommandLogDone(snapshot, clipRect, log) { |
| 127 | this._logTreeView.setCommandLog(log || []); |
| 128 | this._paintProfilerView.setSnapshotAndLog(snapshot, log || [], clipRect); |
| 129 | } |
| 130 | } |
| 131 | |
| 132 | _releaseSnapshot() { |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 133 | if (!this._lastLoadedSnapshot) { |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 134 | return; |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 135 | } |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 136 | this._lastLoadedSnapshot.release(); |
| 137 | this._lastLoadedSnapshot = null; |
| 138 | } |
| 139 | |
| 140 | _onWindowChanged() { |
| 141 | this._logTreeView.updateWindow(this._paintProfilerView.selectionWindow()); |
| 142 | } |
Rob Paveza | 96705c6 | 2020-01-08 01:37:48 | [diff] [blame] | 143 | }; |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 144 | |
| 145 | /** |
| 146 | * @unrestricted |
| 147 | */ |
Rob Paveza | 96705c6 | 2020-01-08 01:37:48 | [diff] [blame] | 148 | Timeline.TimelinePaintImageView = class extends UI.Widget { |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 149 | constructor() { |
| 150 | super(true); |
| 151 | this.registerRequiredCSS('timeline/timelinePaintProfiler.css'); |
| 152 | this.contentElement.classList.add('fill', 'paint-profiler-image-view'); |
| 153 | this._imageContainer = this.contentElement.createChild('div', 'paint-profiler-image-container'); |
| 154 | this._imageElement = this._imageContainer.createChild('img'); |
| 155 | this._maskElement = this._imageContainer.createChild('div'); |
| 156 | this._imageElement.addEventListener('load', this._updateImagePosition.bind(this), false); |
| 157 | |
| 158 | this._transformController = new LayerViewer.TransformController(this.contentElement, true); |
| 159 | this._transformController.addEventListener( |
| 160 | LayerViewer.TransformController.Events.TransformChanged, this._updateImagePosition, this); |
| 161 | } |
| 162 | |
| 163 | /** |
| 164 | * @override |
| 165 | */ |
| 166 | onResize() { |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 167 | if (this._imageElement.src) { |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 168 | this._updateImagePosition(); |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 169 | } |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 170 | } |
| 171 | |
| 172 | _updateImagePosition() { |
| 173 | const width = this._imageElement.naturalWidth; |
| 174 | const height = this._imageElement.naturalHeight; |
| 175 | const clientWidth = this.contentElement.clientWidth; |
| 176 | const clientHeight = this.contentElement.clientHeight; |
| 177 | |
| 178 | const paddingFraction = 0.1; |
| 179 | const paddingX = clientWidth * paddingFraction; |
| 180 | const paddingY = clientHeight * paddingFraction; |
| 181 | const scaleX = (clientWidth - paddingX) / width; |
| 182 | const scaleY = (clientHeight - paddingY) / height; |
| 183 | const scale = Math.min(scaleX, scaleY); |
| 184 | |
| 185 | if (this._maskRectangle) { |
| 186 | const style = this._maskElement.style; |
| 187 | style.width = width + 'px'; |
| 188 | style.height = height + 'px'; |
| 189 | style.borderLeftWidth = this._maskRectangle.x + 'px'; |
| 190 | style.borderTopWidth = this._maskRectangle.y + 'px'; |
| 191 | style.borderRightWidth = (width - this._maskRectangle.x - this._maskRectangle.width) + 'px'; |
| 192 | style.borderBottomWidth = (height - this._maskRectangle.y - this._maskRectangle.height) + 'px'; |
| 193 | } |
| 194 | this._transformController.setScaleConstraints(0.5, 10 / scale); |
| 195 | let matrix = new WebKitCSSMatrix() |
| 196 | .scale(this._transformController.scale(), this._transformController.scale()) |
| 197 | .translate(clientWidth / 2, clientHeight / 2) |
| 198 | .scale(scale, scale) |
| 199 | .translate(-width / 2, -height / 2); |
| 200 | const bounds = UI.Geometry.boundsForTransformedPoints(matrix, [0, 0, 0, width, height, 0]); |
| 201 | this._transformController.clampOffsets( |
| 202 | paddingX - bounds.maxX, clientWidth - paddingX - bounds.minX, paddingY - bounds.maxY, |
| 203 | clientHeight - paddingY - bounds.minY); |
| 204 | matrix = new WebKitCSSMatrix() |
| 205 | .translate(this._transformController.offsetX(), this._transformController.offsetY()) |
| 206 | .multiply(matrix); |
| 207 | this._imageContainer.style.webkitTransform = matrix.toString(); |
| 208 | } |
| 209 | |
| 210 | /** |
| 211 | * @param {string=} imageURL |
| 212 | */ |
| 213 | showImage(imageURL) { |
| 214 | this._imageContainer.classList.toggle('hidden', !imageURL); |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 215 | if (imageURL) { |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 216 | this._imageElement.src = imageURL; |
Tim van der Lippe | 1d6e57a | 2019-09-30 11:55:34 | [diff] [blame] | 217 | } |
Blink Reformat | 4c46d09 | 2018-04-07 15:32:37 | [diff] [blame] | 218 | } |
| 219 | |
| 220 | /** |
| 221 | * @param {?Protocol.DOM.Rect} maskRectangle |
| 222 | */ |
| 223 | setMask(maskRectangle) { |
| 224 | this._maskRectangle = maskRectangle; |
| 225 | this._maskElement.classList.toggle('hidden', !maskRectangle); |
| 226 | } |
Rob Paveza | 96705c6 | 2020-01-08 01:37:48 | [diff] [blame] | 227 | }; |