3

I have an app that uses a JFace TreeViewer. I have it hooked up to a ContentProvider. Mostly, it works great. However, for some actions, like adding a Node in the middle of a list of Nodes or changing a value which should change the label for a Node, the refresh() call doesn't work. I've tried including the parent Node, say "true" for label update. Nothing works all the time.

I have seen that if I leave a collapsible Node closed and add and then expand, the added Node is shown. But if it's already expanded, no change is shown. If I save my tree info to disk and look, the change is made. It's just the TreeViewer refresh that is not working.

I looked at the inputChanged method in my ContentProvider, but it is only called at the beginning and end of my app execution.

Can anyone help? I've read all the web pages that even hint at an answer and nothing has worked.

flavio.donze
  • 7,432
  • 9
  • 58
  • 91
Mark
  • 1,988
  • 2
  • 24
  • 42
  • 1
    TreeViewer is not bug free, so it is possible that you are hitting a bug. If you provide a short code snippet that I can use to reproduce the problem, I can see what is the problem. – Danail Nachev Oct 06 '11 at 08:47

5 Answers5

2

The inputChanged() if the contentprovider shouldn't be called during refresh() - it is only called when a setInput() call is made to the tree viewer.

In worst case you could call setInput() with the original input to make your elements refreshed, but it can be too slow for your application.

Basically, when you add a new Node in the middle of the group, you have to refresh the parent node (the node who returns the added element using the getChildren() call), or one of its parents. Basically calling refresh() without any parameters might work for this reason.

So for testing, I suggest that you should call refresh() without any parameters, try, whether it works or not, and if it works, then try to figure out the most specific node that works with your application.

Zoltán Ujhelyi
  • 13,788
  • 2
  • 32
  • 37
  • Thanks for the reply. I had tried refresh() with all combinations of parameters (none, parent node, boolean) and it doesn't work. I did try setInput() call again as you suggest, but unfortunately it didn't work either. – Mark Oct 05 '11 at 15:00
  • Well, if setInput() does not work, then either there is a bug in your providers or in the TreeViewer. setInput() should reload the entire model, and redraw the contents. But sadly I don't have any idea - I second Danil Nachev's comment about trying to create a a code snippet for reproduction. – Zoltán Ujhelyi Oct 06 '11 at 09:05
1

Maybe this is obvious to you, but are you calling the refresh from the UI thread? Specifically try the following:

Display.getCurrent().asyncExec(new Runnable() {
    @Override
    public void run() {
      // TODO Call refresh() here
    }
});

There is also a syncExec() method.

Hope this helps!

jastram
  • 733
  • 7
  • 19
0

For me the add(), update() or remove() functions worked pretty decent, of course it is annoying to do so manualy... but if you call them from your model on a change it should just work fine.

nyx00
  • 106
  • 3
  • 12
0

Did you apply a label decorator to your TreeViewer?

I just edited an entry in my TreeViewer without the LabelDecorator I applied before and update(selectedItem, null) actually applied the update (it did nothing before).

Perhaps it's a jface bug?

[edit] seems you have to use updateLabel() from your DecoratingLabelProvider object.

0

Unfortunately, nothing I could find resolved this. I ended up closing the file and reopening it to force a "refresh/update". Thanks all for the advice.

Mark
  • 1,988
  • 2
  • 24
  • 42