
1. Voximplant控制面板配置
在react native应用中实现voximplant语音通话之前,首先需要在voximplant控制面板中进行必要的配置。这包括创建voxengine场景和设置路由规则,以确保呼叫能够被正确处理和路由。
1.1 创建VoxEngine场景
VoxEngine场景是Voximplant平台上的JavaScript代码,用于处理呼叫逻辑。当一个呼叫到达Voximplant应用时,它会被分配到一个场景进行处理。对于简单的用户间直呼,我们需要一个场景来将呼叫从发起方转发到接收方。
以下是一个基本的VoxEngine场景示例,它监听AppEvents.CallAlerting事件,并将呼叫直接转发给目标用户:
// VoxEngine 场景示例
VoxEngine.addEventListener(AppEvents.CallAlerting, (e) => {
// 当有呼叫进入应用时触发
// e.call 是发起呼叫的Call对象
// e.destination 是目标用户或号码
// 使用 callUserDirect 将呼叫直接转发给目标用户
const newCall = VoxEngine.callUserDirect(
e.call, // 原始呼叫对象
e.destination, // 目标用户(例如:testuser2)
{
// 可选的呼叫设置,如显示名称、主叫号码和自定义头部
displayName: e.displayName,
callerid: e.callerid,
headers: e.headers,
}
);
// 使用 easyProcess 简化呼叫处理,自动连接原始呼叫和新呼叫
VoxEngine.easyProcess(e.call, newCall, ()=>{}, true);
});将此代码保存为VoxEngine场景并激活。
1.2 配置路由规则
路由规则定义了哪些呼叫会触发哪个VoxEngine场景。为了实现用户间的直呼,建议设置一个通用的路由规则,使其匹配所有可能的用户名。
- 模式 (Pattern): 使用 .*。
- 含义: .* 表示匹配任意数量的任意字符,这意味着所有呼叫尝试都将匹配此规则并被路由到指定的场景。
- 关联场景: 将此路由规则与您刚刚创建的VoxEngine场景关联起来。
通过这种配置,当一个用户尝试呼叫另一个用户时,Voximplant平台将捕获此呼叫,并通过VoxEngine场景进行处理,最终将呼叫路由到目标用户。
2. React Native客户端集成
在React Native应用中,我们需要处理用户登录、发起呼叫和接收呼叫等核心功能。
2.1 用户登录
用户必须先登录到Voximplant服务才能进行呼叫。以下是一个示例登录组件,演示了如何使用Voximplant.getInstance().login()方法进行身份验证。
import React, { useState } from 'react';
import {
SafeAreaView,
StatusBar,
View,
TextInput,
TouchableOpacity,
Text,
Alert,
StyleSheet, // 假设存在样式定义
} from 'react-native';
import { useNavigation } from '@react-navigation/native';
import { Voximplant } from 'react-native-voximplant';
// 替换为您的Voximplant应用和账户信息
const VOXIMPLANT_APP = 'your_app_name';
const VOXIMPLANT_ACCOUNT = 'your_account_name';
const LoginScreen = () => {
const navigation = useNavigation();
const voximplant = Voximplant.getInstance();
const [user, setUser] = useState('');
const [password, setPassword] = useState('');
async function login() {
try {
let clientState = await voximplant.getClientState();
// 如果客户端未连接,则先连接
if (clientState === Voximplant.ClientState.DISCONNECTED) {
await voximplant.connect();
}
// 登录用户
await voximplant.login(
`${user}@${VOXIMPLANT_APP}.${VOXIMPLANT_ACCOUNT}.voximplant.com`,
password,
);
navigation.navigate('CallScreen'); // 登录成功后导航到呼叫界面
} catch (e) {
let message;
switch (e.name) {
case Voximplant.ClientEvents.ConnectionFailed:
message = '连接错误,请检查您的网络连接';
break;
case Voximplant.ClientEvents.AuthResult:
message = convertCodeMessage(e.code);
break;
default:
message = '未知错误,请重试';
}
showLoginError(message);
}
}
function convertCodeMessage(code) {
switch (code) {
case 401: return '密码无效';
case 404: return '用户无效';
case 491: return '状态无效';
default: return '请稍后重试';
}
}
function showLoginError(message) {
Alert.alert('登录错误', message, [{ text: '确定' }]);
}
return (
setUser(text)}
/>
setPassword(text)}
/>
登录
);
};
const styles = StyleSheet.create({
safearea: { flex: 1, backgroundColor: '#fff' },
container: { flex: 1, justifyContent: 'center', alignItems: 'center', padding: 20 },
forminput: {
width: '80%',
height: 50,
borderColor: '#ccc',
borderWidth: 1,
borderRadius: 5,
marginBottom: 15,
paddingHorizontal: 10,
},
button: {
backgroundColor: '#007bff',
paddingVertical: 12,
paddingHorizontal: 30,
borderRadius: 5,
},
textButton: {
color: '#fff',
fontSize: 16,
fontWeight: 'bold',
},
});
export default LoginScreen;注意事项:
- 请将 VOXIMPLANT_APP 和 VOXIMPLANT_ACCOUNT 替换为您在Voximplant控制面板中创建的应用名称和账户名称。
- 登录后,用户将被导航到 CallScreen,这是进行呼叫操作的界面。
2.2 发起外呼通话
一旦用户登录成功,就可以通过Client.call() API发起呼叫。在本教程中,我们将实现一个直接呼叫特定用户的功能,而无需联系人列表。
假设我们希望登录用户“testuser1”直接呼叫“testuser2”。
import React, { useEffect, useState } from 'react';
import { View, Text, Button, Alert, StyleSheet } from 'react-native';
import { Voximplant } from 'react-native-voximplant';
const CallScreen = () => {
const voximplant = Voximplant.getInstance();
const [call, setCall] = useState(null); // 用于存储当前呼叫对象
const targetUser = 'testuser2'; // 直接指定目标用户
// 监听客户端事件,例如 IncomingCall
useEffect(() => {
const clientListeners = {
[Voximplant.ClientEvents.IncomingCall]: (event) => {
handleIncomingCall(event.call);
},
// 可以添加其他客户端事件监听
};
voximplant.on(clientListeners);
return () => {
voximplant.off(clientListeners);
};
}, []);
// 发起呼叫
const makeCall = async () => {
try {
// 配置呼叫设置,例如禁用视频以进行纯语音通话
let callSettings = {
video: {
sendVideo: false,
receiveVideo: false,
},
// 其他可选设置,如自定义头部
// customData: 'some_data',
};
// 发起呼叫到目标用户
const newCall = await voximplant.call(targetUser, callSettings);
setCall(newCall); // 保存呼叫对象
subscribeToCallEvents(newCall); // 订阅呼叫事件
Alert.alert('呼叫', `正在呼叫 ${targetUser}...`);
} catch (e) {
console.error('发起呼叫失败:', e);
Alert.alert('呼叫失败', e.message || '无法发起呼叫');
}
};
// 订阅呼叫事件
const subscribeToCallEvents = (currentCall) => {
if (!currentCall) return;
const callListeners = {
[Voximplant.CallEvents.Connected]: () => {
Alert.alert('呼叫状态', '已连接');
},
[Voximplant.CallEvents.Disconnected]: () => {
Alert.alert('呼叫状态', '已断开');
setCall(null);
},
[Voximplant.CallEvents.Failed]: (event) => {
Alert.alert('呼叫失败', `原因: ${event.reason}`);
setCall(null);
},
// 添加其他您感兴趣的呼叫事件,如 Ringing, Progress etc.
};
currentCall.on(callListeners);
};
// 挂断呼叫
const hangUpCall = () => {
if (call) {
call.hangup();
setCall(null);
Alert.alert('呼叫', '已挂断');
}
};
// 处理来电(在另一个屏幕或组件中实现更完整的功能)
const handleIncomingCall = async (incomingCall) => {
Alert.alert(
'来电',
`来自 ${incomingCall.getCallerDisplayName() || incomingCall.getCallerId()}`,
[
{
text: '拒绝',
onPress: () => incomingCall.decline(),
style: 'cancel',
},
{
text: '接听',
onPress: async () => {
try {
await incomingCall.answer();
setCall(incomingCall);
subscribeToCallEvents(incomingCall);
Alert.alert('来电', '已接听');
} catch (e) {
console.error('接听失败:', e);
Alert.alert('接听失败', e.message || '无法接听');
}
},
},
],
{ cancelable: false }
);
};
return (
Voximplant 语音通话
目标用户: {targetUser}
{!call ? (
) : (
)}
);
};
const styles = StyleSheet.create({
container: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
padding: 20,
},
title: {
fontSize: 24,
fontWeight: 'bold',
marginBottom: 20,
},
subtitle: {
fontSize: 18,
marginBottom: 30,
},
});
export default CallScreen;2.3 处理来电
当有用户呼叫当前登录用户时,Voximplant客户端会触发IncomingCall事件。我们需要监听此事件并提供接听或拒绝来电的选项。
在上面的CallScreen组件中,useEffect钩子已经包含了对Voximplant.ClientEvents.IncomingCall的监听,并通过handleIncomingCall函数处理来电。handleIncomingCall会弹出一个Alert,让用户选择接听或拒绝。
- 接听 (answer()): 调用 incomingCall.answer() 来接听电话。接听后,同样需要订阅此呼叫的事件,以管理其生命周期。
- 拒绝 (decline()): 调用 incomingCall.decline() 来拒绝电话。
2.4 管理通话生命周期事件
无论是发起呼叫还是接听来电,都需要订阅Call对象的事件,以便及时获取呼叫状态的更新。关键事件包括:
- Voximplant.CallEvents.Connected: 呼叫已成功建立连接。
- Voximplant.CallEvents.Disconnected: 呼叫已断开连接(正常挂断)。
- Voximplant.CallEvents.Failed: 呼叫失败(例如,对方无人接听、网络问题等)。
- Voximplant.CallEvents.Ringing: 对方正在响铃。
- Voximplant.CallEvents.Progress: 呼叫正在建立连接。
在CallScreen的subscribeToCallEvents函数中,我们演示了如何监听这些事件,并根据事件类型更新UI或执行其他逻辑。
3. 注意事项与总结
-
权限管理: 在React Native应用中,务必确保已获取麦克风权限。对于Android,需要在AndroidManifest.xml中添加
android:name="android.permission.RECORD_AUDIO" />;对于iOS,需要在Info.plist中添加麦克风使用说明。 - 后台运行: 考虑应用在后台时如何处理来电。Voximplant SDK支持后台通知和呼叫,但需要额外的配置。
- 错误处理: 始终包含健壮的错误处理机制,例如在网络连接失败或登录凭据错误时向用户提供有用的反馈。
- UI/UX: 本教程侧重于核心功能实现。在实际应用中,您需要设计更友好的用户界面来显示呼叫状态、持续时间,并提供静音、扬声器等控制。
- 复杂场景: 对于更复杂的呼叫场景(如多方会议、视频通话、呼叫转移等),Voximplant提供了更高级的API和功能,您可以根据需求进行探索。
通过遵循本教程的步骤,您应该能够在React Native应用中成功集成Voximplant,实现基本的语音通话功能,从用户登录到发起和接收呼叫,为您的应用增添强大的实时通信能力。










