使用 Agora 为Android APP添加视频直播

为 Android 构建视频直播应用可能很困难,特别是在考虑可扩展性的情况下。 声网Agora 通过提供操作简单易用的 SDK 让你更加轻松,该 SDK 还为开发人员提供了对流媒体服务的 low-level 控制。 使用声网Agora 平台时,你不必担心可扩展性、掉线或延迟。

在本教程中,我们将介绍如何将视频直播添加到多主播和观众订阅的 Android 应用中。

那就开始吧!

要求

项目设置

  • 找到 strings.xml 文件,将你的 App ID 填写到 private_app_id。 然后同步 Gradle 文件。

MainActivity.java

现在,创建一个名为 MainActivity.java 的文件。 此文件包含用户首次打开应用时看到的内容的逻辑。 主要的 UI 元素包括一个单选按钮和一个文本框。 单选按钮允许用户决定他们是想要成为直播的主持人还是观众, 文本框允许用户输入他们希望加入的频道名称。

在我们的 onCreate 方法中,我们添加了用户权限,以便应用在构建页面后立即请求摄像头和麦克风权限。

@Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        int MY_PERMISSIONS_REQUEST_CAMERA = 0;
        if (ContextCompat.checkSelfPermission(this, Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED || ContextCompat.checkSelfPermission(this, Manifest.permission.RECORD_AUDIO) != PackageManager.PERMISSION_GRANTED) {
            ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.CAMERA, Manifest.permission.RECORD_AUDIO}, MY_PERMISSIONS_REQUEST_CAMERA);

        }
    }

我们将在我们的类中添加两个方法:

  • 当用户从单选按钮中选择一个选项时,将调用第一个方法。 我们将相应地设置一个变量。 我们将其设置为一个值,该值将确定用户是主播还是观众。
public void onRadioButtonClicked(View view) {
        boolean checked = ((RadioButton) view).isChecked();
        switch (view.getId()) {
            case R.id.host:
                if (checked) {
                    channelProfile = Constants.CLIENT_ROLE_BROADCASTER;
                }
                break;
            case R.id.audience:
                if (checked) {
                    channelProfile = Constants.CLIENT_ROLE_AUDIENCE;
                }
                break;
        }
    }
  • 然后我们实现一个在用户提交详细信息时调用的函数。 在这里,我们将获得我们需要的所有详细信息,并将它们发送到下一个activity。
public void onSubmit(View view) {
        EditText channel = (EditText) findViewById(R.id.channel);
        String channelName = channel.getText().toString();
        Intent intent = new Intent(this, VideoActivity.class);
        intent.putExtra(channelMessage, channelName);
        intent.putExtra(profileMessage, channelProfile);
        startActivity(intent);
    }

VideoActivity.java

默认情况下,在直播应用程序中,观众的摄像头被禁用,麦克风被静音,但主播拥有完全的访问权限。 因此,当用户作为主播加入时,他们的视频会自动添加到界面中。

所以首先我们要添加一些我们将在整个类中使用的变量。 然后我们修改 onCreate 方法以获取我们从前一个activity传入的数据。

package com.agora.samtan.agorabroadcast;

import android.content.Intent;
import android.graphics.PorterDuff;
import android.os.Bundle;
import android.util.Log;
import android.view.SurfaceView;
import android.view.View;   ;//;.;
import android.widget.FrameLayout;
import android.widget.ImageView;

import androidx.appcompat.app.AppCompatActivity;

import io.agora.rtc.Constants;
import io.agora.rtc.IRtcEngineEventHandler;
import io.agora.rtc.RtcEngine;
import io.agora.rtc.video.VideoCanvas;
import io.agora.rtc.video.VideoEncoderConfiguration;

public class VideoActivity extends AppCompatActivity {
  
  private RtcEngine mRtcEngine;
  private String channelName;
  private int channelProfile;
  
  @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_video);

        Intent intent = getIntent();
        channelName = intent.getStringExtra(MainActivity.channelMessage);
        channelProfile = intent.getIntExtra(MainActivity.profileMessage, -1);

        if (channelProfile == -1) {
            Log.e("TAG: ", "No profile");
        }

        initAgoraEngineAndJoinChannel();
    }

}

我们宣布了一个名为 initAgoraEngineAndJoinChannel 的方法,它将调用直播过程中所需的所有其他方法。 我们还定义了事件处理程序,它将决定当远程用户加入或离开或静音时调用哪些方法。

private void initAgoraEngineAndJoinChannel() {
        initalizeAgoraEngine();
        mRtcEngine.setChannelProfile(Constants.CHANNEL_PROFILE_LIVE_BROADCASTING);
        mRtcEngine.setClientRole(channelProfile);
        setupVideoProfile();
        setupLocalVideo();
        joinChannel();
}

我们来更深入地了解 initAgoraEngineAndJoinChannel() 方法以及其中引用的所有其他方法。

  • initializeAgoraEngine(): 这是一个用于初始化RtcEngine的方法。
private void initalizeAgoraEngine() {
        try {
            mRtcEngine = RtcEngine.create(getBaseContext(), getString(R.string.private_app_id), mRtcEventHandler);
        } catch (Exception e) {
            e.printStackTrace();
        }
}
  • setChannelProfile(): 这是一个使用我们 AgoraRtcEngine 对象引用的方法。 Agora 提供了各种配置文件,可以通过该方法调用并集成到应用中。

  • setClientRole(): 此方法将用户的角色设置为主播或观众(默认)。 这个方法应该在加入频道之前调用。 加入频道后可以再次调用,切换客户端角色。

  • setupVideoProfile(): 该方法用于定义视频需要渲染的方式。 你可以对帧速率、比特率、方向、镜像模式和降级偏好等属性使用自己的自定义配置。

private void setupVideoProfile() {
        mRtcEngine.enableVideo();

        mRtcEngine.setVideoEncoderConfiguration(new VideoEncoderConfiguration(VideoEncoderConfiguration.VD_640x480, VideoEncoderConfiguration.FRAME_RATE.FRAME_RATE_FPS_15,
                VideoEncoderConfiguration.STANDARD_BITRATE,
                VideoEncoderConfiguration.ORIENTATION_MODE.ORIENTATION_MODE_FIXED_PORTRAIT));
}
  • setupLocalVideo():这个函数用于从我们的 AgoraRtcEngine 中引用 setupLocalVideo 方法,我们通过它为我们的本地用户设置一个在直播流中使用的表面视图。
private void setupLocalVideo() {
        FrameLayout container = (FrameLayout) findViewById(R.id.local_video_view_container);
        SurfaceView surfaceView = RtcEngine.CreateRendererView(getBaseContext());
        surfaceView.setZOrderMediaOverlay(true);
        container.addView(surfaceView);
        mRtcEngine.setupLocalVideo(new VideoCanvas(surfaceView, VideoCanvas.RENDER_MODE_FIT, 0));
    }

joinChannel(): 频道是人们在同一个视频通话中的公共空间。 joinChannel() 方法可以这样调用:

private void joinChannel() {
        mRtcEngine.joinChannel(token, channelName, "Optional Data", 0);
}

该方法需要四个参数才能成功运行:

  • Token:建议对在生产环境中运行的所有 RTE APP进行Token身份验证。 更多关于声网Agora 平台基于令牌的认证信息,请参见 https://docs.agora.io/cn/Video/token?platform=All%20Platforms
  • 频道名称:需要一个字符串,让用户进入视频通话。
  • 可选信息:这是一个可选字段,你可以通过它传递有关频道的其他信息。
  • uid:每个加入频道的用户的唯一ID。 如果传入 0 或 null 值,Agora 会自动为每个用户分配一个 uid。

注意:此项目仅供参考和开发环境使用,不适用于生产环境。 建议对在生产环境中运行的所有 RTE APP进行Token身份验证。 更多关于 Agora 平台内基于Token身份验证的信息,请参阅本指南: 如何校验用户权限

在我们的 initialize 函数中,我们将 mRtcEventHandler 作为参数之一传递给了 create 方法,这设置了一系列回调事件,每当用户加入频道或离开频道时就会触发这些事件。

private IRtcEngineEventHandler mRtcEventHandler = new IRtcEngineEventHandler() {

        @Override
        public void onUserJoined(final int uid, int elapsed) {
            super.onUserJoined(uid, elapsed);
            runOnUiThread(new Runnable() {
                @Override
                public void run() {
                    setupRemoteVideo(uid);
                }
            });
        }

        @Override
        public void onUserOffline(int uid, int reason) {
            runOnUiThread(new Runnable() {
                @Override
                public void run() {
                    onRemoteUserLeft();
                }
            });
        }
    };

然后我们添加 onDestroy 方法来释放我们使用过的资源。

你还可以通过使用我们的 RtcEngine 的对象调用 switchCamera() 方法来添加诸如切换相机之类的功能:

mRtcEngine.switchCamera()

或者通过使用我们的 RtcEngine 的对象调用 muteLocalAudioStream() 方法来使麦克风静音:

mRtcEngine.muteLocalAudioStream(true)

有了这个,你就可以开始构建自己的直播应用程序了。

测试

在构建应用之前,请确保你已执行以下操作:

  • 在初始化 RtcEngine 时添加了你的 App ID。
  • 为 RtcEngine 和 RtcChannel 添加了频道名称。
  • 如果你的项目启用了APP证书,在Token变量中填写了Token。
  • 正确地遵循了所有说明,例如向 build.gradle 文件添加正确的依赖项,向清单添加权限等。
  • 构建后,应该看到如下内容:


在这里,我添加了两个直播流,同时可以让多个观众订阅它。

结论

恭喜! 你已经使用声网Agora Android SDK 实现了自己的 Android 视频直播应用。 上面给出的代码解释了如何进行直播。

你可以在开源示例代码获取此应用程序的完整代码。

原文作者 Meherdeep Thakur
原文链接 https://www.agora.io/en/blog/add-live-streaming-to-your-android-app-using-agora/

推荐阅读
作者信息
AgoraTechnicalTeam
TA 暂未填写个人简介
文章
169
相关专栏
SDK 教程
61 文章
本专栏仅用于分享音视频相关的技术文章,与其他开发者和 Agora 研发团队交流、分享行业前沿技术、资讯。发帖前,请参考「社区发帖指南」,方便您更好的展示所发表的文章和内容。