使用 React Native 创建多平台视频和语音通话应用可以帮助开发团队通过单一代码库节省维护和更新应用的时间。它提供了一种更快速、更经济有效的方式来构建具有原生组件的 Android 和 iOS 应用。

本指南将帮助您使用 React Native 在 iOS 和 Android 应用中创建或集成实时视频流,使人们可以互动、聊天并一起观看活动。你将发现如何轻松地将像 Facebook Live 这样的应用内直播流添加到现有的应用中,或像 Twitch 那样将其构建为一个独立的应用。本教程的知识将帮助你快速在游戏、音乐、体育和脱口秀应用中实现无限的现场活动广播。

测试示例应用

GitHub 获取 App.tsx 样本代码,用于建立连接和实时视频渲染,配置 React Native 开发环境,并在实际的 Android 和 iOS 设备上测试应用程序。如果您需要帮助设置 React Native 以运行 iOS 和 Android 应用,请查看我们的入门文章。

所需的技术和工具

要跟随教程,需要安装 Xcode,VS Code,Android Studio 和像 Terminal 这样的命令行工具。此外,我们的 React Native 应用中进行实时对话的广播将需要安装 Stream 的 React Native Video SDK。它帮助开发人员构建跨平台的虚拟事件流应用,以创建共享的连接和体验。

  • Xcode 15 或更高版本:配置应用程序在 iOS 上运行。
  • Android Studio Giraffe 或更高版本:为在 Android 设备上运行应用程序进行设置。
  • 终端:用于启动新的 React Native 项目。

步骤 1:创建一个新的 React Native 应用程序

启动终端或最喜欢的命令行工具,并输入以下命令来创建一个新的 React Native 项目。

npx react-native@latest init Livestream

上述命令使用最新的 React Native 模板生成一个名为 Livestream 的新项目。

步骤 2:安装 Stream 的视频 SDK 和对等依赖项

启动 VS Code,拖动你在上述步骤 1 中创建的项目文件夹 Livestream,并将其放在空的 VS Code 窗口上以打开它。现在,我们在 VS Code 中有一个空的 React Native 项目。让我们安装 React Native Video SDK。React Native SDK 是 Stream 的 JavaScript Video SDK 的一部分,允许开发者创建独特的 VoIP 呼叫体验,如视频/语音呼叫,直播流,以及仅音频聊天。

要安装视频 SDK,请打开终端 -> 在 VS Code 中新建终端,并添加以下命令。

yarn add @stream-io/video-react-native-sdk @stream-io/react-native-webrtc

上述命令安装了核心的 React Native 视频 SDK 及其可重用的 VoIP 呼叫组件。视频 SDK 使用 WebRTC 建立呼叫功能。

安装对等依赖项

视频 SDK 使用以下对等库:

yarn add react-native-incall-manager@4.1.0
yarn add react-native-svg
yarn add @react-native-community/netinfo@9.3.9
yarn add @notifee/react-native@7.7.1

步骤 3:配置 iOS 和 Android 特定设置

我们应遵守特定平台的要求,以在 iOS 和 Android 上运行我们的直播应用程序。这些要求包括设置摄像头和麦克风使用权限,并指定要使用的 Java SDK 版本。

为 iOS 声明权限

在 VS Code 中打开 iOS 文件夹。找到 Objective C 文件 AppDelegate.mm ,并添加以下代码片段,使视频 SDK 可用于 iOS。

#import "StreamVideoReactNative.h"

另外,在 launchOptions 闭包的主体中添加 SDK 的设置方法 [StreamVideoReactNative setup];

为 iOS 权限添加键和值:

仍在 iOS 文件夹中,打开 Info.plist ,在 dict 标签下找到以下的 keystring 标签。

<key>CFBundleName</key> <string>$(PRODUCT_NAME)</string>

在上述标签下附加以下键值对。

<key>NSCameraUsageDescription</key>
<string>$(PRODUCT_NAME) would like to use your camera</string>
<key>NSMicrophoneUsageDescription</key>
<string>$(PRODUCT_NAME) would like to use your microphone</string>

总的来说,当人们首次启动应用时,他们将收到上述消息提示,允许或不允许在 iOS 上使用他们的摄像头和麦克风。

为 Android 声明权限:

  1. 打开 MainApplication.kt ,并添加 import com.streamvideo.reactnative.StreamVideoReactNative;
  2. super.onCreate() 方法下方,添加 StreamVideoReactNative.setup();

为 Android 权限添加键和值:

打开 AndroidManifest.xml 并在 application 部分上方的 manifest 标签中添加以下内容,以设置相机、麦克风和蓝牙权限。

<uses-feature android:name="android.hardware.camera" />
  <uses-feature android:name="android.hardware.camera.autofocus" />
  <uses-feature android:name="android.hardware.audio.output" />
  <uses-feature android:name="android.hardware.microphone" />

  <uses-permission android:name="android.permission.CAMERA" />
  <uses-permission android:name="android.permission.RECORD_AUDIO" />
  <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
  <uses-permission android:name="android.permission.CHANGE_NETWORK_STATE" />
  <uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" />
  <uses-permission android:name="android.permission.INTERNET" />

  <uses-permission android:name="android.permission.BLUETOOTH"   android:maxSdkVersion="30" />
  <uses-permission android:name="android.permission.BLUETOOTH_ADMIN"  android:maxSdkVersion="30" />
  <uses-permission android:name="android.permission.BLUETOOTH_CONNECT" />

Android-Only 设置:编译选项

在 Android 文件夹中,打开 /app/build.gradle 并在 android 部分的主体中添加代码片段,以设置源和目标 Java 兼容版本。

compileOptions {
    sourceCompatibility JavaVersion.VERSION_1_8
    targetCompatibility JavaVersion.VERSION_17
  }

注意:所需的 Java 版本可能会有所不同,因此请参考官方的 React Native CLI 设置来安装所需的最新版本。

Android-Only 设置:Desugaring

在文件 android/gradle.properties 中,我们可以通过将 desugaring 设置为 false android.enableDexingArtifactTransform.desugaring=false 来关闭使用较新的语言特性。关闭此功能有助于防止不兼容性。

步骤 4:从 iOS/Android 设备上直播:

image.png

在前面的步骤中,我们为直播应用配置了在 iOS 和 Android 上运行的权限。在这个部分,我们将深入探讨如何使用 iOS 或 Android 设备发布直播。打开 App.tsx 并用以下示例代码替换其内容。我们按照下面的步骤从 iOS 或 Android 设备广播直播。

  1. 导入 Stream Video React Native SDK。
  2. 创建并初始化用户对象。
  3. 使用 API 密钥、用户和令牌创建一个视频客户端。当你创建一个 Stream 账户时,你将获得一个 API 密钥。如果你还没有账户,你可以免费注册。用户应该在生产环境的服务器端生成。对于测试,你可以使用你的 API 密钥和我们的令牌生成器服务来创建随机用户。为了使这个教程简单,你可以从我们文档中的直播教程第 3 步获取用户凭证来测试样本应用
  4. 创建并加入一个直播通话。

阅读下面的示例代码中的注释以获取更多详细信息。另外,查看我们的文档以了解更多关于加入和创建通话的信息。

import React from 'react';
import { StreamCall, StreamVideo, StreamVideoClient, User } from '@stream-io/video-react-native-sdk';
import { SafeAreaView, Text, StyleSheet, View, Image } from 'react-native';

const apiKey = ''; // The API key can be found in the "Credentials" section
const token = ''; // The token can be found in the "Credentials" section
const userId = ''; // The user id can be found in the "Credentials" section
const callId = ''; // The call id can be found in the "Credentials" section

// Initialize the user object. The user can be anonymous, guest, or authenticated
const user: User = {
  id: userId,
  name: 'Santhosh',
  image: `https://getstream.io/random_png/?id=${userId}&name=Santhosh`,
};

// Initialize the client by passing the API Key, user, and user token. Your backend typically generates the user and token on sign-up or login.
const myClient = new StreamVideoClient({ apiKey, user, token });

/*
How to create a call. Stream uses the same call object for livestreaming, audio rooms, and video calling. 
To create the first call object, specify the call type as livestream and provide a unique callId. 
The livestream call type comes with default settings that are usually suitable for live streams, 
but you can customize the features, permissions, and settings in our dashboard. 
Additionally, the dashboard allows you to create new call types as required.
*/
const myCall = myClient.call('livestream', callId);

// Finally, using call.join({ create: true }) will create the call object on our servers and initiate the real-time transport for audio and video. 
myCall.join({ create: true });

export default function App() {
  return (
    <StreamVideo client={myClient} language='en'>
      <StreamCall call={myCall}>
        <SafeAreaView style={{ flex: 1 }}>
          <LivestreamUI />
        </SafeAreaView>
      </StreamCall>
    </StreamVideo>
  );
}

const styles = StyleSheet.create({
  center: {
    flex: 1,
    justifyContent: 'center',
    alignItems: 'center',
    padding : 20,
  },
  text: {
    fontSize: 30, 
    color: '#005fff', 
    textAlign: 'center',
    marginTop: 64, // Add this line to increase the vertical space
  },
});

const LivestreamUI = () => (
  <View style={styles.center}>
    <Image source={require('./src/todo.png')} style={{ width: 424, height: 235 }} />
    <Text style={styles.text}>✅ TODO: How To Render a Live Video</Text>
  </View>
);

步骤 5:渲染主持人的视频

image.png

现在我们的呼叫连接已经成功,我们将在这个部分渲染并观看主播的视频。底层的直播技术使用选择性转发单元(SFU)在全球不同的服务器上复制直播流。

image.png

SFU 帮助实时将直播扩展到无限用户。

要进行本地视频渲染实现,请用以下示例代码替换 App.tsx 的内容。我们在下面的代码中用 SDK 的 videoRenderer 替换了之前的 LivestreamUI 组件。查看我们的文档,了解更多关于 videoRenderer UI 组件的信息。

import React from 'react';
import { StreamCall, StreamVideo, StreamVideoClient, User } from '@stream-io/video-react-native-sdk';
//import { SafeAreaView, Text, StyleSheet, View, Image } from 'react-native';
import { useCall, useCallStateHooks, useIncallManager, VideoRenderer } from '@stream-io/video-react-native-sdk';
import { Button, Text, View, StyleSheet, SafeAreaView } from 'react-native';

const apiKey = ''; // the API key can be found in the "Credentials" section
const token = ''; // the token can be found in the "Credentials" section
const userId = ''; // the user id can be found in the "Credentials" section
const callId = ''; // the call id can be found in the "Credentials" section

// Initialize the user object. The user can be anonymous, guest, or authenticated
const user: User = {
  id: userId,
  name: 'Santhosh',
  image: `https://getstream.io/random_png/?id=${userId}&name=Santhosh`,
};

// Initialize the client by passing the API Key, user, and token. Your backend typically generates the user and token on sign-up or login.
const myClient = new StreamVideoClient({ apiKey, user, token });

/*
How to create a call. Stream uses the same call object for livestreaming, audio rooms, and video calling. 
To create the first call object, specify the call type as livestream and provide a unique callId. 
The livestream call type comes with default settings that are usually suitable for live streams, 
but you can customize features, permissions, and settings in the dashboard. 
Additionally, the dashboard allows you to create new call types as required.
*/

const myCall = myClient.call('livestream', callId);

// Finally, using call.join({ create: true }) will create the call object on our servers and initiate the real-time transport for audio and video. 
myCall.join({ create: true });

export default function App() {
  return (
    <StreamVideo client={myClient} language='en'>
      <StreamCall call={myCall}>
        <SafeAreaView style={{ flex: 1 }}>
          <LivestreamUI />
        </SafeAreaView>
      </StreamCall>
    </StreamVideo>
  );
}

const LivestreamUI = () => {
  const call = useCall();

  const { useParticipantCount, useLocalParticipant, useIsCallLive } = useCallStateHooks();

  const totalParticipants = useParticipantCount();
  const localParticipant = useLocalParticipant();
  const isCallLive = useIsCallLive();

  // Automatically route audio to speaker devices as relevant for watching videos.
  useIncallManager({ media: 'video', auto: true });

  return (
    <View style={styles.flexed}>
      <Text style={styles.text}>Live: {totalParticipants}</Text>
      <View style={styles.flexed}>{localParticipant && <VideoRenderer participant={localParticipant} trackType='videoTrack' />}</View>
      <View style={styles.bottomBar}>
        {isCallLive ? (
          <Button onPress={() => call?.stopLive()} title='Stop Livestream' />
        ) : (
          <Button
            onPress={() => {
              call?.goLive();
            }}
            title='Start Livestream'
          />
        )}
      </View>
    </View>
  );
};

const styles = StyleSheet.create({
  flexed: {
    flex: 1,
  },
  text: {
    alignSelf: 'center',
    color: 'white',
    backgroundColor: 'blue',
    padding: 6,
    margin: 4,
  },
  bottomBar: {
    alignSelf: 'center',
    margin: 4,
  },
});

我们在上述代码中使用以下钩子来获取关于调用状态的信息 const { useParticipantCount, useLocalParticipant, useIsCallLive } = useCallStateHooks();

  • useParticipantCount : 显示正在观看直播的参与者数量。
  • useLocalParticipant : 显示主播的视频。
  • useIsCallLive : 显示直播流是否在后台(加入前屏幕)。

查看我们的文档,了解更多关于呼叫和参与者状态的信息

步骤 6:在 iOS 或 Android 设备上运行应用程序

当你正确设置了 React Native 命令行界面后,应该能够在 iOS 和 Android 设备上成功运行实时流媒体应用。如果您需要关于设置 React Native CLI 的逐步指南,请查看我们的入门教程。

注意:官方的 React Native CLI 设置经常变化,因此建议参考它来确定要安装的依赖项版本,尤其是对于 Android。

要在 iOS 设备上运行应用程序,请转到 iOS 文件夹并在 Xcode 中打开 .xcworkspace 文件。在此应用程序的上下文中,我们有 Livestream.xcworkspace 。如下图所示,为主目标和测试目标设置您的团队和捆绑标识符

image.png

image.png

按照上述步骤操作后,您现在可以连接 iOS 设备并点击 Xcode 中的运行按钮。下面的视频演示了该应用的 iPhone 版本。

image.png

从上面的视频中注意到有多个观众正在观看直播。可以使用 Stream Video 网络应用程序让众多人观看直播。

在 Android 上运行应用程序需要安装 Android 13 Tiramisu SDK。要安装它,打开 Android Studio,点击右上角的菜单按钮(3 个点)并选择 SDK 管理器。

image.png

请在下面的图片中选择所有选项进行安装。如果遇到问题,请阅读我们关于如何在没有 Expo 的情况下设置 React Native 的文章。

image.png

将 Android 设备连接到 Android Studio,然后点击工具栏中的“运行”按钮。下面的视频演示了应用程序的 Android 预览,观众通过配套的 Stream Video 网络应用程序进行观看。

下一步是什么?

在这个教程中,我们创建了一个支持类似 Facebook Live 的应用内活动流应用,以及一个类似 Twitch 的独立虚拟直播流应用。我们只介绍了使用 React Native 为 iOS 和 Android 构建直播视频流体验的基础知识。

前往我们的文档以了解更多关于高级功能和使用案例的信息,例如添加通知,管理共同主持人,以及集成屏幕录制,聊天和自定义事件。

首发于公众号 大迁世界,欢迎关注。📝 每周一篇实用的前端文章 🛠️ 分享值得关注的开发工具 ❓ 有疑问?我来回答

本文 GitHub https://github.com/qq449245884/xiaozhi 已收录,有一线大厂面试完整考点、资料以及我的系列文章。


王大冶
68.2k 声望105k 粉丝