Flutter SIP通信插件td_sip_plugin的使用

Flutter SIP通信插件td_sip_plugin的使用

td_sip_plugin 是一个属于Trudian的用于Flutter应用的SIP通信插件。本指南将详细介绍如何在Flutter项目中集成并使用该插件。

使用步骤

  1. 添加依赖 在你的 pubspec.yaml 文件中添加 td_sip_plugin 作为依赖项。

    dependencies:
      td_sip_plugin: ^版本号
    
  2. Android权限配置AndroidManifest.xml 文件中添加以下权限:

    <uses-permission android:name="android.permission.WAKE_LOCK" />
    <uses-permission android:name="android.permission.DISABLE_KEYGUARD" />
    <uses-permission android:name="android.permission.RECORD_AUDIO" />
    <uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" />
    <uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
    
  3. iOS权限配置Info.plist 文件中添加麦克风使用权限描述:

    <key>NSMicrophoneUsageDescription</key>
    <string>需要麦克风权限以进行通话</string>
    

示例代码

下面是一个完整的示例代码,展示了如何在Flutter应用中集成和使用 td_sip_plugin 插件。

import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:td_sip_plugin/TDDisplayView.dart';
import 'package:td_sip_plugin/td_sip_plugin.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatefulWidget {
  [@override](/user/override)
  _MyAppState createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {
  [@override](/user/override)
  void initState() {
    super.initState();

    /// 初始化云对讲插件
    TdSipPlugin.initial();
  }

  [@override](/user/override)
  Widget build(BuildContext context) {
    return MaterialApp(
      initialRoute: "/",
      routes: <String, WidgetBuilder>{
        "/": (BuildContext context) => HomePage(),
        "/td_sip_page": (BuildContext context) => SipPage(),
      },
    );
  }
}

class HomePage extends StatefulWidget {
  [@override](/user/override)
  _HomePageState createState() => _HomePageState();
}

class _HomePageState extends State<HomePage> with WidgetsBindingObserver, TdSipObserver {
  String _loginStatus = "";
  String _callStatus = "";
  bool _isPaused = false; // 判断是否处于后台

  [@override](/user/override)
  void initState() {
    super.initState();
    _getLoginStatus();

    WidgetsBinding.instance.addObserver(this);
    TdSipPlugin.addSipObserver(this);
  }

  [@override](/user/override)
  void dispose() {
    WidgetsBinding.instance.removeObserver(this);

    /// 移除监听
    TdSipPlugin.removeSipObserver(this);
    super.dispose();
  }

  [@override](/user/override)
  void didChangeAppLifecycleState(AppLifecycleState state) {
    super.didChangeAppLifecycleState(state);
    _isPaused = state == AppLifecycleState.paused;
  }

  [@override](/user/override)
  void tdSipLoginStatus(TDSipLoginStatus status) {
    super.tdSipLoginStatus(status);
    setState(() {
      _loginStatus = "$status";
    });
  }

  [@override](/user/override)
  void tdSipDidCallOut() {
    super.tdSipDidCallOut();
    Navigator.of(context).pushNamed("/td_sip_page");
  }

  [@override](/user/override)
  void tdSipDidCallEnd() {
    super.tdSipDidCallEnd();
    Navigator.of(context).pop();
  }

  [@override](/user/override)
  void tdSipDidReceiveCallForID(String sipID) {
    super.tdSipDidReceiveCallForID(sipID);

    /// 设置呼叫页面息屏显示后,只有iOS需要做页面跳转处理,Android已在原生底层处理,只需要实现路由为"/td_sip_page"的页面即可
    /// ⚠️ 路由"/td_sip_page"为固定的呼叫页面路由
    /// 需要应用开启相关权限
    /// 1 显示在其他应用上层
    /// 2 后台弹框
    /// 3 悬浮窗
    /// 4 启动管理允许自启动和后台活动(电池)
    if (defaultTargetPlatform == TargetPlatform.android && _isPaused) {
      /// 这里可以本地存储相关呼叫信息,然后在SipPage里面去获取
      /// 比如shared_preferences
      TdSipPlugin.showSipPage();
    } else {
      Navigator.of(context)
          .pushNamed("/td_sip_page", arguments: {"sipID": sipID});
    }
  }

  void _getLoginStatus() async {
    TDSipLoginStatus status = await TdSipPlugin.getLoginStatus();
    setState(() {
      _loginStatus = "$status";
    });
  }

  void _checkPermission() async {
    Permission permission = Permission.microphone;
    PermissionStatus status = await permission.status;
    if (status.isGranted) {
      // 2107556514130605
      // 100000004
      // 110000004
      TdSipPlugin.call("2107556514130605");
    } else if (status.isPermanentlyDenied) {
      /// 用户点击了 拒绝且不再提示
    } else {
      PermissionStatus newStatus = await permission.request();
      if (newStatus.isGranted) {
        TdSipPlugin.call("2107556514130605");
      }
    }
  }

  [@override](/user/override)
  Widget build(BuildContext context) {
    return WillPopScope(
      child: Scaffold(
        appBar: AppBar(
          title: const Text('Plugin example app'),
        ),
        body: Center(
          child: Column(
            children: [
              Text(_loginStatus),
              SizedBox(height: 20),
              ElevatedButton(
                child: Text("登录"),
                onPressed: () {
                  TdSipPlugin.login(
                    sipID: "110000004",
                    sipPassword: "285f758dff64a1d8",
                    sipDomain: "47.106.186.8",
                    sipPort: "8060",
                    turnEnable: false,
                    turnServer: "",
                    turnUser: "",
                    turnPassword: "",
                    iceEnable: false,
                  );
                },
              ),
              ElevatedButton(
                child: Text("退出登录"),
                onPressed: () {
                  TdSipPlugin.logout();
                },
              ),
              ElevatedButton(
                child: Text("呼叫"),
                onPressed: () {
                  _checkPermission();
                },
              ),
              Text(_callStatus),
            ],
          ),
        ),
      ),
      onWillPop: _onWillPop,
    );
  }

  Future<bool> _onWillPop() {
    if (defaultTargetPlatform == TargetPlatform.iOS) {
      return Future.value(true);
    }

    /// 处理Android物理返回桌面后app销毁的问题
    // MzBackPlugin.navigateToSystemHome();
    return Future.value(false);
  }
}

class SipPage extends StatefulWidget {
  [@override](/user/override)
  _SipPageState createState() => _SipPageState();
}

class _SipPageState extends State<SipPage> with TdSipObserver {
  bool _showPlaceholder = true;

  [@override](/user/override)
  void initState() {
    super.initState();
    TdSipPlugin.addSipObserver(this);
  }

  [@override](/user/override)
  void dispose() {
    TdSipPlugin.removeSipObserver(this);
    super.dispose();
  }

  [@override](/user/override)
  void tdSipStreamsDidBeginRunning() {
    super.tdSipStreamsDidBeginRunning();
    setState(() {
      _showPlaceholder = false;
    });
  }

  [@override](/user/override)
  Widget build(BuildContext context) {
    Size size = MediaQuery.of(context).size;
    return Scaffold(
      body: Container(
        width: size.width,
        height: size.height,
        color: Colors.brown,
        child: Center(
          child: Column(
            children: [
              SizedBox(height: 200),
              Container(
                width: 200,
                height: 120,
                child: Stack(
                  children: [
                    TDDisplayView(),
                    Visibility(
                      visible: _showPlaceholder,
                      child: Image.asset(
                        "images/video.png",
                        width: 200,
                        height: 120,
                        fit: BoxFit.cover,
                      ),
                    ),
                  ],
                ),
              ),
              ElevatedButton(
                child: Text("挂断"),
                onPressed: () {
                  TdSipPlugin.hangup();
                },
              ),
              ElevatedButton(
                child: Text("接听"),
                onPressed: () {
                  TdSipPlugin.answer();
                },
              ),
            ],
          ),
        ),
      ),
    );
  }
}

更多关于Flutter SIP通信插件td_sip_plugin的使用的实战教程也可以访问 https://www.itying.com/category-92-b0.html

1 回复

更多关于Flutter SIP通信插件td_sip_plugin的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html


td_sip_plugin 是一个用于在 Flutter 应用中实现 SIP(Session Initiation Protocol)通信的插件。SIP 是一种用于建立、修改和终止多媒体会话(如语音和视频通话)的协议,常用于 VoIP(Voice over IP)应用。

以下是如何在 Flutter 项目中使用 td_sip_plugin 的基本步骤:

1. 添加依赖

首先,在 pubspec.yaml 文件中添加 td_sip_plugin 依赖:

dependencies:
  flutter:
    sdk: flutter
  td_sip_plugin: ^0.0.1  # 使用最新版本

然后运行 flutter pub get 来获取依赖包。

2. 初始化 SIP 客户端

在 Flutter 应用中初始化 SIP 客户端。通常,你可以在 main.dart 或某个专用的服务类中进行初始化。

import 'package:td_sip_plugin/td_sip_plugin.dart';

void initializeSipClient() async {
  await TdSipPlugin.initializeSipClient(
    account: 'your_sip_account',
    password: 'your_sip_password',
    domain: 'your_sip_domain',
    transport: 'udp',  // 或 'tcp'
  );
}

3. 注册 SIP 账户

在初始化 SIP 客户端后,你需要注册 SIP 账户以进行通信。

void registerSipAccount() async {
  bool isRegistered = await TdSipPlugin.registerSipAccount();
  if (isRegistered) {
    print('SIP account registered successfully');
  } else {
    print('Failed to register SIP account');
  }
}

4. 发起 SIP 呼叫

你可以使用 makeCall 方法发起 SIP 呼叫。

void makeCall(String callee) async {
  bool isCallInitiated = await TdSipPlugin.makeCall(callee);
  if (isCallInitiated) {
    print('Call initiated to $callee');
  } else {
    print('Failed to initiate call');
  }
}

5. 接收 SIP 呼叫

要接收 SIP 呼叫,你需要监听来自 SIP 服务器的事件。

void listenForIncomingCalls() {
  TdSipPlugin.onIncomingCall.listen((callInfo) {
    print('Incoming call from ${callInfo['caller']}');
    // 你可以在这里处理接听或拒接的逻辑
  });
}

6. 接听和结束呼叫

你可以使用 answerCallendCall 方法来接听和结束呼叫。

void answerCall() async {
  bool isAnswered = await TdSipPlugin.answerCall();
  if (isAnswered) {
    print('Call answered');
  } else {
    print('Failed to answer call');
  }
}

void endCall() async {
  bool isEnded = await TdSipPlugin.endCall();
  if (isEnded) {
    print('Call ended');
  } else {
    print('Failed to end call');
  }
}

7. 注销 SIP 账户

在应用退出或不再需要 SIP 通信时,记得注销 SIP 账户。

void unregisterSipAccount() async {
  bool isUnregistered = await TdSipPlugin.unregisterSipAccount();
  if (isUnregistered) {
    print('SIP account unregistered successfully');
  } else {
    print('Failed to unregister SIP account');
  }
}

8. 处理 SIP 事件

你可以通过监听事件来处理 SIP 客户端的状态变化和事件。

void listenForSipEvents() {
  TdSipPlugin.onSipEvent.listen((event) {
    print('SIP Event: ${event['event']}');
    // 根据事件类型处理逻辑
  });
}

9. 配置和调试

确保你的 SIP 服务器配置正确,并且你已经配置了必要的网络权限。你可以在 Android AndroidManifest.xml 和 iOS Info.plist 文件中添加相应的权限。

<!-- AndroidManifest.xml -->
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.RECORD_AUDIO" />

<!-- Info.plist -->
<key>NSMicrophoneUsageDescription</key>
<string>We need access to the microphone for SIP calls</string>
回到顶部