I'm currently recoding a TableViewer to work fully virtual. So far I'm pretty content with the results, but I still have a problem, that all visible elements in the table are refreshed on a fixed timer. The model changes continously though. This means, that if I click on an entry before a periodic update happens, the table loads in the actual value for that position, but leaves all other elements untouched. Since this is how the LazyContentProvider works that is set for the TableViewer this is not much of a problem. Since my TableViewer is a Live-Viewer of incoming events, with the newest entry shifting all other items one down, I'd like to refresh all visible elements on adding a new event.
I've tried to use TableViewer.refresh() on adding a new item, but that does not seem to do anything.
Since the full code is pretty complex, and part of a bigger piece of code I'll provide a basic representation of the code:
public class MyClass{
public TableViewer liveViewer;
public List<String> myItems=new ArrayList<>();
void init(){
liveViewer = new TableViewer(liveComp, SWT.BORDER | SWT.FULL_SELECTION | SWT.VIRTUAL);
liveViewer.setContentProvider(new LiveViewerContentProvider(liveViewer));
liveViewer.setLabelProvider(someLabelProvider);
liveViewer.setUseHashlookup(true);
ClassThatProvidesItems.addListener(new ItemAddedListener(){
@Override
void itemAdded(String item){
myItems.add(0,item);
}
}
}
}
public class LiveViewerContentProvider implements ILazyContentProvider{
private TableViewer viewer;
private List<String> input;
public LiveViewerContentProvider(TableViewer viewer) {
this.viewer = viewer;
}
@Override
public void dispose() {
}
@Override
public void inputChanged(Viewer viewer, Object oldInput, Object newInput) {
this.input = (List<String>) newInput;
}
@Override
public void updateElement(int index) {
viewer.replace(input.get(index), index);
}
}
I'm aware, that an ArrayList is probably not the best choice, for always adding an element at the head, but please ignore it for now. I've tried to perform a liveViewer.refresh(); at the end of the listener callback, but it didn't seem to refresh my elements. What could I do to force a refresh for all visible items on adding a new one?
Thanks in advance.
I've just noticed, that my solution was almost working. The problem was, that the whole code was somewhere within a weird try-catch-block that just silently swallowed Exceptions, and didn't give me the invalid-Thread-access exception that I should have gotten for not performing the liveViewer.refresh within the Display-Thread. Wrapping the line like this fixed the issue:
Display.getDefault().asyncExec(new Runnable() {
@Override
public void run() {
liveViewer.refresh();
}
});