Runnable Tutorial and Examples
Understanding Runnable in Android or Java.
As a developer, you may have come across the term "Runnable" in Android or Java programming. Simply put, a Runnable is an interface that represents a unit of work that can be executed asynchronously on a separate thread. In this article, we will explore the basics of Runnable and how it can be used in Android or Java programming.
Creating a Runnable
To create a new Runnable, you need to implement the Runnable interface and override the run() method. Here's an example:
public class MyRunnable implements Runnable {
@Override
public void run() {
// Do some work here
}
}
In this example, MyRunnable is a class that implements the Runnable interface and overrides the run() method. The run() method is where you put your code that needs to be executed asynchronously.
Running a Runnable
Once you have created a Runnable, you can execute it by passing it to a new thread and calling the start() method. Here's an example:
MyRunnable myRunnable = new MyRunnable();
Thread thread = new Thread(myRunnable);
thread.start();
In this example, we create a new instance of MyRunnable and pass it to a new instance of Thread. We then call the start() method on the thread to start the execution of the Runnable.
Using Runnable in Android
In Android, Runnable is often used to perform tasks that take a long time to complete, such as network requests or database queries. Here's an example of how you might use a Runnable to download an image from the internet:
public class ImageDownloader implements Runnable {
private String imageUrl;
private ImageView imageView;
public ImageDownloader(String imageUrl, ImageView imageView) {
this.imageUrl = imageUrl;
this.imageView = imageView;
}
@Override
public void run() {
try {
URL url = new URL(imageUrl);
InputStream inputStream = url.openConnection().getInputStream();
final Bitmap bitmap = BitmapFactory.decodeStream(inputStream);
imageView.post(new Runnable() {
@Override
public void run() {
imageView.setImageBitmap(bitmap);
}
});
} catch (IOException e) {
e.printStackTrace();
}
}
}
In this example, ImageDownloader is a class that implements Runnable and takes an image URL and an ImageView as arguments. The run() method downloads the image from the URL and sets it as the image for the ImageView.
To use this Runnable in your Android app, you would create a new instance of ImageDownloader and pass it to a new instance of Thread, like this:
ImageDownloader imageDownloader = new ImageDownloader("https://example.com/image.jpg", imageView);
Thread thread = new Thread(imageDownloader);
thread.start();
More about Runnable?
It's an interface and is defined in the java.lang package and has an abstract method called run() that we have to implement.
package java.lang;
public interface Runnable{
public abstract void run();
}
Usage
The Runnable interface is used extensively to execute code in Threads. The Runnable interface has one abstract method called run():
public abstract void run ()
Normally you implement that method whenever your class implements Runnable interface. The method will then get called to start executing the active part of the class' code.
Let's say we want to use Runnable as our threading mechanism. Well first implement the interface. Then provide the implementation for the run() method:
public class MyRunnable implements Runnable {
public void run(){
Log.d("Generic","Running in the Thread " +
Thread.currentThread().getId());
}
}
With that, our Runnable subclass can now be passed to Thread and is executed independently in the concurrent line of execution:
Thread thread = new Thread(new MyRunnable());
thread.start();
In the following code, we basically created the Runnable subclass so that it implements the run() method and can be passed and executed by a thread:
Runnable Interface Indirect Subclasses
Runnable has alot of them so we list only afew commonly used:
| No. | Class | Description |
|---|---|---|
| 1. | Thread | A concurrent unit of execution.This class implements Runnable interface.The Thread class makes use of the Runnable's abstract run() method by calling it's(the Thread's) concrete run() method. That run() method then calls the Runnable's abstract run() method internally. |
| 2. | TimerTask | An abstract class used to describe a task that should run at a specified time.Maybe once,Maybe recurringly.TimerTask implements Runnable interface.The tasks done by the TimerTask do get specified in the run() method. |
| 3. | FutureTask<> | A class that represents a ceancellable asynchronous computation.This class implements the RunnableFuture interface, which implements the Runnable interface. |
Let's now see some examples:
Android Runnable Example Step by Step
This is an android example. Android obviously uses Java and Runnable interface has existed since API level 1.
We can use a Runnable with a Service as follows:
public class MyService extends Service implements Runnable{}
This will then force us implement the abstract run() method inside that class:
@Override
public void run() {
}
And given this is a service we will also have to override another abstract method for Service called onBind()
@Override
public IBinder onBind(Intent intent) {
return null;
}
Service is an Android component which has lifecycle callbacks. One of them is the onCreate(), a method that get's raised everytime a service is created.
So for us everytime that happens we want to create a thread and start it:
@Override
public void onCreate() {
super.onCreate();
Thread myThead=new Thread(this);
myThead.start();
}
Then say I want to log some messages every 1 second, add the following code inside the run() method:
while (true)
{
try{
Log.i(MY_TAG,"Distance in Light Years : "+spaceship_distance);
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
Then as instance variables, add the following above your onCreate() method:
public static String MY_TAG="MY_SERVICE";
private int spaceship_distance=0;
Well that's an example of using Runnable with Android. If you are interested in having the service actually run: then do the following:
Register the service in the Manifest:
Make sure you specify your Service name instead of
MyService.Start the service in the MainActivity:
Intent i=new Intent(this,MyService.class);
startService(i);
And that's it, an android Runnable interface example with services.
Note that sometimes people use Runnable in this way:
@Override
public void onCreate() {
super.onCreate();
new Thread(new Runnable() {
@Override
public void run() {
ArrayList<Song> songs = scanSongs(ScanMusicService.this);
LogUtils.d(songs);
ToastUtils.showLongToast(songs.toString());
}
}).start();
}
Runnable Quick Samples
(a). How to Perform a HTTP GET with HttpURLConnection and Runnable
HttpURLConnection is our networking class and allows us to perform our HTTP GET request.
On the other hand Runnable is our interface that will allow us perform our HTTP GET request in the background thread.
So you start by implementing the Runnable interface, forcing you to override the run() method.
It is inside that run() method where we perform our HTTP GET:
public class UrlRequest implements Runnable {
......
@Override
public void run() {
try {
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
InputStream stream = connection.getInputStream();
int responseCode = connection.getResponseCode();
ByteArrayOutputStream responseBody = new ByteArrayOutputStream();
byte buffer[] = new byte[1024];
int bytesRead = 0;
while ((bytesRead = stream.read(buffer)) > 0) {
responseBody.write(buffer, 0, bytesRead);
}
listener.onReceivedBody(responseCode, responseBody.toByteArray());
}
catch (Exception e) {
listener.onError(e);
}
}
}
Here's the full class:
import android.support.annotation.NonNull;
import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
public class UrlRequest implements Runnable {
public interface Listener {
void onReceivedBody(int responseCode, byte body[]);
void onError(Exception e);
}
public interface RequestFactory {
@NonNull
UrlRequest makeRequest(URL url, Listener listener);
}
private static RequestFactory factory = new RequestFactory() {
@NonNull
@Override
public UrlRequest makeRequest(URL url, Listener listener) {
return new UrlRequest(url, listener);
}
};
private URL url;
private Listener listener;
public static UrlRequest makeRequest(URL url, Listener listener) {
return factory.makeRequest(url, listener);
}
public static void setFactory(RequestFactory newFactory) {
factory = newFactory;
}
public UrlRequest(URL url, Listener listener) {
this.url = url;
this.listener = listener;
}
@Override
public void run() {
try {
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
InputStream stream = connection.getInputStream();
int responseCode = connection.getResponseCode();
ByteArrayOutputStream responseBody = new ByteArrayOutputStream();
byte buffer[] = new byte[1024];
int bytesRead = 0;
while ((bytesRead = stream.read(buffer)) > 0) {
responseBody.write(buffer, 0, bytesRead);
}
listener.onReceivedBody(responseCode, responseBody.toByteArray());
}
catch (Exception e) {
listener.onError(e);
}
}
}
Conclusion
In conclusion, Runnable is a powerful tool in Android or Java programming that allows you to execute tasks asynchronously on a separate thread. By implementing the Runnable interface and overriding the run() method, you can create custom tasks that can be executed in the background without blocking the main thread. We hope this article has given you a better understanding of how Runnable works and how it can be used in your Android or Java projects.