Skip to content

Commit

Permalink
🐎 Use dedicated pending changes array for back and front decorations
Browse files Browse the repository at this point in the history
No need to redraw the invalidated ranges from back decorations when
redrawing the front decorations.
  • Loading branch information
abe33 committed Dec 11, 2015
1 parent b78ad30 commit aef0c49
Show file tree
Hide file tree
Showing 3 changed files with 56 additions and 22 deletions.
7 changes: 6 additions & 1 deletion lib/minimap-element.js
Original file line number Diff line number Diff line change
Expand Up @@ -642,7 +642,12 @@ export default class MinimapElement {
}))

this.subscriptions.add(this.minimap.onDidChangeDecorationRange((change) => {
this.pendingDecorationChanges.push(change)
const {type} = change
if (type === 'line' || type === 'highlight-under') {
this.pendingBackDecorationChanges.push(change)
} else {
this.pendingFrontDecorationChanges.push(change)
}
this.requestUpdate()
}))

Expand Down
42 changes: 33 additions & 9 deletions lib/mixins/canvas-drawer.js
Original file line number Diff line number Diff line change
Expand Up @@ -41,13 +41,22 @@ export default class CanvasDrawer extends Mixin {
this.pendingChanges = []
}

if (!this.pendingDecorationChanges) {
if (!this.pendingBackDecorationChanges) {
/**
* Stores the changes from the minimap decorations.
* Stores the changes from the minimap back decorations.
* @type {Array<Object>}
* @access private
*/
this.pendingDecorationChanges = []
this.pendingBackDecorationChanges = []
}

if (!this.pendingFrontDecorationChanges) {
/**
* Stores the changes from the minimap front decorations.
* @type {Array<Object>}
* @access private
*/
this.pendingFrontDecorationChanges = []
}
}

Expand Down Expand Up @@ -92,10 +101,12 @@ export default class CanvasDrawer extends Mixin {
const lastRow = this.minimap.getLastVisibleScreenRow()

this.updateTokensLayer(firstRow, lastRow)
this.updateDecorationsLayers(firstRow, lastRow)
this.updateBackDecorationsLayers(firstRow, lastRow)
this.updateFrontDecorationsLayers(firstRow, lastRow)

this.pendingChanges = []
this.pendingDecorationChanges = []
this.pendingBackDecorationChanges = []
this.pendingFrontDecorationChanges = []

/**
* The first row in the last render of the offscreen canvas.
Expand Down Expand Up @@ -125,17 +136,30 @@ export default class CanvasDrawer extends Mixin {
}

/**
* Performs an update of the decoration layers using the pending changes
* and the pending decoration changes arrays.
* Performs an update of the back decorations layer using the pending changes
* and the pending back decorations changes arrays.
*
* @param {number} firstRow firstRow the first row of the range to update
* @param {number} lastRow lastRow the last row of the range to update
* @access private
*/
updateDecorationsLayers (firstRow, lastRow) {
const intactRanges = this.computeIntactRanges(firstRow, lastRow, this.pendingChanges.concat(this.pendingDecorationChanges))
updateBackDecorationsLayers (firstRow, lastRow) {
const intactRanges = this.computeIntactRanges(firstRow, lastRow, this.pendingChanges.concat(this.pendingBackDecorationChanges))

this.redrawRangesOnLayer(this.backLayer, intactRanges, firstRow, lastRow, this.drawBackDecorationsForLines)
}

/**
* Performs an update of the front decorations layer using the pending changes
* and the pending front decorations changes arrays.
*
* @param {number} firstRow firstRow the first row of the range to update
* @param {number} lastRow lastRow the last row of the range to update
* @access private
*/
updateFrontDecorationsLayers (firstRow, lastRow) {
const intactRanges = this.computeIntactRanges(firstRow, lastRow, this.pendingChanges.concat(this.pendingFrontDecorationChanges))

this.redrawRangesOnLayer(this.frontLayer, intactRanges, firstRow, lastRow, this.drawFrontDecorationsForLines)
}

Expand Down
29 changes: 17 additions & 12 deletions lib/mixins/decoration-management.js
Original file line number Diff line number Diff line change
Expand Up @@ -282,16 +282,16 @@ export default class DecorationManagement extends Mixin {
* highlight is rendered below the line's text.
* - __highlight-outline__: Renders a colored outline on the minimap. The
* highlight box is rendered above the line's text.
* @param {string} decorationParams.class the CSS class to use to retrieve
* @param {string} [decorationParams.class] the CSS class to use to retrieve
* the background color of the
* decoration by building a scop
* corresponding to
* `.minimap .editor <your-class>`
* @param {string} decorationParams.scope the scope to use to retrieve the
* @param {string} [decorationParams.scope] the scope to use to retrieve the
* decoration background. Note that if
* the `scope` property is set, the
* `class` won't be used.
* @param {string} decorationParams.color the CSS color to use to render the
* @param {string} [decorationParams.color] the CSS color to use to render the
* decoration. When set, neither
* `scope` nor `class` are used.
* @return {Decoration} the created decoration
Expand All @@ -307,6 +307,8 @@ export default class DecorationManagement extends Mixin {
decorationParams.type = 'highlight-over'
}

const {type} = decorationParams

if (decorationParams.scope == null && decorationParams['class'] != null) {
let cls = decorationParams['class'].split(' ').join('.')
decorationParams.scope = `.minimap .${cls}`
Expand Down Expand Up @@ -355,7 +357,7 @@ export default class DecorationManagement extends Mixin {

for (let i = 0, len = rangesDiffs.length; i < len; i++) {
let [start, end] = rangesDiffs[i]
this.emitRangeChanges({
this.emitRangeChanges(type, {
start: start,
end: end
}, 0)
Expand All @@ -375,7 +377,7 @@ export default class DecorationManagement extends Mixin {
if (this.decorationUpdatedSubscriptions[decoration.id] == null) {
this.decorationUpdatedSubscriptions[decoration.id] =
decoration.onDidChangeProperties((event) => {
this.emitDecorationChanges(decoration)
this.emitDecorationChanges(type, decoration)
})
}

Expand All @@ -384,7 +386,7 @@ export default class DecorationManagement extends Mixin {
this.removeDecoration(decoration)
})

this.emitDecorationChanges(decoration)
this.emitDecorationChanges(type, decoration)
this.emitter.emit('did-add-decoration', {
marker: marker,
decoration: decoration
Expand Down Expand Up @@ -426,29 +428,31 @@ export default class DecorationManagement extends Mixin {
* Emits a change in the `Minimap` corresponding to the
* passed-in decoration.
*
* @param {string} type the type of decoration that changed
* @param {Decoration} decoration the decoration for which emitting an event
* @access private
*/
emitDecorationChanges (decoration) {
emitDecorationChanges (type, decoration) {
if (decoration.marker.displayBuffer.isDestroyed()) { return }

this.invalidateDecorationForScreenRowsCache()

let range = decoration.marker.getScreenRange()
if (range == null) { return }

this.emitRangeChanges(range, 0)
this.emitRangeChanges(type, range, 0)
}

/**
* Emits a change for the specified range.
*
* @param {string} type the type of decoration that changed
* @param {Object} range the range where changes occured
* @param {number} [screenDelta] an optional screen delta for the
* change object
* @access private
*/
emitRangeChanges (range, screenDelta) {
emitRangeChanges (type, range, screenDelta) {
let startScreenRow = range.start.row
let endScreenRow = range.end.row
let lastRenderedScreenRow = this.getLastVisibleScreenRow()
Expand All @@ -462,7 +466,8 @@ export default class DecorationManagement extends Mixin {
let changeEvent = {
start: startScreenRow,
end: endScreenRow,
screenDelta: screenDelta
screenDelta: screenDelta,
type: type
}

this.emitter.emit('did-change-decoration-range', changeEvent)
Expand Down Expand Up @@ -495,7 +500,7 @@ export default class DecorationManagement extends Mixin {
let decorations = this.decorationsByMarkerId[marker.id]
if (!decorations) { return }

this.emitDecorationChanges(decoration)
this.emitDecorationChanges(decoration.getProperties().type, decoration)

let index = decorations.indexOf(decoration)
if (index > -1) {
Expand Down Expand Up @@ -528,7 +533,7 @@ export default class DecorationManagement extends Mixin {
for (let i = 0, len = decorations.length; i < len; i++) {
let decoration = decorations[i]

this.emitDecorationChanges(decoration)
this.emitDecorationChanges(decoration.getProperties().type, decoration)
this.emitter.emit('did-remove-decoration', {
marker: marker,
decoration: decoration
Expand Down

0 comments on commit aef0c49

Please sign in to comment.