1

I have about 50 variables that get updated with an rate of about 1kHz by network, but their values change only every few seconds.

The values are for the UI (e.g. text, visibility and background color for buttons).

What is the most efficient way to update the UI?

I previously runned a task every 100ms on the UI thread that set all UI variables. The problem for me was the jitter of the other tasks every 100ms.

I'm looking for a solution to update the UI only when the variables changes.

Is there another way than implementing an own 'variable changed' listener?

Unihedron
  • 10,902
  • 13
  • 62
  • 72
L__M
  • 13
  • 3

5 Answers5

2

That is a common problem in computer science and has been already solved by the Gang of Four. Use the Observer/Observable pattern to recognize changes. Android has also some built in modules that implement MVC (Adapters and ListViews...).

Community
  • 1
  • 1
code monkey
  • 2,094
  • 3
  • 23
  • 26
0

I believe that implementing a "variable changed" listener is probably the most correct (and most efficient) way to implement this, but you could always compare the value currently displayed in the UI to the value updated on the network prior to changing the UI.

if(!label.getText().equals(networkVal)) {
    label.setText(networkVal);
}

I think something like that would work with the system that you described and reduce the jitter.

Samuel
  • 16,923
  • 6
  • 62
  • 75
  • thx I'll try to only run the .setText() in the UI-Thread. I keep the .getText().equals() in a normal thread. Do you think that idea is ok? btw: the UI doesn't need to be fast – L__M Nov 19 '14 at 20:33
  • What's the barrier of doing it all on the UI thread? Doing the check in a different thread than the set will cause race conditions . http://en.wikipedia.org/wiki/Race_condition – Samuel Nov 19 '14 at 21:25
0

You might want to consider using setter methods for your variables and updating your widgets inside these methods.

Ivan Wooll
  • 4,145
  • 3
  • 23
  • 34
0

I previously runned a task every 100ms on the UI thread that set all UI variables. The problem for me was the jitter of the other tasks every 100ms.

Then split the updating into ten parts and run every 10 ms one part.

From another answer:

you could always compare the value currently displayed in the UI to the value updated on the network prior to changing the UI.

I would not do it. This means to access the components often and getting their value may be expensive and complicated as they belong to the AWT-Thread. If your model contains an int, then getting the value back from the GUI may include parsing, which needlessly slows it down.

I keep the .getText().equals() in a normal thread. This would work if this very thread was the only one updating the value. Which is not true as you should do all the updates on the AWT Thread. This could lead to problems.

The simple solution is:

  • Maintain a copy of the variables.
  • From time to time compare a few variables against the copy (so that in total every 100 ms all variables get checked).
  • When there are any differences, update the GUI (using SwingUtilities.invokeLater) and update the copy (normally).

The Observer Pattern is the nicer but much more verbose solution.

maaartinus
  • 44,714
  • 32
  • 161
  • 320
-1

You can try to use either websocket or long polling.

What are Long-Polling, Websockets, Server-Sent Events (SSE) and Comet has a good discussion.

Community
  • 1
  • 1
Hy L
  • 522
  • 5
  • 11