| 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 /** | 4 /** |
| 5 * @unrestricted | 5 * @unrestricted |
| 6 */ | 6 */ |
| 7 WebInspector.Segment = class { | 7 Common.Segment = class { |
| 8 /** | 8 /** |
| 9 * @param {number} begin | 9 * @param {number} begin |
| 10 * @param {number} end | 10 * @param {number} end |
| 11 * @param {*} data | 11 * @param {*} data |
| 12 */ | 12 */ |
| 13 constructor(begin, end, data) { | 13 constructor(begin, end, data) { |
| 14 if (begin > end) | 14 if (begin > end) |
| 15 console.assert(false, 'Invalid segment'); | 15 console.assert(false, 'Invalid segment'); |
| 16 this.begin = begin; | 16 this.begin = begin; |
| 17 this.end = end; | 17 this.end = end; |
| 18 this.data = data; | 18 this.data = data; |
| 19 } | 19 } |
| 20 | 20 |
| 21 /** | 21 /** |
| 22 * @param {!WebInspector.Segment} that | 22 * @param {!Common.Segment} that |
| 23 * @return {boolean} | 23 * @return {boolean} |
| 24 */ | 24 */ |
| 25 intersects(that) { | 25 intersects(that) { |
| 26 return this.begin < that.end && that.begin < this.end; | 26 return this.begin < that.end && that.begin < this.end; |
| 27 } | 27 } |
| 28 }; | 28 }; |
| 29 | 29 |
| 30 /** | 30 /** |
| 31 * @unrestricted | 31 * @unrestricted |
| 32 */ | 32 */ |
| 33 WebInspector.SegmentedRange = class { | 33 Common.SegmentedRange = class { |
| 34 /** | 34 /** |
| 35 * @param {(function(!WebInspector.Segment, !WebInspector.Segment): ?WebInspec
tor.Segment)=} mergeCallback | 35 * @param {(function(!Common.Segment, !Common.Segment): ?Common.Segment)=} mer
geCallback |
| 36 */ | 36 */ |
| 37 constructor(mergeCallback) { | 37 constructor(mergeCallback) { |
| 38 /** @type {!Array<!WebInspector.Segment>} */ | 38 /** @type {!Array<!Common.Segment>} */ |
| 39 this._segments = []; | 39 this._segments = []; |
| 40 this._mergeCallback = mergeCallback; | 40 this._mergeCallback = mergeCallback; |
| 41 } | 41 } |
| 42 | 42 |
| 43 /** | 43 /** |
| 44 * @param {!WebInspector.Segment} newSegment | 44 * @param {!Common.Segment} newSegment |
| 45 */ | 45 */ |
| 46 append(newSegment) { | 46 append(newSegment) { |
| 47 // 1. Find the proper insertion point for new segment | 47 // 1. Find the proper insertion point for new segment |
| 48 var startIndex = this._segments.lowerBound(newSegment, (a, b) => a.begin - b
.begin); | 48 var startIndex = this._segments.lowerBound(newSegment, (a, b) => a.begin - b
.begin); |
| 49 var endIndex = startIndex; | 49 var endIndex = startIndex; |
| 50 var merged = null; | 50 var merged = null; |
| 51 if (startIndex > 0) { | 51 if (startIndex > 0) { |
| 52 // 2. Try mering the preceding segment | 52 // 2. Try mering the preceding segment |
| 53 var precedingSegment = this._segments[startIndex - 1]; | 53 var precedingSegment = this._segments[startIndex - 1]; |
| 54 merged = this._tryMerge(precedingSegment, newSegment); | 54 merged = this._tryMerge(precedingSegment, newSegment); |
| 55 if (merged) { | 55 if (merged) { |
| 56 --startIndex; | 56 --startIndex; |
| 57 newSegment = merged; | 57 newSegment = merged; |
| 58 } else if (this._segments[startIndex - 1].end >= newSegment.begin) { | 58 } else if (this._segments[startIndex - 1].end >= newSegment.begin) { |
| 59 // 2a. If merge failed and segments overlap, adjust preceding segment. | 59 // 2a. If merge failed and segments overlap, adjust preceding segment. |
| 60 // If an old segment entirely contains new one, split it in two. | 60 // If an old segment entirely contains new one, split it in two. |
| 61 if (newSegment.end < precedingSegment.end) | 61 if (newSegment.end < precedingSegment.end) |
| 62 this._segments.splice( | 62 this._segments.splice( |
| 63 startIndex, 0, new WebInspector.Segment(newSegment.end, precedingS
egment.end, precedingSegment.data)); | 63 startIndex, 0, new Common.Segment(newSegment.end, precedingSegment
.end, precedingSegment.data)); |
| 64 precedingSegment.end = newSegment.begin; | 64 precedingSegment.end = newSegment.begin; |
| 65 } | 65 } |
| 66 } | 66 } |
| 67 // 3. Consume all segments that are entirely covered by the new one. | 67 // 3. Consume all segments that are entirely covered by the new one. |
| 68 while (endIndex < this._segments.length && this._segments[endIndex].end <= n
ewSegment.end) | 68 while (endIndex < this._segments.length && this._segments[endIndex].end <= n
ewSegment.end) |
| 69 ++endIndex; | 69 ++endIndex; |
| 70 // 4. Merge or adjust the succeeding segment if it overlaps. | 70 // 4. Merge or adjust the succeeding segment if it overlaps. |
| 71 if (endIndex < this._segments.length) { | 71 if (endIndex < this._segments.length) { |
| 72 merged = this._tryMerge(newSegment, this._segments[endIndex]); | 72 merged = this._tryMerge(newSegment, this._segments[endIndex]); |
| 73 if (merged) { | 73 if (merged) { |
| 74 endIndex++; | 74 endIndex++; |
| 75 newSegment = merged; | 75 newSegment = merged; |
| 76 } else if (newSegment.intersects(this._segments[endIndex])) | 76 } else if (newSegment.intersects(this._segments[endIndex])) |
| 77 this._segments[endIndex].begin = newSegment.end; | 77 this._segments[endIndex].begin = newSegment.end; |
| 78 } | 78 } |
| 79 this._segments.splice(startIndex, endIndex - startIndex, newSegment); | 79 this._segments.splice(startIndex, endIndex - startIndex, newSegment); |
| 80 } | 80 } |
| 81 | 81 |
| 82 /** | 82 /** |
| 83 * @param {!WebInspector.SegmentedRange} that | 83 * @param {!Common.SegmentedRange} that |
| 84 */ | 84 */ |
| 85 appendRange(that) { | 85 appendRange(that) { |
| 86 that.segments().forEach(segment => this.append(segment)); | 86 that.segments().forEach(segment => this.append(segment)); |
| 87 } | 87 } |
| 88 | 88 |
| 89 /** | 89 /** |
| 90 * @return {!Array<!WebInspector.Segment>} | 90 * @return {!Array<!Common.Segment>} |
| 91 */ | 91 */ |
| 92 segments() { | 92 segments() { |
| 93 return this._segments; | 93 return this._segments; |
| 94 } | 94 } |
| 95 | 95 |
| 96 /** | 96 /** |
| 97 * @param {!WebInspector.Segment} first | 97 * @param {!Common.Segment} first |
| 98 * @param {!WebInspector.Segment} second | 98 * @param {!Common.Segment} second |
| 99 * @return {?WebInspector.Segment} | 99 * @return {?Common.Segment} |
| 100 */ | 100 */ |
| 101 _tryMerge(first, second) { | 101 _tryMerge(first, second) { |
| 102 var merged = this._mergeCallback && this._mergeCallback(first, second); | 102 var merged = this._mergeCallback && this._mergeCallback(first, second); |
| 103 if (!merged) | 103 if (!merged) |
| 104 return null; | 104 return null; |
| 105 merged.begin = first.begin; | 105 merged.begin = first.begin; |
| 106 merged.end = Math.max(first.end, second.end); | 106 merged.end = Math.max(first.end, second.end); |
| 107 return merged; | 107 return merged; |
| 108 } | 108 } |
| 109 }; | 109 }; |
| OLD | NEW |