Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(50)

Side by Side Diff: Source/devtools/front_end/FlameChart.js

Issue 214633002: FlameChart: vertical scroll implementation (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Created 6 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « no previous file | Source/devtools/front_end/flameChart.css » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /** 1 /**
2 * Copyright (C) 2013 Google Inc. All rights reserved. 2 * Copyright (C) 2013 Google Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are 5 * modification, are permitted provided that the following conditions are
6 * met: 6 * met:
7 * 7 *
8 * * Redistributions of source code must retain the above copyright 8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above 10 * * Redistributions in binary form must reproduce the above
(...skipping 25 matching lines...) Expand all
36 WebInspector.FlameChartDelegate.prototype = { 36 WebInspector.FlameChartDelegate.prototype = {
37 /** 37 /**
38 * @param {number} startTime 38 * @param {number} startTime
39 * @param {number} endTime 39 * @param {number} endTime
40 */ 40 */
41 requestWindowTimes: function(startTime, endTime) { }, 41 requestWindowTimes: function(startTime, endTime) { },
42 } 42 }
43 43
44 /** 44 /**
45 * @constructor 45 * @constructor
46 * @extends {WebInspector.VBox} 46 * @extends {WebInspector.HBox}
47 * @param {!WebInspector.FlameChartDataProvider} dataProvider 47 * @param {!WebInspector.FlameChartDataProvider} dataProvider
48 * @param {!WebInspector.FlameChartDelegate} flameChartDelegate 48 * @param {!WebInspector.FlameChartDelegate} flameChartDelegate
49 * @param {boolean} isTopDown 49 * @param {boolean} isTopDown
50 * @param {boolean} timeBasedWindow 50 * @param {boolean} timeBasedWindow
51 */ 51 */
52 WebInspector.FlameChart = function(dataProvider, flameChartDelegate, isTopDown, timeBasedWindow) 52 WebInspector.FlameChart = function(dataProvider, flameChartDelegate, isTopDown, timeBasedWindow)
53 { 53 {
54 WebInspector.VBox.call(this); 54 WebInspector.HBox.call(this);
55 this.element.classList.add("flame-chart-main-pane"); 55 this.element.classList.add("flame-chart-main-pane");
56 this._flameChartDelegate = flameChartDelegate; 56 this._flameChartDelegate = flameChartDelegate;
57 this._isTopDown = isTopDown; 57 this._isTopDown = isTopDown;
58 this._timeBasedWindow = timeBasedWindow; 58 this._timeBasedWindow = timeBasedWindow;
59 59
60 this._calculator = new WebInspector.FlameChart.Calculator(); 60 this._calculator = new WebInspector.FlameChart.Calculator();
61
62 this._canvas = this.element.createChild("canvas"); 61 this._canvas = this.element.createChild("canvas");
63 this._canvas.addEventListener("mousemove", this._onMouseMove.bind(this)); 62 this._canvas.addEventListener("mousemove", this._onMouseMove.bind(this));
64 this._canvas.addEventListener("mousewheel", this._onMouseWheel.bind(this), f alse); 63 this._canvas.addEventListener("mousewheel", this._onMouseWheel.bind(this), f alse);
65 this._canvas.addEventListener("click", this._onClick.bind(this), false); 64 this._canvas.addEventListener("click", this._onClick.bind(this), false);
66 WebInspector.installDragHandle(this._canvas, this._startCanvasDragging.bind( this), this._canvasDragging.bind(this), this._endCanvasDragging.bind(this), "mov e", null); 65 WebInspector.installDragHandle(this._canvas, this._startCanvasDragging.bind( this), this._canvasDragging.bind(this), this._endCanvasDragging.bind(this), "mov e", null);
66 this._vScrollElement = this.element.createChild("div", "flame-chart-v-scroll ");
67 this._vScrollContent = this._vScrollElement.createChild("div");
68 this._vScrollElement.addEventListener("scroll", this._scheduleUpdate.bind(th is), false);
67 69
68 this._entryInfo = this.element.createChild("div", "profile-entry-info"); 70 this._entryInfo = this.element.createChild("div", "profile-entry-info");
69 this._highlightElement = this.element.createChild("div", "flame-chart-highli ght-element"); 71 this._highlightElement = this.element.createChild("div", "flame-chart-highli ght-element");
70 this._selectedElement = this.element.createChild("div", "flame-chart-selecte d-element"); 72 this._selectedElement = this.element.createChild("div", "flame-chart-selecte d-element");
71 73
72 this._dataProvider = dataProvider; 74 this._dataProvider = dataProvider;
73 75
74 this._windowLeft = 0.0; 76 this._windowLeft = 0.0;
75 this._windowRight = 1.0; 77 this._windowRight = 1.0;
76 this._windowWidth = 1.0; 78 this._windowWidth = 1.0;
(...skipping 353 matching lines...) Expand 10 before | Expand all | Expand 10 after
430 432
431 /** 433 /**
432 * @param {?MouseEvent} e 434 * @param {?MouseEvent} e
433 */ 435 */
434 _onMouseWheel: function(e) 436 _onMouseWheel: function(e)
435 { 437 {
436 var windowLeft = this._timeWindowLeft ? this._timeWindowLeft : this._dat aProvider.zeroTime(); 438 var windowLeft = this._timeWindowLeft ? this._timeWindowLeft : this._dat aProvider.zeroTime();
437 var windowRight = this._timeWindowRight !== Infinity ? this._timeWindowR ight : this._dataProvider.zeroTime() + this._dataProvider.totalTime(); 439 var windowRight = this._timeWindowRight !== Infinity ? this._timeWindowR ight : this._dataProvider.zeroTime() + this._dataProvider.totalTime();
438 440
439 if (e.wheelDeltaY) { 441 if (e.wheelDeltaY) {
440 const mouseWheelZoomSpeed = 1 / 120; 442 if (e.altKey) {
441 var zoom = Math.pow(1.2, -e.wheelDeltaY * mouseWheelZoomSpeed) - 1; 443 const mouseWheelZoomSpeed = 1 / 120;
442 var cursorTime = this._cursorTime(e.offsetX); 444 var zoom = Math.pow(1.2, -e.wheelDeltaY * mouseWheelZoomSpeed) - 1;
443 windowLeft += (windowLeft - cursorTime) * zoom; 445 var cursorTime = this._cursorTime(e.offsetX);
444 windowRight += (windowRight - cursorTime) * zoom; 446 windowLeft += (windowLeft - cursorTime) * zoom;
447 windowRight += (windowRight - cursorTime) * zoom;
448 } else
449 this._vScrollElement.scrollTop += -e.wheelDeltaY / 120 * this._o ffsetHeight / 8;
pfeldman 2014/03/27 12:48:04 += - ?
alph 2014/03/27 13:15:36 nit: perhaps move "e.wheelDeltaY / 120" out of the
445 } else { 450 } else {
446 var shift = e.wheelDeltaX * this._pixelToTime; 451 var shift = e.wheelDeltaX * this._pixelToTime;
447 shift = Number.constrain(shift, this._zeroTime - windowLeft, this._t otalTime + this._zeroTime - windowRight); 452 shift = Number.constrain(shift, this._zeroTime - windowLeft, this._t otalTime + this._zeroTime - windowRight);
448 windowLeft += shift; 453 windowLeft += shift;
449 windowRight += shift; 454 windowRight += shift;
450 } 455 }
451 windowLeft = Number.constrain(windowLeft, this._zeroTime, this._totalTim e + this._zeroTime); 456 windowLeft = Number.constrain(windowLeft, this._zeroTime, this._totalTim e + this._zeroTime);
452 windowRight = Number.constrain(windowRight, this._zeroTime, this._totalT ime + this._zeroTime); 457 windowRight = Number.constrain(windowRight, this._zeroTime, this._totalT ime + this._zeroTime);
453 this._flameChartDelegate.requestWindowTimes(windowLeft, windowRight); 458 this._flameChartDelegate.requestWindowTimes(windowLeft, windowRight);
454 }, 459 },
455 460
456 /** 461 /**
457 * @param {number} x 462 * @param {number} x
458 * @return {number} 463 * @return {number}
459 */ 464 */
460 _cursorTime: function(x) 465 _cursorTime: function(x)
461 { 466 {
462 return (x + this._pixelWindowLeft - this._paddingLeft) * this._pixelToTi me + this._zeroTime; 467 return (x + this._pixelWindowLeft - this._paddingLeft) * this._pixelToTi me + this._zeroTime;
463 }, 468 },
464 469
465 /** 470 /**
466 * @param {!number} x 471 * @param {!number} x
467 * @param {!number} y 472 * @param {!number} y
468 */ 473 */
469 _coordinatesToEntryIndex: function(x, y) 474 _coordinatesToEntryIndex: function(x, y)
470 { 475 {
476 y += this._scrollTop;
pfeldman 2014/03/27 12:48:04 How does this work with the retina?
471 var timelineData = this._timelineData(); 477 var timelineData = this._timelineData();
472 if (!timelineData) 478 if (!timelineData)
473 return -1; 479 return -1;
474 var cursorTimeOffset = this._cursorTime(x) - this._zeroTime; 480 var cursorTimeOffset = this._cursorTime(x) - this._zeroTime;
475 var cursorLevel = this._isTopDown ? Math.floor((y - WebInspector.FlameCh art.DividersBarHeight) / this._barHeight) : Math.floor((this._canvas.height / wi ndow.devicePixelRatio - y) / this._barHeight); 481 var cursorLevel = this._isTopDown ? Math.floor((y - WebInspector.FlameCh art.DividersBarHeight) / this._barHeight) : Math.floor((this._canvas.height / wi ndow.devicePixelRatio - y) / this._barHeight);
476 var entryOffsets = timelineData.entryOffsets; 482 var entryOffsets = timelineData.entryOffsets;
477 var entryTotalTimes = timelineData.entryTotalTimes; 483 var entryTotalTimes = timelineData.entryTotalTimes;
478 var entryLevels = timelineData.entryLevels; 484 var entryLevels = timelineData.entryLevels;
479 var length = entryOffsets.length; 485 var length = entryOffsets.length;
480 for (var i = 0; i < length; ++i) { 486 for (var i = 0; i < length; ++i) {
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
518 var lastTitleIndex = 0; 524 var lastTitleIndex = 0;
519 var textPadding = this._dataProvider.textPadding(); 525 var textPadding = this._dataProvider.textPadding();
520 this._minTextWidth = 2 * textPadding + this._measureWidth(context, "\u20 26"); 526 this._minTextWidth = 2 * textPadding + this._measureWidth(context, "\u20 26");
521 var minTextWidth = this._minTextWidth; 527 var minTextWidth = this._minTextWidth;
522 528
523 var lastDrawOffset = new Int32Array(this._dataProvider.maxStackDepth()); 529 var lastDrawOffset = new Int32Array(this._dataProvider.maxStackDepth());
524 for (var i = 0; i < lastDrawOffset.length; ++i) 530 for (var i = 0; i < lastDrawOffset.length; ++i)
525 lastDrawOffset[i] = -1; 531 lastDrawOffset[i] = -1;
526 532
527 var barHeight = this._barHeight; 533 var barHeight = this._barHeight;
528 this._baseHeight = this._isTopDown ? WebInspector.FlameChart.DividersBar Height : height - barHeight;
529 534
530 var offsetToPosition = this._offsetToPosition.bind(this); 535 var offsetToPosition = this._offsetToPosition.bind(this);
531 var textBaseHeight = this._baseHeight + barHeight - this._dataProvider.t extBaseline(); 536 var textBaseHeight = this._baseHeight + barHeight - this._dataProvider.t extBaseline();
532 var colorBuckets = {}; 537 var colorBuckets = {};
533 var maxBarLevel = Math.min(this._dataProvider.maxStackDepth(), Math.ceil (height / barHeight)); 538 var minVisibleBarLevel = Math.max(0, Math.floor((this._scrollTop - this. _baseHeight) / barHeight));
539 var maxVisibleBarLevel = Math.min(this._dataProvider.maxStackDepth(), Ma th.ceil((height + this._scrollTop) / barHeight));
540 var visibleBarsCount = maxVisibleBarLevel - minVisibleBarLevel + 1;
534 541
542 context.translate(0, -this._scrollTop * ratio);
535 var levelsCompleted = 0; 543 var levelsCompleted = 0;
536 var lastEntryOnLevelPainted = []; 544 var lastEntryOnLevelPainted = [];
537 for (var i = 0; i < maxBarLevel; ++i) 545 for (var i = 0; i < visibleBarsCount; ++i)
538 lastEntryOnLevelPainted[i] = false; 546 lastEntryOnLevelPainted[i] = false;
539 547
540 for (var entryIndex = 0; levelsCompleted < maxBarLevel && entryIndex < e ntryOffsets.length; ++entryIndex) { 548 for (var entryIndex = 0; levelsCompleted < visibleBarsCount && entryInde x < entryOffsets.length; ++entryIndex) {
541 // skip if it is not visible (top/bottom side) 549 // skip if it is not visible (top/bottom side)
542 var barLevel = entryLevels[entryIndex]; 550 var barLevel = entryLevels[entryIndex];
543 if (barLevel > maxBarLevel || lastEntryOnLevelPainted[barLevel]) 551 if (barLevel < minVisibleBarLevel || barLevel > maxVisibleBarLevel | | lastEntryOnLevelPainted[barLevel - minVisibleBarLevel])
544 continue; 552 continue;
545 553
546 // stop if we reached right border in time (entries were ordered by start time). 554 // stop if we reached right border in time (entries were ordered by start time).
547 var entryOffset = entryOffsets[entryIndex]; 555 var entryOffset = entryOffsets[entryIndex];
548 if (entryOffset > timeWindowRight) { 556 if (entryOffset > timeWindowRight) {
549 lastEntryOnLevelPainted[barLevel] = true; 557 lastEntryOnLevelPainted[barLevel - minVisibleBarLevel] = true;
550 levelsCompleted++; 558 levelsCompleted++;
551 continue; 559 continue;
552 } 560 }
553 561
554 // skip if it is not visible (left side). 562 // skip if it is not visible (left side).
555 var entryOffsetRight = entryOffset + entryTotalTimes[entryIndex]; 563 var entryOffsetRight = entryOffset + entryTotalTimes[entryIndex];
556 if (entryOffsetRight < timeWindowLeft) 564 if (entryOffsetRight < timeWindowLeft)
557 continue; 565 continue;
558 566
559 var barRight = this._offsetToPosition(entryOffsetRight); 567 var barRight = this._offsetToPosition(entryOffsetRight);
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after
645 return; 653 return;
646 var timeRange = this._dataProvider.highlightTimeRange(entryIndex); 654 var timeRange = this._dataProvider.highlightTimeRange(entryIndex);
647 if (!timeRange) 655 if (!timeRange)
648 return; 656 return;
649 var timelineData = this._timelineData(); 657 var timelineData = this._timelineData();
650 var barX = this._offsetToPosition(timeRange.startTimeOffset); 658 var barX = this._offsetToPosition(timeRange.startTimeOffset);
651 var barRight = this._offsetToPosition(timeRange.endTimeOffset); 659 var barRight = this._offsetToPosition(timeRange.endTimeOffset);
652 if (barRight === 0 || barX === this._canvas.width) 660 if (barRight === 0 || barX === this._canvas.width)
653 return; 661 return;
654 var barWidth = Math.max(barRight - barX, this._minWidth); 662 var barWidth = Math.max(barRight - barX, this._minWidth);
655 var barY = this._levelToHeight(timelineData.entryLevels[entryIndex]); 663 var barY = this._levelToHeight(timelineData.entryLevels[entryIndex]) - t his._scrollTop;
656 var style = element.style; 664 var style = element.style;
657 style.left = barX + "px"; 665 style.left = barX + "px";
658 style.top = barY + "px"; 666 style.top = barY + "px";
659 style.width = barWidth + "px"; 667 style.width = barWidth + "px";
660 style.height = this._barHeight + "px"; 668 style.height = this._barHeight + "px";
661 this.element.appendChild(element); 669 this.element.appendChild(element);
662 }, 670 },
663 671
664 _offsetToPosition: function(offset) 672 _offsetToPosition: function(offset)
665 { 673 {
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after
749 } 757 }
750 758
751 this._pixelWindowWidth = this._offsetWidth - this._paddingLeft; 759 this._pixelWindowWidth = this._offsetWidth - this._paddingLeft;
752 this._totalPixels = Math.floor(this._pixelWindowWidth / this._windowWidt h); 760 this._totalPixels = Math.floor(this._pixelWindowWidth / this._windowWidt h);
753 this._pixelWindowLeft = Math.floor(this._totalPixels * this._windowLeft) ; 761 this._pixelWindowLeft = Math.floor(this._totalPixels * this._windowLeft) ;
754 this._pixelWindowRight = Math.floor(this._totalPixels * this._windowRigh t); 762 this._pixelWindowRight = Math.floor(this._totalPixels * this._windowRigh t);
755 763
756 this._timeToPixel = this._totalPixels / this._totalTime; 764 this._timeToPixel = this._totalPixels / this._totalTime;
757 this._pixelToTime = this._totalTime / this._totalPixels; 765 this._pixelToTime = this._totalTime / this._totalPixels;
758 this._paddingLeftTime = this._paddingLeft / this._timeToPixel; 766 this._paddingLeftTime = this._paddingLeft / this._timeToPixel;
767
768 this._baseHeight = this._isTopDown ? WebInspector.FlameChart.DividersBar Height : this._offsetHeight - this._barHeight;
769
770 var totalHeight = this._levelToHeight(this._dataProvider.maxStackDepth() );
771 this._vScrollContent.style.height = totalHeight + "px";
772 this._scrollTop = this._vScrollElement.scrollTop;
759 }, 773 },
760 774
761 onResize: function() 775 onResize: function()
762 { 776 {
763 this._offsetWidth = this.element.offsetWidth; 777 this._offsetWidth = this.element.offsetWidth - this._vScrollElement.offs etWidth;
764 this._offsetHeight = this.element.offsetHeight; 778 this._offsetHeight = this.element.offsetHeight;
765 this._canvas.style.width = this._offsetWidth + "px"; 779 this._canvas.style.width = this._offsetWidth + "px";
766 this._canvas.style.height = this._offsetHeight + "px"; 780 this._canvas.style.height = this._offsetHeight + "px";
767 this._scheduleUpdate(); 781 this._scheduleUpdate();
768 }, 782 },
769 783
770 _scheduleUpdate: function() 784 _scheduleUpdate: function()
771 { 785 {
772 if (this._updateTimerId) 786 if (this._updateTimerId)
773 return; 787 return;
(...skipping 12 matching lines...) Expand all
786 }, 800 },
787 801
788 reset: function() 802 reset: function()
789 { 803 {
790 this._highlightedEntryIndex = -1; 804 this._highlightedEntryIndex = -1;
791 this._selectedEntryIndex = -1; 805 this._selectedEntryIndex = -1;
792 this._textWidth = {}; 806 this._textWidth = {};
793 this.update(); 807 this.update();
794 }, 808 },
795 809
796 __proto__: WebInspector.VBox.prototype 810 __proto__: WebInspector.HBox.prototype
797 } 811 }
OLDNEW
« no previous file with comments | « no previous file | Source/devtools/front_end/flameChart.css » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698