Android Question Avoiding Delay in GUI when running background services

Marcos Alves

Well-Known Member
Licensed User
Longtime User
I have one app that , when starting at the first time, needs to do many requests to a remote server to eventually upgrade some parameters and data in user interface (even in some resumes this requests are also interesting to avoid the needing of finishing the activity to refresh data)...
I noticed some freezing when opening the activity due these background services and think that it's something related to the time between httputils post requests and answers... the gui doesn't depends on the results of services. There is a local database and the background services will only update this database (and request a callsub, if the respective activity is not paused).
But the user experience is a little bit compromised with the "small freezing events"... Is this happening because the httpjob runs in the same thread? If yes, is there any workaround?
 

nobbi59

Active Member
Licensed User
Longtime User
Id recommend you to not do big tasks in Activty_Create / Resume. Show the UI and everything thats important for the UX and after all of this is done, you can do intensive tasks.

Maybe show a Loading Indicator or something that shows the user that your App is updating something.
 
Upvote 0

Marcos Alves

Well-Known Member
Licensed User
Longtime User
Id recommend you to not do big tasks in Activty_Create / Resume. Show the UI and everything thats important for the UX and after all of this is done, you can do intensive tasks.

Maybe show a Loading Indicator or something that shows the user that your App is updating something.

Thanks for answering! I really would like to have a way to call a real background task because sometimes we need to do some intensive data request from internet but only the result will be showed (or not) to the user, IF and WHEN finished with success. This is a typical job for an insulated thread. I saw that there is a library that starts a separated thread in app, but the post is very old (https://www.b4x.com/android/forum/threads/threading-library.6775/#content - from 2010!!!) . I think that using this library I could incur in some compatibility issues... what do you think?
 
Upvote 0

Didier9

Well-Known Member
Licensed User
Longtime User
Would it be a problem if the user starts using the app before all the data is updated?
You may actually need to have updated data before processing the user's query and if so, there would be no real benefit to letting the user start a query if you cannot process it before the data has been updated anyway?
 
Upvote 0

Marcos Alves

Well-Known Member
Licensed User
Longtime User
Would it be a problem if the user starts using the app before all the data is updated?
You may actually need to have updated data before processing the user's query and if so, there would be no real benefit to letting the user start a query if you cannot process it before the data has been updated anyway?

Imagine an hypothetical situation: an user has a sales list on screen, stored in a local database, downloaded in a time when he has internet connection... but now he opens again and could be interesting to query the remote server to know if there is some new. Of course that I could add an update action in menu and allow user decide if wants or no to click... but could be much more elegant if the app automatically checks the internet and updates the screen... then, the sequence is:

- Activity create: download the data from local database
- Activity resume (occurs also after create): start update service

Update service gets the data from internet and callsub in activity IF ispaused(activity) = false ... a beautiful and elegant solution that allows the app to show the data to the user instantaneously and either get the new data if there is connection with server. But the "small freeze" at the start of GUI really breaks the magic...

So, any solution?
 
Upvote 0

udg

Expert
Licensed User
Longtime User
Did you try to launch the data updating service from the Starter service?
 
Upvote 0

walterf25

Expert
Licensed User
Longtime User
I have one app that , when starting at the first time, needs to do many requests to a remote server to eventually upgrade some parameters and data in user interface (even in some resumes this requests are also interesting to avoid the needing of finishing the activity to refresh data)...
I noticed some freezing when opening the activity due these background services and think that it's something related to the time between httputils post requests and answers... the gui doesn't depends on the results of services. There is a local database and the background services will only update this database (and request a callsub, if the respective activity is not paused).
But the user experience is a little bit compromised with the "small freezing events"... Is this happening because the httpjob runs in the same thread? If yes, is there any workaround?
You can run your tasks inside a thread, that way your GUI won't hang, search in the forums for the Threading library, i use it a lot, or if you are using the OKHTTP library you can use the Wait For method, this allows you to wait for any events that needs to be raised from an asynchronous task while allowing your GUI to stay active.

Regards,
Walter
 
Upvote 0

Marcos Alves

Well-Known Member
Licensed User
Longtime User
I recommend you to avoid using the Threading library.

Http requests are sent in the background and will not slow down the UI.

JobDone itself runs on the main thread. What are you doing with the response?

Maybe it is better to add Sleep(5000) to start everything after the UI appeared.
Hi @Erel . I noticed that the freeze occurs when starting httputils2 service finishing a couple seconds after... could be something related to httputils2 loading service? The callback routine isn't generating gui freeze even because I added some strategic sleep(200) in these subs... see, when in "downlink" steps the app is free and it's running a callback (jobdone)...

upload_2018-1-26_8-25-16.png
 
Upvote 0

Marcos Alves

Well-Known Member
Licensed User
Longtime User
You can run your tasks inside a thread, that way your GUI won't hang, search in the forums for the Threading library, i use it a lot, or if you are using the OKHTTP library you can use the Wait For method, this allows you to wait for any events that needs to be raised from an asynchronous task while allowing your GUI to stay active.

Regards,
Walter
Hi @walterf25 . Thanks! My app could have a big advantage using threads because GUI doesn't depends on the data updated. I have a local database. Like whatsapp, if you have new messages, internet connection...good. If no, your old downloaded data will be still available. And app will do background queries, checking internet (eventually answering to a push event), to update as soon as possible. Of course that during these queries the gui interface must to remain free and fluid.
But I have a serious concern about threads library: this is from 2010! Maybe there is some stability alert... compatibility problem... in 2010 Android was version 4 or less... do you have something to tell me about this possible problem (compatibility and deprecated library?)...
 
Upvote 0

Marcos Alves

Well-Known Member
Licensed User
Longtime User
Did you try to launch the data updating service from the Starter service?
Hi,

updates can occur anytime in app life cycle and many services are doing specific update jobs. If I add startservice in flow the only change will be the creation of subs in this service calling other services. I see this implementation as only adding a new layer... I'm not sure that startservice will work as an insulation layer.
 
Upvote 0

udg

Expert
Licensed User
Longtime User
Probably a misunderstanding. I meant my suggestion as a way to start just the first update call, the one you currently do in Main.Resume.
An indipendent service where the update subs reside in, firstly called by Starter when your app is launched then by any other section of code where it is appropriate.
 
Upvote 0

Marcos Alves

Well-Known Member
Licensed User
Longtime User
Probably a misunderstanding. I meant my suggestion as a way to start just the first update call, the one you currently do in Main.Resume.
An indipendent service where the update subs reside in, firstly called by Starter when your app is launched then by any other section of code where it is appropriate.
Thanks @udg ... but unfortunately I need to do updates when app is open also... then, I have small freezes . If I had this need only in app start could be easy to add a "wait screen" or something like that...
 
Upvote 0

udg

Expert
Licensed User
Longtime User
Does your B4A release support Wait For? If yes, did you have a look at the examples in this thread?
 
Upvote 0

Marcos Alves

Well-Known Member
Licensed User
Longtime User
Does your B4A release support Wait For? If yes, did you have a look at the examples in this thread?
Hi,
I use the latest version... I already used sleep() in code, but not wait for yet.
I noticed that probably the delay is happening when the services are calling Job.initialize("jobdone",Me) (starting httputils2 service)... then, the freeze is almost "out of my control"... I will do some additional tests and post here the results.
 
  • Like
Reactions: udg
Upvote 0

KMatle

Expert
Licensed User
Longtime User
C'mon guys. I can't imagine that this is really a thing. I retrieve data from my servers a lot and of course the user needs to wait. It does not make sence to let the user use the UI before all data is loaded.

What do I mean with "all data"?

1. As an app is for USERS, all data means "all data the user can handle at one time"
2. This can be 10, 50 or maybe 100 records at one time
3. It's not about loading "all possible records" (which is a design problem/programming mistake to me). No use can handle 10.000 records.
4. Of course a user has to wait at some point until the data is available
5. There are other issues causing a "delay"

- bad internet connection
- bad hardware (1 GB RAM does not work)
- slow hardware
- other apps running on the device
- Google services having "fun" on the device
- bad server response (where you get the data from)

6. A mobile device is NOT as server handling 100.000 records (it's a device to display things to a user)
7. If you need to synchronize, let the user know

So if a "freeze" means 0.75 secs -> forget about it
 
Upvote 0

Marcos Alves

Well-Known Member
Licensed User
Longtime User
C'mon guys. I can't imagine that this is really a thing. I retrieve data from my servers a lot and of course the user needs to wait. It does not make sence to let the user use the UI before all data is loaded.

What do I mean with "all data"?

1. As an app is for USERS, all data means "all data the user can handle at one time"
2. This can be 10, 50 or maybe 100 records at one time
3. It's not about loading "all possible records" (which is a design problem/programming mistake to me). No use can handle 10.000 records.
4. Of course a user has to wait at some point until the data is available
5. There are other issues causing a "delay"

- bad internet connection
- bad hardware (1 GB RAM does not work)
- slow hardware
- other apps running on the device
- Google services having "fun" on the device
- bad server response (where you get the data from)

6. A mobile device is NOT as server handling 100.000 records (it's a device to display things to a user)
7. If you need to synchronize, let the user know

So if a "freeze" means 0.75 secs -> forget about it
:)Yes, a freeze means about 0,7 sec per call... but sometimes I joined 4 calls... solution: separated the service calls and, when needing to do together, I put a sleep(500) between... In emulator I still have some performance issues but in physical device is running almost fine. Then, I think that for now this is the best that we can do right?
 
Upvote 0

walterf25

Expert
Licensed User
Longtime User
Hi @walterf25 . Thanks! My app could have a big advantage using threads because GUI doesn't depends on the data updated. I have a local database. Like whatsapp, if you have new messages, internet connection...good. If no, your old downloaded data will be still available. And app will do background queries, checking internet (eventually answering to a push event), to update as soon as possible. Of course that during these queries the gui interface must to remain free and fluid.
But I have a serious concern about threads library: this is from 2010! Maybe there is some stability alert... compatibility problem... in 2010 Android was version 4 or less... do you have something to tell me about this possible problem (compatibility and deprecated library?)...
Hi Marcos, i have been using the thread library for a while and i haven't had any issues with it so far, the reason i started using it is because i made an app for a client that required creating a pdf workbook of more than 300 pages, as you can imagine this process takes a long time to complete depending on the amount of information each pdf page contains, if I left the application run without any type of background task handling then the user would just keep tapping on the screen now knowing whether the application crashed, then the OS would keep popping up the message saying wait or close application.

I know Erel doesn't recommend using this library and I understand his reasoning behind it, but i personally have not had any issues with it, the only downside of it is that you won't be able to run your up in debug mode.

Regards,
Walter
 
Upvote 0
Top