In this quickstart, we will introduce you to Daily's Client SDK for Android by walking through the creation of a simple video call application. By the end of this walkthrough, you'll have a starting point for writing Daily-powered video apps for Android with Kotlin.
This walkthrough will implement the following features:
- Creating and joining a public Daily room
- Asking for required application permissions
- Displaying videos from local and remote room participants
- Managing local microphone and camera input
- Leaving the call
You can find the full codebase of this Android app on GitHub.
Before you get started, make sure you have a functioning Android development environment including Android Studio. You will also need a free Daily account.
If you plan to test your app on a hardware device, make sure you have debugging enabled on the device.
If you plan to test your app on an emulator, make sure you have a virtual device created. Note that by default, the emulator will use an emulated camera.
Create a Daily room
Begin by navigating to Daily's developer dashboard and creating a new Daily room.
Give your room a name and click the "Create room" button. All other options can be left at their defaults.
Make note of your Daily room URL. We'll be using it in the code shortly.
Create a new Android project
Next, open Android Studio. From the Welcome screen, create a new project using the "Empty Views Activity" template.
Give your project a name and make sure the project language is set to Kotlin. Next, click the "Finish" button to have Android Studio set up your new project.
Note that if this is your first Kotlin project setup, it can take a few minutes for Android Studio to download relevant dependencies and initialize the project for the first time.
Add a dependency on Daily's Client SDK for Android
With your new project created, you can add the Daily's Android SDK as a dependency. Android Studio uses Gradle as its default build tool and dependency manager. Open the project's Gradle build script in the app directory:
Once open, add
'co.daily:client:0.8.0' to the dependencies object:
0.8.0at the time of this publication. When developing your production application, we recommend referencing the latest stable version.
Save the Gradle file and then sync the changes by using the
Sync Project with Gradle Files command in the Android Studio File menu.
Import namespaces and classes
After adding a dependency on Daily's Android SDK, we can import relevant classes. Open
app/java/com.example.[YOUR_APP_NAME]/MainActivity.kt and add the following
Setting up the Main Activity
The next step is modifying the
MainActivity class to set up the basic structure of our application.
Start by adding the
TAG member variable and two functions:
Then, add a call to
checkPermissions() from the
Build the application to verify that there are not errors or warnings.
Configure application permissions
The application will need a number of user permissions in order to access the internet, use the device camera, and record and play audio. To request these permissions, we have to declare what we need as part of our app manifest.
manifests/AndroidManifest.xml. Then, add the following
uses-feature elements inside the
<manifest xmlns:android="http://schemas.android.com/apk/res/android"xmlns:tools="http://schemas.android.com/tools"><uses-feature android:name="android.hardware.camera" android:required="false" /><uses-permission android:name="android.permission.INTERNET" /><uses-permission android:name="android.permission.CAMERA" /><uses-permission android:name="android.permission.RECORD_AUDIO" /><uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" /><!-- ... --></manifest>
Modifying the app manifest tells Android which permissions the app intends to use. However, we still need to request these permissions from the user. To do so, we'll add some additional code to
MainActivity.kt, which uses Android's built-in tools for creating runtime permission requests.
First, create a member variable named
requestPermissionLauncher and use it to register an activity using the
RequestMultiplePermissions takes an array of permissions the application would like to request.
In the activity callback, we check to see if additional permissions are needed. If so, we run
checkPermissions(). If not, the application can call
initializeCallClient() to begin setting up the video call.
Next, implement the
checkPermissions() method you defined within the
MainActivity class as follows:
checkPermissions() method above gets the list of permissions the application needs from the app manifest and checks whether they have already been granted.
If all of permissions have been granted, the application begins initializing the Daily
CallClient object by calling the
If the application requires additional permissions from the user, it launches the built-in request flow.
Define the user interface
After implementing permission handling, we can define the user interface for our application. The user interface will include the following:
- Displaying participants' video
- Presenting call controls for toggling the camera/microphone and leaving the meeting
To implement the above, we'll create two main UI elements:
- A main UI that contains call controls and a participant list
- A wrapper around the Daily
VideoViewthat holds each participant's video
/res/layout/activity_main.xml layout file and switch to Code view:
Replace the default UI XML with the following:
<?xml version="1.0" encoding="utf-8"?><androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"xmlns:app="http://schemas.android.com/apk/res-auto"android:layout_width="match_parent"android:layout_height="match_parent"><ToggleButtonandroid:id="@+id/toggleCamera"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_marginTop="16dp"android:checked="true"android:textOff="Cam Off"android:textOn="Cam On"app:layout_constraintEnd_toStartOf="@+id/toggleMicrophone"app:layout_constraintStart_toStartOf="parent"app:layout_constraintTop_toTopOf="parent" /><ToggleButtonandroid:id="@+id/toggleMicrophone"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_marginTop="16dp"android:checked="false"android:textOff="Muted"android:textOn="Unmuted"app:layout_constraintEnd_toStartOf="@+id/leave"app:layout_constraintStart_toEndOf="@+id/toggleCamera"app:layout_constraintTop_toTopOf="parent" /><Buttonandroid:id="@+id/leave"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_marginTop="16dp"android:text="Leave Call"app:layout_constraintEnd_toEndOf="parent"app:layout_constraintStart_toEndOf="@+id/toggleMicrophone"app:layout_constraintTop_toTopOf="parent" /><LinearLayoutandroid:id="@+id/videoLinearLayout"android:layout_width="match_parent"android:layout_height="0dp"android:layout_marginStart="8dp"android:layout_marginTop="8dp"android:layout_marginEnd="8dp"android:layout_marginBottom="8dp"android:orientation="vertical"android:background="@color/black"app:layout_constraintBottom_toBottomOf="parent"app:layout_constraintTop_toBottomOf="@+id/toggleCamera"/></androidx.constraintlayout.widget.ConstraintLayout>
The XML above creates two
ToggleButtons for controlling the camera and microphone, a single
Button to leave the call, and a
LinearLayout to contain participant videos.
Next, we need a wrapper for
/res/layout, create a new Android Resource file named
participant_view.xml. Replace the default UI XML with the following:
<?xml version="1.0" encoding="utf-8"?><androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="300dp"android:layout_margin="20dp"><co.daily.view.VideoViewandroid:id="@+id/participant_video"android:layout_width="match_parent"android:layout_height="match_parent"/></androidx.constraintlayout.widget.ConstraintLayout>
Build and run the application by clicking the "Play" button in the debug toolbar at the top of the Android Studio IDE window:
The application should prompt you for permissions and, once granted, display the basic interface you created.
You won't see any video just yet because we haven't set up the call client or joined a Daily room. We'll do that next.
Create the call client
Now that the basics of the application are in place, we can implement functionality to join a call and display participant videos.
CallClient is the main interface into your Daily video call. It should be instantiated and retained for at least the duration of the video call session.
MainActivity.kt and locate the
initializeCallClient() method. Within it, create an instance of
CallClient followed by a map of
Next, set up relevant event listeners within
initializeCallClient(). Start by retrieving the participant layout view within this method:
Then, add the relevant
CallClient event listeners. These events are raised in response to actions like meeting participants joining, leaving, or being updated:
For each participant who joins, we create an instance of the
VideoView UI element. The
VideoView instance has its track set to the joining participant's available video track.
If a participant is updated (for example, by turning off their camera), we update that participant's
Join a call
Now that our application has a
CallClient instance and can react to meeting participant events, we're ready to join a room. To do this, call the
join() function and pass in the URL of the Daily room you created at the start of this tutorial.
"[YOUR_DAILY_ROOM_URL]" with th URL of your room. You can find the room URL in your Daily developer dashboard.
Go ahead and run the application again. Once you have successully joined the meeting, if you are running on actual hardware, you should see your Android device's camera video being shown as a participant in the application. If you are using the Android emulator, you should see an emulated camera.
To test the app with a remote participant, open the room URL in your browser on any device. Once you've joined via the browser, the new participant's video should appear in the app view on your Android device or emulator.
Toggling microphone and camera states
Now that we have participant video being displayed in the app, we can implement call controls.
We'll begin by checking the initial state of the local participant's microphone and camera and reflect it in the call control UI.
To do so, initialize the toggle button member variables within the
MainActivity class definition:
onCreate() to find the toggle buttons within the application layout:
join() callback we defined earlier, check the
inputs() function to get current camera and microphone states:
Next, we'll react to changes in the local device state by overriding the
onInputsUpdated() event handler within the call client listener:
Finally, let's allow the end user to toggle their input device state. We'll do so using the
setInputEnabled() call client instance method. This method will be defined within
initializeCallClient() and invoked when the microphone and camera button states change:
Leaving a call
Now that we're done with the video handling and device toggling functionality, we'll implement a final critical feature: leaving the call.
The application user should be able to disconnect from the Daily room by tapping the Leave button. This action invokes the call client's
leave() method. Add the following code within
Go ahead and run the application once more. This time, the cam and mic buttons should reflect the correct initial device state. Tapping the toggle buttons should toggle video and audio. Tapping the Leave button should exit the video call.
This quickstart walked you through the basics of using the Daily's Client SDK for Android to build a simple video call app. You should now be familiar with:
- How to create the app with appropriate dependencies and permissions
- How to join a Daily room
- How to display participant video in your Android app
- How to toggle the local participant's microphone and camera
- How to leave the Daily room
To delve further into our Android SDK, please refer to our reference documentation or reach out to our support team