/* * Ext GWT - Ext for GWT * Copyright(c) 2007-2009, Ext JS, LLC. * licensing@extjs.com * * http://extjs.com/license */ package com.extjs.gxt.ui.client.widget; import java.util.Arrays; import com.extjs.gxt.ui.client.Style.SelectionMode; import com.extjs.gxt.ui.client.data.ModelData; import com.extjs.gxt.ui.client.event.ComponentEvent; import com.extjs.gxt.ui.client.event.EventType; import com.extjs.gxt.ui.client.event.Events; import com.extjs.gxt.ui.client.event.ListViewEvent; import com.extjs.gxt.ui.client.event.Listener; import com.extjs.gxt.ui.client.store.ListStore; import com.extjs.gxt.ui.client.util.KeyNav; import com.extjs.gxt.ui.client.widget.selection.AbstractStoreSelectionModel; /** * ListView selection model. * * <dl> * <dt>Inherited Events:</dt> * <dd>AbstractStoreSelectionModel BeforeSelect</dd> * <dd>AbstractStoreSelectionModel SelectionChange</dd> * </dl> */ public class ListViewSelectionModel<M extends ModelData> extends AbstractStoreSelectionModel<M> implements Listener<ListViewEvent<M>> { protected ListView<M> listView; protected ListStore<M> listStore; protected KeyNav<ComponentEvent> keyNav = new KeyNav<ComponentEvent>() { @Override public void onDown(ComponentEvent e) { onKeyDown(e); } @Override public void onKeyPress(ComponentEvent ce) { ListViewSelectionModel.this.onKeyPress(ce); } @Override public void onUp(ComponentEvent e) { onKeyUp(e); } }; /** * Binds the list view to the selection model. * * @param listView the list view */ @SuppressWarnings("unchecked") public void bindList(ListView<M> listView) { if (this.listView != null) { this.listView.removeListener(Events.Select, this); this.listView.removeListener(Events.RowUpdated, this); this.listView.removeListener(Events.Refresh, this); keyNav.bind(null); bind(null); } this.listView = listView; if (listView != null) { listView.addListener(Events.Select, this); listView.addListener(Events.Refresh, this); listView.addListener(Events.RowUpdated, this); keyNav.bind(listView); bind(listView.getStore()); this.listStore = (ListStore)listView.getStore(); } bind(listView != null ? listView.getStore() : null); } public void handleEvent(ListViewEvent<M> e) { EventType type = e.getType(); if (type == Events.Select) { onSelect(e); } else if (type == Events.RowUpdated) { onRowUpdated(e); } else if (type == Events.Refresh) { refresh(); } } @SuppressWarnings("unchecked") protected void handleMouseDown(ListViewEvent<M> e) { if (locked) return; M sel = listStore.getAt(e.getIndex()); if (isSelected(sel) && !e.isControlKey()) { return; } if (selectionMode == SelectionMode.SINGLE) { if (isSelected(sel) && e.isControlKey()) { deselect(sel); } else if (!isSelected(sel)) { select(sel, false); } } else { if (e.isShiftKey() && lastSelected != null) { int last = listStore.indexOf(lastSelected); int index = e.getIndex(); int a = (last > index) ? index : last; int b = (last < index) ? index : last; select(a, b, e.isControlKey()); lastSelected = listStore.getAt(last); listView.focusItem(index); // view.focusRow(index); } else if (isSelected(sel) && e.isControlKey()) { doDeselect(Arrays.asList(sel), false); } else { doSelect(Arrays.asList(sel), e.isControlKey(), false); listView.focusItem(e.getIndex()); // view.focusRow(e.rowIndex); } } } protected boolean hasNext() { return lastSelected != null && listStore.indexOf(lastSelected) < (listStore.getCount() - 1); } protected boolean hasPrevious() { return lastSelected != null && listStore.indexOf(lastSelected) > 0; } protected void onKeyDown(ComponentEvent e) { selectNext(e.isShiftKey()); e.preventDefault(); } protected void onKeyPress(ComponentEvent e) { } protected void onKeyUp(ComponentEvent e) { selectPrevious(e.isShiftKey()); e.preventDefault(); } protected void onRowUpdated(ListViewEvent<M> ge) { if (isSelected(ge.getModel())) { onSelectChange(ge.getModel(), true); } } protected void onSelect(ListViewEvent<M> e) { handleMouseDown(e); } @Override protected void onSelectChange(M model, boolean select) { listView.onSelectChange(model, select); } protected void selectNext(boolean keepexisting) { if (hasNext()) { int idx = listStore.indexOf(lastSelected) + 1; select(idx, keepexisting); listView.focusItem(idx); } } protected void selectPrevious(boolean keepexisting) { if (hasPrevious()) { int idx = listStore.indexOf(lastSelected) - 1; select(idx, keepexisting); listView.focusItem(idx); } } }