Handle consequences of item removal in the model

This commit is contained in:
Nathan Sobo
2014-01-09 16:05:00 -07:00
parent 2965d2e974
commit 073ea84d69
3 changed files with 36 additions and 26 deletions

View File

@@ -1,6 +1,7 @@
PaneModel = require '../src/pane-model'
PaneAxisModel = require '../src/pane-axis-model'
PaneContainerModel = require '../src/pane-container-model'
FocusContext = require '../src/focus-context'
describe "PaneModel", ->
describe "split methods", ->
@@ -83,6 +84,25 @@ describe "PaneModel", ->
pane2 = pane1.splitRight()
expect(pane2.focused).toBe true
describe "::removeItemAtIndex(index)", ->
describe "when the removal of the item causes blur to be called on the pane model", ->
it "remains focused if it was before the item was removed", ->
pane = new PaneModel(items: ["A", "B", "C"], focusContext: new FocusContext)
pane.on 'item-removed', -> pane.blur()
pane.focus()
pane.removeItemAtIndex(0)
expect(pane.focused).toBe true
pane.blur()
pane.removeItemAtIndex(0)
expect(pane.focused).toBe false
describe "when the last item is removed", ->
it "destroys the pane", ->
pane = new PaneModel(items: ["A", "B"])
pane.removeItemAtIndex(0)
pane.removeItemAtIndex(0)
expect(pane.isDestroyed()).toBe true
describe "::destroy()", ->
[pane1, container] = []

View File

@@ -94,16 +94,15 @@ class PaneModel extends Model
item
# Public:
removeItem: (item, detach) ->
removeItem: (item) ->
index = @items.indexOf(item)
@removeItemAtIndex(index, detach) if index >= 0
@removeItemAtIndex(index) if index >= 0
# Public: Just remove the item at the given index.
removeItemAtIndex: (index, detach) ->
removeItemAtIndex: (index) ->
item = @items[index]
@showNextItem() if item is @activeItem and @items.length > 1
@items.splice(index, 1)
@emit 'item-removed', item, index, detach
@suppressBlur => @items.splice(index, 1)
# Public: Moves the given item to a the new index.
moveItem: (item, newIndex) ->
@@ -115,7 +114,7 @@ class PaneModel extends Model
# Public: Moves the given item to another pane.
moveItemToPane: (item, pane, index) ->
pane.addItem(item, index)
@removeItem(item, true)
@removeItem(item)
# Public: Remove the currently active item.
destroyActiveItem: ->

View File

@@ -53,6 +53,8 @@ class Pane extends View
@is(':focus') or @is(':has(:focus)')
handleEvents: ->
@subscribe @model, 'destroyed', => @remove()
@subscribe @model.$activeItem, 'value', @onActiveItemChanged
@subscribe @model, 'item-added', @onItemAdded
@subscribe @model, 'item-removed', @onItemRemoved
@@ -158,12 +160,10 @@ class Pane extends View
@trigger 'pane:active-item-changed', [item]
onItemAdded: (item, index) =>
if typeof item.on is 'function'
@subscribe item, 'destroyed', => @destroyItem(item)
@trigger 'pane:item-added', [item, index]
onItemRemoved: (item, index, detach) =>
@cleanupItemView(item, detach)
onItemRemoved: (item, index) =>
@cleanupItemView(item)
@trigger 'pane:item-removed', [item, index]
onItemMoved: (item, newIndex) =>
@@ -181,27 +181,15 @@ class Pane extends View
@trigger 'pane:active-item-title-changed'
# Private:
cleanupItemView: (item, detach) ->
cleanupItemView: (item) ->
if item instanceof $
viewToRemove = item
else if viewToRemove = @viewsByItem.get(item)
@viewsByItem.delete(item)
if @items.length > 0
if detach and item is viewToRemove
viewToRemove?.detach()
else if detach and viewToRemove?.setModel
viewToRemove.setModel(null) # dont want to destroy the model, so set to null
viewToRemove.remove()
else
viewToRemove?.remove()
else
if detach and item is viewToRemove
viewToRemove?.detach()
else if detach and viewToRemove?.setModel
viewToRemove.setModel(null) # dont want to destroy the model, so set to null
@parent().view().removeChild(this)
if viewToRemove?
viewToRemove.setModel?(null)
viewToRemove.detach()
# Private:
viewForItem: (item) ->
@@ -231,6 +219,9 @@ class Pane extends View
getContainer: ->
@closest('.panes').view()
beforeRemove: ->
@trigger 'pane:removed', [this]
# Private:
remove: (selector, keepData) ->
return super if keepData