Accessing a Bluetooth "ConnectedThread" from various activities - android

I have created a BluetoothManager much like the one in this example. This object is instantiated in a connection activity, reached from the main acitivty by clicking on a "Connect" button, which provides a ListView of selectable devices. Works great so far.
I am now connected and have a BluetoothManager.ConnectedThread running and the streams set up. I would now like to be able to send Bluetooth data from/to various other activities when they are running. For example, I will want to chart realtime values when the charting activity is running.
As far as I can tell, the pushing of the data out from the ConnectedThread will occur via a Handler, which is a new topic for me. What I am unclear on his how other activities might access the ConnectedThread's write() function.

First of all, even though a singleton could be a solution, android Service's are there for this purpose, since these are elements that can keep running when your UI is out. So my suggestion would be to create a sticky service an then you have two options:
Handle data using a handler between the activity and the Service. Maybe if you are not too familiar with the Handler api this will take some time to you. In this example of the official documentation you can also check how to use the handler.
Create a bound service, to which you can bind from the activities and send some data when required. Here you have the official information about bound services.
You can have a look to this tutorial to get more information about handlers.

Related

how to send continous streams from a separate thread to activity

I have started a thread which connected to bluetooth device and streams data. I actually started this thread from a service(Thread not started from activity). So know I need to communicate to activity to show the list of input streams. I am not sure if event bus can provide a such a high frequently changing data. Can some one give me a better existing examples of how to use display the streams.
Please don't ask me for the source code.
I believe Event bus can be a good solution, also check bound services:
https://developer.android.com/guide/components/bound-services.html
I advise you to look into LiveData from the Android architecture components. You can observe the result from the activity, and it will "unsubscribe" for you when needed (onStop()). You can read about the advantages on the link I provided.
You could extend a LiveData and implement the logic inside it (like this example), or just use it to dispatch the updates, then observe it on the Activity. The postValue() method will ensure that it gets dispatched on the MainThread.

Activity, Service and what kind of communication between?

I'm trying to develop an Android application consists of an Activity and a Service. The Activity launch a process on the Service of indefinite duration, which will be closed from Activity. Do not use then the subclass IntentService, but directly Service. Controlled by onStartCommand and OnDestroy.
I obviously need to pass information from the Activity to the Service: the status of the Service and some strings.
I tried to use LocalBrodcastManager, but when turning the devices or when the activity goes in state onPause, the message will lost. I tried to follow several examples, but with little success. This in particular I could not complete it because of some missing information, evidently deemed obvious, but which are not obvious to me: https://developer.android.com/training/run-background-service/report-status.html
I then tried to use Messenger via IBinder ( Example: Communication between Activity and Service using Messaging ), But the program seems a bit complex and I can not able to fit my needs.
What I need is to launch the service from my activity (possibly make binding automatically?, in case of Messenger use), the Service should signal the Activity to be active, then Service records some points via GPS LocationListener, writes it to a file and should point out, again the Activity, the data that is recording, the file size, etc.
What do you recommend to use to pass this information and can you provide to me some example?
I am actually in the midst of a tutorial explaining and comparing many different approaches to IPC in Android but since it's not ready and because you need an easy fix i'll recommend https://github.com/greenrobot/EventBus.
Also feel free to look in an old but still relevant example me and my friends made a while back here: https://github.com/RanNachmany/AndconLab
Goodluck.

what is the best/preferred approach to implement multi-threading in android app

I'm a beginner in android development and I'm trying to implement an android udp client, which connects to a java server and sends/receives some packets from it.In this process it collects some data (like round-trip delay etc), which is used to measure the QoS of that particular network. I have tried implementing the connection and sending/receiving data using Java Threads, but the application crashes, and hangs if i try to use more than 2 threads. So I'm looking for alternatives. While going through this site as well as some other links I found that in android multiple threads can be implemented using AsyncTask, Handler etc. Also I found that the Service class also helps to run a background service in an app. Please suggest which approach among these would be the best to achieve my purpose.
Thanks in advance.
You can use AasyncTask to do this and as you mentioned service may be useful too, where u can let your application do whatever it wants in background , if user needs to use application by its interface then AsyncTask must be used to avoid Crashing
There is not one right answer that can be applied as a broad stroke to how to do Android multi-threading. There are a few different ways to approach it based on what your specific needs are.
Any long running, blocking call, in Android will result in the application crashing.
The most common solution is to use an AsyncTask though. For example, when I want to make a call out to a web API endpoint for some XML data within an Activity I would in this case use an AsyncTask and kick off the calls from within doInBackground.
This is not an appropriate solution though if the wait time is longer, or possibly an unknown wait time. Or in a situation where there will always be waiting such as a message queuing service. In this type of situation it may be best to write a separate app based on extending the Service class. Then you can send/receive notifications to/from the service from your primary application in a similar manner to how you would communicate with a web service.

Using a Handler in multiple Activities

I am developing an application which has around 8 Activities, and a class which is used to connect/receive data to/from an embedded Bluetooth chip. When I started, a Bluetooth object was initialized in my initial Activity, where there was a Handler which received messages from the Bluetooth object.
After poking around on the internet for a while, it seems like the best idea for me is to turn my class into an Application subclass. However, doing this removes the need for me to initialize an object in the MainMenu, which removes my ability to pass it the Handler used.
Does anyone know of a way to eliminate the need for a Handler, so that every time the Bluetooth Application changes it state or receives data, the current Activity can access it?
My main problem with this approach is that the Activity doesn't know when the Bluetooth Application will be sending it messages, the Application waits and listens, and then notifies the Activity when it happens.
OR
Is it bad practice for me to write the Handler into the MainMenu, have it handle messages for ALL the different activities, and then pass the Handler from Activity to Activity?
I'm going to assume that you're trying to achieve the following as it's a little unclear from your question your ultimate aim (sorry!):
Your application has several activities but only one Activity receives the data from the bluetooth device.
The other activities in in your application require the data from the bluetooth device but are not receiving it directly from the bluetooth device. Currently you're providing the data via the one activity mentioned above.
You want to NOT use a Handler to achieve this.
If my above assumptions are correct then you are going along the correct lines but you probably do not want to use a Handler.
You are quite correct in having one Activity handle all the interactions with the Bluetooth device. It simplifies things and provides a much better, cleaner way of handling the Bluetooth device. However you need to get the data from this one Activity to all the others and to achieve this you would probably want to use Broadcasts, BroadcastReceivers and Intents. See here for an overview.
However if you can you might want to take a look at using LocalBroadcastManager as this keeps any broadcasts within your own app's space. Broadcasts are global and should be avoided if you do not need to pass the data outside of your own app due to security implications.
Finally, have you considered using Fragments for your other Activities? Another disadvantage with Broadcasts is there is extra overhead associated with them. If you're keeping data within your app then you can create an interface to be implemented by each of your Fragments and your main activity just calls that interface on the Fragment that is currently selected.
You can use BroadcastReceiver class to send broadcast messages to your activities. see here http://developer.android.com/reference/android/content/BroadcastReceiver.html
When you get the data you need into the application class, you can send it to the activity you want.. just make sure that the activity has registered to receive that broadcast message..

Am I using and Android in-memory way to share data that's simply not the way the Android activity model works?

I've asked various questions related to one goal: how to develop an Android app that plots bluetooth data forever in real-time. I now have a new question from a different angle. To be fair to new readers I will cover some of the same background, but basically the question is in the title.
I found some open source code Bluetooth that apparently creates a background thread which updates the screen with new data it receives over a bluetooth connection. Then when I launch my Plot activity I can see the bluetooth background thread continue to write bluetooth data to Logcat. So I know for a fact the bluetooth background thread is still running when I launch my Plot activity.
Again, my goal is to plot the bluetooth data that is continually provided by the bluetooth background thread. I have succeeded as follows: since this bluetooth background thread seems to run continually and just won't die, I decided to use its update() method to call my static Plot.plotData() method to plot the data. And this works. It will will run endlessly with out a problem - receiving bluetooth data and plotting it via periodic calls from the bluetooth background method update() to my static Plot.plotData() method.
Although I have received some negative feedback regarding my solution, I have found sharing data across Activities where Edward Falk says sharing static data is OK. Here Edward Falk asks: "Are the activities all in the same application? [yes] Same task? [not sure] It seems to me that you could just store the data in a static variable accessible by all of the activities." Well I tried static data and it worked, but I switched to a static method Plot.plotData() which seems to work better for me.
The latest feedback I have received from one person #emmby that says my static Plot.plotData() goes against the following: "It sounds like you're looking for an in-memory way to share data, and that's simply not the way the Android activity model works." But what am I else to do? I thought that an Android phone has a limited amount of RAM for running Activities (one at a time), threads, handlers, Services, AnycTasks, etc. And an SD card for persisting data.
#emmby seem to say that in order to share data from a bluetooth background thread to my Plot activity (Plot.plotData()) that I must use the SD card. This doesn't sound right. After all I have it working using my static method Plot.plotData().
Frankly I don't see anything wrong with my solution primary because those who criticize it do not follow up with a definitive alternative.
If you find my solution deficient please speak up and provide a definitive solution. Otherwise I will take Edward Faulk's solution as the best one.
If I understood you correctly, your thread is running at the background even when none of the activities display data obtained by that thread. For example, let's consider scenario:
You started your bluetooth thread.
Your activity A started and now read data from that thread.
Your activity A is backgrounded (for example user navigates away via "Recent" tasks).
Your activity is idle but bluetooth thread still consumes cpu and power.
If you don't use your bluetooth data you shouldn't run the thread. You can introduce some kind of counter that tracks number of clients that use your thread's data. And if counter drops to zero - thread stops/pauses.
But Android has built-in solution for such cases. You can introduce service which will be bound by different activities and will have DataSource interface with getNextData function. See Bounded Services for more details.
When there are no clients bound to service Android will stop the service. This way you completely decouple Activities from thread. Your bluetooth thread is now managed by Service. And Service is now managed by Android.
In your case Local Service should be enough to share data between your thread and activities.

Categories

Resources