Search code examples
javaeclipseeclipse-pluginjfacetableviewer

How to preserve selections in a JFace TableViewer when refreshing?


In my project I have a TableViewer which has a model, a content provider and a label provider.

Once I update my model I call tableviewer.refresh(true) and according to the documentation here:

TableViewer Methods

I'm expecting my selections to be preserved.

Unfortunately this doesn't happen. Does anybody know a solution for that?

Is it something that I miss in here or is it a bug?

EDIT: This is my model class(counter is for testing purposes to be sure that I have the same list returned after the first refresh):

public class ItemWorkgroup {


    List<Item> currentItems = new ArrayList<Item>();
    static int counter = 0;


    public ItemWorkgroup()
    {

    }

    public void add(Item item)
    {
        currentItems.add(item);
    }

    public Object[] getItems()
    {
        return currentItems.toArray();
    }

    public void addList(List<Item> newItemsList)
    {   

        System.out.println("Current items first 1: "+currentItems);

        if(counter == 0)
        {
            currentItems = newItemsList;
            counter++;
        }
        System.out.println("Current items first 2: "+currentItems);


    }

    public List<Item> getItemList()
    {   
        return currentItems;
    }

}

This is the content provider class:

public class ContentProvider implements IStructuredContentProvider{


private Mediator mediator;
private ItemWorkgroup model;

public ContentProvider(Mediator mediator, ItemWorkgroup model) {
    // TODO Auto-generated constructor stub
    this.mediator = mediator;
    this.model = model;
}

@Override
public void dispose() {
    // TODO Auto-generated method stub

}

@Override
public void inputChanged(Viewer viewer, Object oldInput, Object newInput) {
    // TODO Auto-generated method stub
    System.out.println("Input changed");
}

@Override
public Object[] getElements(Object inputElement) {
    // TODO Auto-generated method stub
    System.out.println("Getting elements");

    if(inputElement instanceof ItemWorkgroup)
    {           
        return ((ItemWorkgroup) inputElement).getItems();
    }
    else
        return new Object[0];   

}


public ItemWorkgroup getItems()
{

        //Items is a list of items that I'm getting from somewhere

        model.addList(items);


    return model;
}

Solution

  • The viewer tries to maintain the selection but if your content provider returns different objects for the elements that were selected after the refresh then the tree viewer will not be able to restore the selection.

    Your content provider must return the same object for things which have not changed for the selection to be preserved. (Or you can return an object where the equals and hashCode methods make it appear the same).