ios pjsip - 在 sip 通话期间播放声音

2023-12-07

当我进行 sip 呼叫时,有时我想发送 dtmf 数字。
为此,我创建了一个自定义拨号盘,当按下某个键时,该拨号盘应播放该键的声音,但在 sip 呼叫期间不会播放该声音(当没有呼叫时,会播放声音)。
这些声音是通过以下函数播放的AudioToolbox.h图书馆 (AudioServicesPlaySystemSound(soundID)).

我需要在 pjsip (pjsua) 或 AudioToolbox 库中设置一些属性才能在 sip 呼叫期间播放声音吗?
我知道这是可能的(Bria有这个,接地线另外,不确定他们是否使用 pjsip 来实现 sip)。


这个答案是这两个链接的代码片段的组合:PJSUA-API 媒体操作 and pjsipDll_PlayWav.cpp.

当 pjsua 拨打电话时,它会使用端口(会议端口)将媒体从呼叫目的地传输到您的设备扬声器。您可以同时打开多个端口.

因此,要播放键盘按钮点击声音,我们要做的就是再打开一个端口并播放声音(在本例中,它是一个 wav 文件,您可以注意到,还有一个用于流式传输 avi 文件的 pjsua 函数) 。
为此,我们将使用这个函数:

 pj_status_t    pjsua_conf_connect (pjsua_conf_port_id source, pjsua_conf_port_id sink)

其中我们的接收器端口是我们的设备扬声器端口,在这种情况下(大多数情况下)它是 0。

以下所有函数都添加到 pjsua_app.c 文件中。 在 Objective-C 类中使用它们的地方之前,您必须添加如下行:

pj_status_t play_sound_during_call(pj_str_t sound_file);

这里要播放声音的是函数:

pj_status_t play_sound_during_call(pj_str_t sound_file)
{
    pjsua_player_id player_id;
    pj_status_t status;
    status = pjsua_player_create(&sound_file, 0, &player_id);
    if (status != PJ_SUCCESS)
        return status;

    pjmedia_port *player_media_port;

    status = pjsua_player_get_port(player_id, &player_media_port);
    if (status != PJ_SUCCESS)
    {
        return status;
    }

    pj_pool_t *pool = pjsua_pool_create("my_eof_data", 512, 512);
    struct pjsua_player_eof_data *eof_data = PJ_POOL_ZALLOC_T(pool, struct pjsua_player_eof_data);
    eof_data->pool = pool;
    eof_data->player_id = player_id;

    pjmedia_wav_player_set_eof_cb(player_media_port, eof_data, &on_pjsua_wav_file_end_callback);

    status = pjsua_conf_connect(pjsua_player_get_conf_port(player_id), 0);

    if (status != PJ_SUCCESS)
    {
        return status;
    }        

    return status;
}

这是当你的 wav 文件读取(播放)结束时监听的回调函数:

struct pjsua_player_eof_data
{
    pj_pool_t          *pool;
    pjsua_player_id player_id;
};

static PJ_DEF(pj_status_t) on_pjsua_wav_file_end_callback(pjmedia_port* media_port, void* args)
{
    pj_status_t status;

    struct pjsua_player_eof_data *eof_data = (struct pjsua_player_eof_data *)args;

    status = pjsua_player_destroy(eof_data->player_id);

    PJ_LOG(3,(THIS_FILE, "End of Wav File, media_port: %d", media_port));

    if (status == PJ_SUCCESS)
    {
        return -1;// Here it is important to return a value other than PJ_SUCCESS
                  //Check link below
    }

    return PJ_SUCCESS;
}

pjmedia_wav_player_set_eof_cb 回调函数应返回 PJ_SUCCESS 以外的值的原因是因为此处的文档pjmedia_wav_player_set_eof_cb says:

请注意,如果应用程序在回调中销毁文件端口,则此处必须返回非 PJ_SUCCESS。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

ios pjsip - 在 sip 通话期间播放声音 的相关文章

随机推荐

  • 使用什么语法从 JavaDB 数据库中选择常量字段值?

    我在用着UNION ALL结合几个结果SELECT查询成一ResultSet 我使用常量字段值来标识哪条语句生成了每一行 这适用于 MySQL 但 Java DB 会抛出异常SQLSyntaxErrorException 指向第一个常量字段
  • Mac OSx 10.8 上 IDLE (Python 3.3.2) 中的 NumPy

    我知道这可能是一个重复的问题 但我在这里找到的所有答案都超出了我的想象 我对 Python 很陌生 但我想在 IDLE 中使用 NumPy python 3 3 2 IDLE 似乎无法访问 OSX 10 8 即 python 2 7 附带的
  • 按关键字对数组中的元素进行分组

    我正在 AngularJS 1 上开发一个应用程序 但我不知道如何按项目拆分另一个数组中的项目数组 我的意思是我有一系列不同的项目 我会按 uuid 对项目进行分组 如下所示 name toto uuid 1111 name tata uu
  • 做 {...} while(false)

    我正在查看一个人的一些代码 注意到他的函数中似乎有一个模式
  • 可以使用“new”位置来更改“const”数据吗?

    这是后续memcpy 可以用来更改 const 成员数据吗 And 声明 C 不可变类的惯用方式真正解决这个问题 尤其是this回答 在围绕不可变数据设计的语言中 它知道它可以 移动 您的数据 尽管它具有 逻辑 不变性 Given a st
  • 如何在 AutoFixture 中设置更复杂(类似 IoC)的注册

    使用 AutoFixture 时 是否可以在集成测试中重用生产 IoC 容器注册 问题是 如果未注册依赖项并注入 真实 数据库相关依赖项 我需要以下固定装置设置来注入模拟 var fixture new Fixture WithMocks
  • 使用 JavaFX 将渐变应用于球体对象

    我正在 JavaFX 中工作 我正在尝试将渐变应用于球体 但是 显然 我不知道该怎么做 我被困住了 因为我知道球体是一个对象 所以它需要有一种材质 但是 就颜色而言 PhongMaterial 只采用一种颜色 所以它不会采用渐变 因为渐变是
  • pyQt Matplotlib 小部件实时数据更新

    使用 pyQt 4 8 5 在 Python 2 7 中编写 如何在 pyQt 中实时更新 Matplotlib 小部件 目前 我正在对数据进行采样 现在是 random gauss 附加此数据并进行绘图 您可以看到我每次都会清除该数字并为
  • 将具有多个键的字典按一个键求和的最有效方法是什么?

    我有以下字典结构 product1 product tmpl id product id qty product uom qty price price unit subtotal price subtotal total price to
  • 在appdomain中加载静态类

    我在 C AppDomain 中遇到了一个大问题 我需要在 dll 文件中加载静态类并执行其方法 当我尝试通过以下方式加载它们时 Assembly LoadFrom XXXXX XXXXX is the full path of dll d
  • Laravel 递归关系

    我正在做一个项目Laravel 我有一个可以有父母或可以有孩子的帐户模型 所以我的模型设置如下 public function immediateChildAccounts return this gt hasMany Account ac
  • 仅对特定像素着色

    我有一个代表大脑图像的矩阵 每个 i j 位置的值都在 0 和 1 之间 我正在应用颜色图 以便那些值为 1 的像素为红色 0 为黄色 介于两者之间的像素得到中介值 现在 我想要的是那些值高于 0 8 的像素根据颜色图获得颜色 其余的变得透
  • 在另一个程序集中找到 Razor Pages

    我想在另一个程序集中找到 我的项目 Razor 页面 为此 我编写以下代码 public void ConfigureServices IServiceCollection services var adminAssembly Assemb
  • 应该避免 query_posts() 吗?

    我正在读那个query posts 应避免有利于wp query and pre get posts 我对弄乱循环没有信心 也不完全理解法典 下面的代码是否使用query posts 如果是的话 从那时起query posts 应该避免 你
  • 如何将一组变量放置在 gcc 的特定部分中,arm 是否有类似 #pragma default_variable_attributes 的内容

    下面的链接https www iar com support tech notes linker how do i place a group of functions or variables in a specific section
  • Web Worker 中的传感器读取

    看来我们无法在网络工作者中获取传感器数据 我想知道其背后的原因 用例是我正在考虑在工作线程中获取地理位置数据 并且仅将处理后的版本发送到主线程 对于 GPS 这post说工作线程不支持它 没有给出原因 我仔细检查了一下 网络工作人员不支持
  • SWT Tree - 可以降低本机展开图标吗?

    我有一个JFaceTreeViewer与 SWTTree底层 我正在绘制我的单元格 为自己提供多行支撑 目前 它看起来像这样 我希望展开图标和标签都像这样降低 这对于标签来说没有问题 因为我从StyledCellLabelProvider并
  • 根据日期检查创建新列

    我在 Scala 中有两个数据框 df1 ID Field1 1 AAA 2 BBB 4 CCC and df2 PK start date time 1 2016 10 11 11 55 23 2 2016 10 12 12 25 00
  • getSupportActionBar() 在 Android 应用程序中返回 Null

    我正在尝试在 Android Studio 中使用选项卡执行操作 但是getSupportActionBar 总是返回 null 我只想要一个带有 3 个选项卡的简单操作栏 我可以在其中单击 但操作栏或选项卡都没有出现 这是我的代码 imp
  • ios pjsip - 在 sip 通话期间播放声音

    当我进行 sip 呼叫时 有时我想发送 dtmf 数字 为此 我创建了一个自定义拨号盘 当按下某个键时 该拨号盘应播放该键的声音 但在 sip 呼叫期间不会播放该声音 当没有呼叫时 会播放声音 这些声音是通过以下函数播放的AudioTool