static void _ics_conference_call(ics_t *data, int call_id) { int i, max; PJ_UNUSED_ARG(data); max = pjsua_call_get_count(); SHOW_LOG(3, "Let's conference call!\n"); pjsua_call_info ci; #if 1 if ( (call_id != current_call) && pjsua_call_is_active(call_id) ) { pjsua_call_reinvite(call_id, PJ_TRUE, NULL); for (i = 0; i < max; i++) { if (pjsua_call_has_media(i) != 0) { pjsua_conf_connect(pjsua_call_get_conf_port(call_id), pjsua_call_get_conf_port(i)); pjsua_conf_connect(pjsua_call_get_conf_port(i), pjsua_call_get_conf_port(call_id)); } } } else SHOW_LOG(3, "Cannot transfer call!\n"); #endif //For test only: #if 1 for (i = 0; i < max; i++){ if (pjsua_call_is_active(i) && (i != current_call)) { pjsua_call_reinvite(i, PJ_TRUE, NULL); pjsua_call_get_info(i, &ci); pjsua_conf_connect(pjsua_call_get_conf_port(ci.id), pjsua_call_get_conf_port(current_call)); pjsua_conf_connect(pjsua_call_get_conf_port(current_call), pjsua_call_get_conf_port(ci.id)); } break; } #endif }
/* * Callback on media state changed event. * The action may connect the call to sound device, to file, or * to loop the call. */ static void on_call_media_state(pjsua_call_id call_id) { pjsua_call_info call_info; pjsua_call_get_info(call_id, &call_info); /* Connect ports appropriately when media status is ACTIVE or REMOTE HOLD, * otherwise we should NOT connect the ports. */ if (call_info.media_status == PJSUA_CALL_MEDIA_ACTIVE || call_info.media_status == PJSUA_CALL_MEDIA_REMOTE_HOLD) { pj_bool_t connect_sound = PJ_TRUE; /* Loopback sound, if desired */ if (app_config.auto_loop) { pjsua_conf_connect(call_info.conf_slot, call_info.conf_slot); connect_sound = PJ_FALSE; } /* Automatically record conversation, if desired */ if (app_config.auto_rec && app_config.rec_port != PJSUA_INVALID_ID) { pjsua_conf_connect(call_info.conf_slot, app_config.rec_port); } /* Stream a file, if desired */ if ((app_config.auto_play || app_config.auto_play_hangup) && app_config.wav_port != PJSUA_INVALID_ID) { pjsua_conf_connect(app_config.wav_port, call_info.conf_slot); connect_sound = PJ_FALSE; } /* Put call in conference with other calls, if desired */ if (app_config.auto_conf) { pjsua_call_id call_ids[PJSUA_MAX_CALLS]; unsigned call_cnt=PJ_ARRAY_SIZE(call_ids); unsigned i; /* Get all calls, and establish media connection between * this call and other calls. */ pjsua_enum_calls(call_ids, &call_cnt); for (i=0; i<call_cnt; ++i) { if (call_ids[i] == call_id) continue; if (!pjsua_call_has_media(call_ids[i])) continue; pjsua_conf_connect(call_info.conf_slot, pjsua_call_get_conf_port(call_ids[i])); pjsua_conf_connect(pjsua_call_get_conf_port(call_ids[i]), call_info.conf_slot); /* Automatically record conversation, if desired */ if (app_config.auto_rec && app_config.rec_port != PJSUA_INVALID_ID) { pjsua_conf_connect(pjsua_call_get_conf_port(call_ids[i]), app_config.rec_port); } } /* Also connect call to local sound device */ connect_sound = PJ_TRUE; } /* Otherwise connect to sound device */ if (connect_sound) { pjsua_conf_connect(call_info.conf_slot, 0); pjsua_conf_connect(0, call_info.conf_slot); /* Automatically record conversation, if desired */ if (app_config.auto_rec && app_config.rec_port != PJSUA_INVALID_ID) { pjsua_conf_connect(call_info.conf_slot, app_config.rec_port); pjsua_conf_connect(0, app_config.rec_port); } } } PJ_LOG(3,(THIS_FILE, "Media for call %d is active", call_id)); /* Handle media status */ switch (call_info.media_status) { case PJSUA_CALL_MEDIA_ACTIVE: PJ_LOG(3,(THIS_FILE, "Media for call %d is active", call_id)); break; case PJSUA_CALL_MEDIA_LOCAL_HOLD: PJ_LOG(3,(THIS_FILE, "Media for call %d is suspended (hold) by local", call_id)); // call on call hold handler cb_callholdconf(call_id); break; case PJSUA_CALL_MEDIA_REMOTE_HOLD: PJ_LOG(3,(THIS_FILE, "Media for call %d is suspended (hold) by remote", call_id)); break; case PJSUA_CALL_MEDIA_ERROR: PJ_LOG(3,(THIS_FILE, "Media has reported error, disconnecting call")); { pj_str_t reason = pj_str("ICE negotiation failed"); pjsua_call_hangup(call_id, 500, &reason, NULL); } break; case PJSUA_CALL_MEDIA_NONE: PJ_LOG(3,(THIS_FILE, "Media for call %d is inactive", call_id)); break; default: pj_assert(!"Unhandled media status"); break; } }