cycled update of label

Hello all,

I have a question regarding cycled update of a label (e.g. “28:46 minutes remaining”): What is the best way to handle this? Start a thread and push the update of the label?

Thanks for your help!

Best Regards,
Thomas

Updating the browser every second seems like a lot of unneccesary communicaiton between server and client, as the length of a second is quite static. How about you do a simple javascript component, something like http://jsfiddle.net/mrwilk/qVuHW/, and wrap it into a Vaadin component? Then you give the initial time to it from the server and it handles the counting down from it on the client.

Thanks for the answer! Let’s assume I want to update on minute base? Is there a other solution without java script?

Regards,
Thomas

There is two steps in the problem: 1) Do something with an x interval and 2) Update the ui when step 1 has happened

With as high as a minute, I would look into using Java Timer or spawn a thread and thread.sleep for the duration. When you go into per-hour, day, week territory and do something that is not bound to one UI session, you could go enterpisey and use for example Quartz. But here I feel that the
Timer
is the best option to you. Spawn a timer and within it update the label.

By only updating the label, you won’t see a change in the browser, because the browser isn’t actively watching for changes that happen on the server. For this you have to enable push and use it. You have to wrap the ui updating into a ui.access(); call and finally call ui.push() to update it, to avoid data loss and deadlocks.
You can read more about it in the documentation.

I’ll copy paste to code snippets together directly in the forum so the validity of the code below is probably bad. It also as a runnable within a runnable which sounds unneccesary, but can’t figure out a leaner solution without an IDE. Remember to turn on push or this will not do anything!

Label label = new Label("Updated 0 times");
addComponent(label);
UI ui = getUI();
int i = 0;
Timer t = new Timer();
t.schedule(new TimerTask() {
    @Override
    public void run() {
        ui.access(new Runnable() {
            @Override
            public void run() {
                i++;
                label.setValue("Updated " + i + " times");
                ui.push();
            }
        });
    }
}, 0, 1000*60); // each minute

Wow, perfect for the fast answer! I will try this. Thanks! :slight_smile:

Hello,

with the Timer and the push function it is a good option to handle this requirement. But how can I stop the timer? I do not want to handle for have multiple threads running in the background (e.g. by closing the browser)?

Regards,
Thomas

Depends a bit on the case but you can do cleanup for example by overriding
UI.detach()
or with a
SessionDestroyListener
. Both will take some minutes to notice that the user has indeed left the app as it can’t be sure directly if it is just a bad internet connection or if the user has actually closed the browser. It has a heartbeat system and it does the cleanup after a few missed heartbeats.

Okay, i try it! Thanks :slight_smile: