Add ability to cancel marker head position observations

This commit is contained in:
Nathan Sobo
2013-01-31 14:11:28 -07:00
parent bc44540b10
commit ec521b3fd3
4 changed files with 38 additions and 4 deletions

View File

@@ -707,15 +707,26 @@ describe 'Buffer', ->
describe "marker observation", ->
describe ".observeMarkerHeadPosition(marker, callback)", ->
observeHandler = null
beforeEach ->
observeHandler = jasmine.createSpy("observeHandler")
it "calls the given callback whenever the marker's head position changes", ->
marker = buffer.markRange([[4, 20], [4, 23]])
observeHandler = jasmine.createSpy("observeHandler")
buffer.observeMarkerHeadPosition(marker, observeHandler)
buffer.setMarkerHeadPosition(marker, [6, 2])
expect(observeHandler).toHaveBeenCalled()
expect(observeHandler.argsForCall[0][0]).toEqual [6, 2]
it "allows the observation subscription to be cancelled", ->
marker = buffer.markRange([[4, 20], [4, 23]])
subscription = buffer.observeMarkerHeadPosition(marker, observeHandler)
subscription.cancel()
buffer.setMarkerHeadPosition(marker, [6, 2])
expect(observeHandler).not.toHaveBeenCalled()
describe "marker updates due to buffer changes", ->
[marker1, marker2] = []

View File

@@ -604,10 +604,14 @@ describe "DisplayBuffer", ->
expect(displayBuffer.getMarkerBufferRange(marker)).toEqual [[5, 4], [8, 4]]
describe "observation", ->
observeHandler = null
beforeEach ->
observeHandler = jasmine.createSpy("observeHandler")
describe ".observeMarkerHeadScreenPosition(marker, callback)", ->
it "calls the callback whenever the markers head's screen position changes", ->
marker = displayBuffer.markScreenRange([[5, 4], [5, 10]])
observeHandler = jasmine.createSpy("observeHandler")
displayBuffer.observeMarkerHeadScreenPosition(marker, observeHandler)
displayBuffer.setMarkerHeadScreenPosition(marker, [8, 20])
expect(observeHandler).toHaveBeenCalled()
@@ -630,7 +634,6 @@ describe "DisplayBuffer", ->
it "does not call the callback for screen changes that don't change the position of the marker", ->
marker = displayBuffer.markScreenPosition([3, 4])
observeHandler = jasmine.createSpy("observeHandler")
displayBuffer.observeMarkerHeadScreenPosition(marker, observeHandler)
buffer.insert([3, 0], '...')
@@ -649,3 +652,13 @@ describe "DisplayBuffer", ->
fold.destroy()
expect(observeHandler).toHaveBeenCalled()
expect(observeHandler.argsForCall[0][0]).toEqual [3, 7]
it "allows observation subscriptions to be cancelled", ->
marker = displayBuffer.markScreenRange([[5, 4], [5, 10]])
subscription = displayBuffer.observeMarkerHeadScreenPosition(marker, observeHandler)
subscription.cancel()
buffer.insert([11, 0], '...')
expect(observeHandler).not.toHaveBeenCalled()
displayBuffer.unfoldBufferRow(4)
expect(observeHandler).not.toHaveBeenCalled()

View File

@@ -53,6 +53,8 @@ class BufferMarker
observeHeadPosition: (callback) ->
@headPositionObservers.push(callback)
cancel: =>
_.remove(@headPositionObservers, callback)
tryToInvalidate: (oldRange) ->
containsStart = oldRange.containsPoint(@getStartPosition(), exclusive: true)

View File

@@ -355,10 +355,18 @@ class DisplayBuffer
@markerScreenPositionObservers[id] ?= { head: [], tail: [] }
@cacheMarkerScreenPositions(id) unless @markerScreenPositions[id]
@markerScreenPositionObservers[id].head.push(callback)
@buffer.observeMarkerHeadPosition id, (bufferPosition) =>
subscription = @buffer.observeMarkerHeadPosition id, (bufferPosition) =>
@cacheMarkerScreenPositions(id)
callback(@screenPositionForBufferPosition(bufferPosition))
cancel: =>
subscription.cancel()
{ head, tail } = @markerScreenPositionObservers[id]
_.remove(head, callback)
unless head.length + tail.length
delete @markerScreenPositionObservers[id]
delete @markerScreenPositions[id]
cacheMarkerScreenPositions: (id) ->
@markerScreenPositions[id] = { head: @getMarkerHeadScreenPosition(id), tail: @getMarkerTailScreenPosition }