mirror of
https://github.com/irungentoo/toxcore.git
synced 2024-03-22 13:30:51 +08:00
Implement pausing
This commit is contained in:
parent
29601feb76
commit
9e65cd5337
173
toxav/av_test.c
173
toxav/av_test.c
|
@ -16,13 +16,25 @@
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
bool incoming;
|
bool incoming;
|
||||||
bool ringing;
|
TOXAV_CALL_STATE state;
|
||||||
bool ended;
|
|
||||||
bool errored;
|
|
||||||
bool sending;
|
|
||||||
bool paused;
|
|
||||||
} CallControl;
|
} CallControl;
|
||||||
|
|
||||||
|
const char* stringify_state(TOXAV_CALL_STATE s)
|
||||||
|
{
|
||||||
|
static const char* strings[] =
|
||||||
|
{
|
||||||
|
"NOT SENDING",
|
||||||
|
"SENDING AUDIO",
|
||||||
|
"SENDING VIDEO",
|
||||||
|
"SENDING AUDIO AND VIDEO",
|
||||||
|
"PAUSED",
|
||||||
|
"END",
|
||||||
|
"ERROR"
|
||||||
|
};
|
||||||
|
|
||||||
|
return strings [s];
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Callbacks
|
* Callbacks
|
||||||
|
@ -34,53 +46,9 @@ void t_toxav_call_cb(ToxAV *av, uint32_t friend_number, bool audio_enabled, bool
|
||||||
}
|
}
|
||||||
void t_toxav_call_state_cb(ToxAV *av, uint32_t friend_number, TOXAV_CALL_STATE state, void *user_data)
|
void t_toxav_call_state_cb(ToxAV *av, uint32_t friend_number, TOXAV_CALL_STATE state, void *user_data)
|
||||||
{
|
{
|
||||||
printf("Handling CALL STATE callback: ");
|
printf("Handling CALL STATE callback: %s\n", stringify_state(state));
|
||||||
|
|
||||||
if (((CallControl*)user_data)->paused)
|
((CallControl*)user_data)->state = state;
|
||||||
((CallControl*)user_data)->paused = false;
|
|
||||||
|
|
||||||
switch (state)
|
|
||||||
{
|
|
||||||
case TOXAV_CALL_STATE_NOT_SENDING: {
|
|
||||||
printf("Not sending");
|
|
||||||
((CallControl*)user_data)->sending = false;
|
|
||||||
} break;
|
|
||||||
|
|
||||||
case TOXAV_CALL_STATE_SENDING_A: {
|
|
||||||
printf("Sending Audio");
|
|
||||||
((CallControl*)user_data)->sending = true;
|
|
||||||
} break;
|
|
||||||
|
|
||||||
case TOXAV_CALL_STATE_SENDING_V: {
|
|
||||||
printf("Sending Video");
|
|
||||||
((CallControl*)user_data)->sending = true;
|
|
||||||
} break;
|
|
||||||
|
|
||||||
case TOXAV_CALL_STATE_SENDING_AV: {
|
|
||||||
printf("Sending Both");
|
|
||||||
((CallControl*)user_data)->sending = true;
|
|
||||||
} break;
|
|
||||||
|
|
||||||
case TOXAV_CALL_STATE_PAUSED: {
|
|
||||||
printf("Paused");
|
|
||||||
((CallControl*)user_data)->paused = true;
|
|
||||||
((CallControl*)user_data)->sending = false;
|
|
||||||
} break;
|
|
||||||
|
|
||||||
case TOXAV_CALL_STATE_END: {
|
|
||||||
printf("Ended");
|
|
||||||
((CallControl*)user_data)->ended = true;
|
|
||||||
((CallControl*)user_data)->sending = false;
|
|
||||||
} break;
|
|
||||||
|
|
||||||
case TOXAV_CALL_STATE_ERROR: {
|
|
||||||
printf("Error");
|
|
||||||
((CallControl*)user_data)->errored = true;
|
|
||||||
((CallControl*)user_data)->sending = false;
|
|
||||||
} break;
|
|
||||||
}
|
|
||||||
|
|
||||||
printf("\n");
|
|
||||||
}
|
}
|
||||||
void t_toxav_receive_video_frame_cb(ToxAV *av, uint32_t friend_number,
|
void t_toxav_receive_video_frame_cb(ToxAV *av, uint32_t friend_number,
|
||||||
uint16_t width, uint16_t height,
|
uint16_t width, uint16_t height,
|
||||||
|
@ -211,27 +179,24 @@ int main (int argc, char** argv)
|
||||||
long long unsigned int start_time = time(NULL); \
|
long long unsigned int start_time = time(NULL); \
|
||||||
\
|
\
|
||||||
\
|
\
|
||||||
while (!AliceCC.ended || !BobCC.ended) { \
|
while (BobCC.state != TOXAV_CALL_STATE_END) { \
|
||||||
\
|
\
|
||||||
if (BobCC.incoming) { \
|
if (BobCC.incoming) { \
|
||||||
TOXAV_ERR_ANSWER rc; \
|
TOXAV_ERR_ANSWER rc; \
|
||||||
toxav_answer(BobAV, 0, 48, 4000, &rc); \
|
toxav_answer(BobAV, 0, A_BR, V_BR, &rc); \
|
||||||
\
|
\
|
||||||
if (rc != TOXAV_ERR_ANSWER_OK) { \
|
if (rc != TOXAV_ERR_ANSWER_OK) { \
|
||||||
printf("toxav_answer failed: %d\n", rc); \
|
printf("toxav_answer failed: %d\n", rc); \
|
||||||
exit(1); \
|
exit(1); \
|
||||||
} \
|
} \
|
||||||
BobCC.incoming = false; \
|
BobCC.incoming = false; \
|
||||||
BobCC.sending = true; /* There is no more start callback when answering */\
|
} else { \
|
||||||
} \
|
|
||||||
else if (AliceCC.sending && BobCC.sending) { \
|
|
||||||
/* TODO rtp */ \
|
/* TODO rtp */ \
|
||||||
\
|
\
|
||||||
if (time(NULL) - start_time == 5) { \
|
if (time(NULL) - start_time == 5) { \
|
||||||
\
|
\
|
||||||
TOXAV_ERR_CALL_CONTROL rc; \
|
TOXAV_ERR_CALL_CONTROL rc; \
|
||||||
toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_CANCEL, &rc); \
|
toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_CANCEL, &rc); \
|
||||||
AliceCC.ended = true; /* There is no more end callback when hanging up */\
|
|
||||||
\
|
\
|
||||||
if (rc != TOXAV_ERR_CALL_CONTROL_OK) { \
|
if (rc != TOXAV_ERR_CALL_CONTROL_OK) { \
|
||||||
printf("toxav_call_control failed: %d\n", rc); \
|
printf("toxav_call_control failed: %d\n", rc); \
|
||||||
|
@ -286,7 +251,7 @@ int main (int argc, char** argv)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
while (!AliceCC.ended)
|
while (AliceCC.state != TOXAV_CALL_STATE_END)
|
||||||
iterate(Bsn, AliceAV, BobAV);
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
|
||||||
printf("Success!\n");
|
printf("Success!\n");
|
||||||
|
@ -323,12 +288,102 @@ int main (int argc, char** argv)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Alice will not receive end state */
|
/* Alice will not receive end state */
|
||||||
while (!BobCC.ended)
|
while (BobCC.state != TOXAV_CALL_STATE_END)
|
||||||
iterate(Bsn, AliceAV, BobAV);
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
|
||||||
printf("Success!\n");
|
printf("Success!\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
{ /* Check Mute-Unmute etc */
|
||||||
|
printf("\nTrying mute functionality...\n");
|
||||||
|
|
||||||
|
|
||||||
|
memset(&AliceCC, 0, sizeof(CallControl));
|
||||||
|
memset(&BobCC, 0, sizeof(CallControl));
|
||||||
|
|
||||||
|
/* Assume sending audio and video */
|
||||||
|
{
|
||||||
|
TOXAV_ERR_CALL rc;
|
||||||
|
toxav_call(AliceAV, 0, 48, 1000, &rc);
|
||||||
|
|
||||||
|
if (rc != TOXAV_ERR_CALL_OK) {
|
||||||
|
printf("toxav_call failed: %d\n", rc);
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
while (!BobCC.incoming)
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
|
||||||
|
/* At first try all stuff while in invalid state */
|
||||||
|
assert(!toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_PAUSE, NULL));
|
||||||
|
assert(!toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_RESUME, NULL));
|
||||||
|
assert(!toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_MUTE_AUDIO, NULL));
|
||||||
|
assert(!toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_MUTE_VIDEO, NULL));
|
||||||
|
assert(!toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_UNMUTE_AUDIO, NULL));
|
||||||
|
assert(!toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_UNMUTE_VIDEO, NULL));
|
||||||
|
|
||||||
|
{
|
||||||
|
TOXAV_ERR_ANSWER rc;
|
||||||
|
toxav_answer(BobAV, 0, 48, 4000, &rc);
|
||||||
|
|
||||||
|
if (rc != TOXAV_ERR_ANSWER_OK) {
|
||||||
|
printf("toxav_answer failed: %d\n", rc);
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
|
||||||
|
/* Pause and Resume */
|
||||||
|
printf("Pause and Resume\n");
|
||||||
|
assert(toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_PAUSE, NULL));
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
assert(BobCC.state == TOXAV_CALL_STATE_PAUSED);
|
||||||
|
assert(toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_RESUME, NULL));
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
assert(BobCC.state == TOXAV_CALL_STATE_SENDING_AV);
|
||||||
|
|
||||||
|
/* Mute/Unmute single */
|
||||||
|
printf("Mute/Unmute single\n");
|
||||||
|
assert(toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_MUTE_AUDIO, NULL));
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
assert(BobCC.state == TOXAV_CALL_CONTROL_MUTE_AUDIO);
|
||||||
|
assert(toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_UNMUTE_AUDIO, NULL));
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
assert(BobCC.state == TOXAV_CALL_CONTROL_UNMUTE_AUDIO);
|
||||||
|
|
||||||
|
/* Mute/Unmute both */
|
||||||
|
printf("Mute/Unmute both\n");
|
||||||
|
assert(toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_MUTE_AUDIO, NULL));
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
assert(BobCC.state == TOXAV_CALL_STATE_SENDING_V);
|
||||||
|
assert(toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_MUTE_VIDEO, NULL));
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
assert(BobCC.state == TOXAV_CALL_STATE_NOT_SENDING);
|
||||||
|
assert(toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_UNMUTE_AUDIO, NULL));
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
assert(BobCC.state == TOXAV_CALL_STATE_SENDING_A);
|
||||||
|
assert(toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_UNMUTE_VIDEO, NULL));
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
assert(BobCC.state == TOXAV_CALL_STATE_SENDING_AV);
|
||||||
|
|
||||||
|
{
|
||||||
|
TOXAV_ERR_CALL_CONTROL rc;
|
||||||
|
toxav_call_control(AliceAV, 0, TOXAV_CALL_CONTROL_CANCEL, &rc);
|
||||||
|
|
||||||
|
if (rc != TOXAV_ERR_CALL_CONTROL_OK) {
|
||||||
|
printf("toxav_call_control failed: %d\n", rc);
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
iterate(Bsn, AliceAV, BobAV);
|
||||||
|
assert(BobCC.state == TOXAV_CALL_STATE_END);
|
||||||
|
|
||||||
|
printf("Success!\n");
|
||||||
|
}
|
||||||
|
|
||||||
printf("\nTest successful!\n");
|
printf("\nTest successful!\n");
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
|
@ -41,8 +41,8 @@ typedef enum {
|
||||||
msi_InvalidState,
|
msi_InvalidState,
|
||||||
msi_StrayMessage,
|
msi_StrayMessage,
|
||||||
msi_SystemError,
|
msi_SystemError,
|
||||||
msi_ErrUndisclosed,
|
|
||||||
msi_HandleError,
|
msi_HandleError,
|
||||||
|
msi_ErrUndisclosed, /* NOTE: must be last enum otherwise parsing wont work */
|
||||||
} MSIError;
|
} MSIError;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
160
toxav/toxav.c
160
toxav/toxav.c
|
@ -235,6 +235,8 @@ bool toxav_call(ToxAV* av, uint32_t friend_number, uint32_t audio_bit_rate, uint
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
call->msi_call->av_call = call;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -310,12 +312,22 @@ bool toxav_call_control(ToxAV* av, uint32_t friend_number, TOXAV_CALL_CONTROL co
|
||||||
switch (control)
|
switch (control)
|
||||||
{
|
{
|
||||||
case TOXAV_CALL_CONTROL_RESUME: {
|
case TOXAV_CALL_CONTROL_RESUME: {
|
||||||
|
if (!call->active) {
|
||||||
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Only act if paused and had media transfer active before */
|
||||||
if (call->msi_call->self_capabilities == 0 &&
|
if (call->msi_call->self_capabilities == 0 &&
|
||||||
call->last_capabilities ) {
|
call->last_capabilities ) {
|
||||||
/* Only act if paused and had media transfer active before */
|
|
||||||
|
|
||||||
if (msi_change_capabilities(call->msi_call, call->last_capabilities) == -1)
|
if (msi_change_capabilities(call->msi_call,
|
||||||
return false;
|
call->last_capabilities) == -1) {
|
||||||
|
/* The only reason for this function to fail is invalid state
|
||||||
|
* ( not active ) */
|
||||||
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
rtp_start_receiving(call->rtps[audio_index]);
|
rtp_start_receiving(call->rtps[audio_index]);
|
||||||
rtp_start_receiving(call->rtps[video_index]);
|
rtp_start_receiving(call->rtps[video_index]);
|
||||||
|
@ -323,13 +335,21 @@ bool toxav_call_control(ToxAV* av, uint32_t friend_number, TOXAV_CALL_CONTROL co
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
case TOXAV_CALL_CONTROL_PAUSE: {
|
case TOXAV_CALL_CONTROL_PAUSE: {
|
||||||
if (call->msi_call->self_capabilities) {
|
if (!call->active) {
|
||||||
/* Only act if not already paused */
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Only act if not already paused */
|
||||||
|
if (call->msi_call->self_capabilities) {
|
||||||
call->last_capabilities = call->msi_call->self_capabilities;
|
call->last_capabilities = call->msi_call->self_capabilities;
|
||||||
|
|
||||||
if (msi_change_capabilities(call->msi_call, 0) == -1 )
|
if (msi_change_capabilities(call->msi_call, 0) == -1 ) {
|
||||||
return false;
|
/* The only reason for this function to fail is invalid state
|
||||||
|
* ( not active ) */
|
||||||
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
rtp_stop_receiving(call->rtps[audio_index]);
|
rtp_stop_receiving(call->rtps[audio_index]);
|
||||||
rtp_stop_receiving(call->rtps[video_index]);
|
rtp_stop_receiving(call->rtps[video_index]);
|
||||||
|
@ -341,26 +361,84 @@ bool toxav_call_control(ToxAV* av, uint32_t friend_number, TOXAV_CALL_CONTROL co
|
||||||
msi_hangup(call->msi_call);
|
msi_hangup(call->msi_call);
|
||||||
|
|
||||||
/* No mather the case, terminate the call */
|
/* No mather the case, terminate the call */
|
||||||
|
call_kill_transmission(call);
|
||||||
call_remove(call);
|
call_remove(call);
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
case TOXAV_CALL_CONTROL_MUTE_AUDIO: {
|
case TOXAV_CALL_CONTROL_MUTE_AUDIO: {
|
||||||
if (call->msi_call->self_capabilities & msi_CapRAudio ||
|
if (!call->active) {
|
||||||
call->msi_call->self_capabilities & msi_CapSAudio) {
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
uint8_t capabilities = call->msi_call->self_capabilities;
|
if (call->msi_call->self_capabilities & msi_CapRAudio) {
|
||||||
capabilities ^= msi_CapRAudio;
|
if (msi_change_capabilities(call->msi_call, call->
|
||||||
capabilities ^= msi_CapRAudio;
|
msi_call->self_capabilities ^ msi_CapRAudio) == -1) {
|
||||||
|
/* The only reason for this function to fail is invalid state
|
||||||
if (msi_change_capabilities(call->msi_call, call->msi_call->self_capabilities) == -1)
|
* ( not active ) */
|
||||||
return false;
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
rtp_stop_receiving(call->rtps[audio_index]);
|
rtp_stop_receiving(call->rtps[audio_index]);
|
||||||
}
|
}
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
case TOXAV_CALL_CONTROL_MUTE_VIDEO: {
|
case TOXAV_CALL_CONTROL_MUTE_VIDEO: {
|
||||||
|
if (!call->active) {
|
||||||
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (call->msi_call->self_capabilities & msi_CapRVideo) {
|
||||||
|
if (msi_change_capabilities(call->msi_call, call->
|
||||||
|
msi_call->self_capabilities ^ msi_CapRVideo) == -1) {
|
||||||
|
/* The only reason for this function to fail is invalid state
|
||||||
|
* ( not active ) */
|
||||||
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
|
rtp_stop_receiving(call->rtps[video_index]);
|
||||||
|
}
|
||||||
|
} break;
|
||||||
|
|
||||||
|
case TOXAV_CALL_CONTROL_UNMUTE_AUDIO: {
|
||||||
|
if (!call->active) {
|
||||||
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (call->msi_call->self_capabilities & ~msi_CapRAudio) {
|
||||||
|
if (msi_change_capabilities(call->msi_call, call->
|
||||||
|
msi_call->self_capabilities | msi_CapRAudio) == -1) {
|
||||||
|
/* The only reason for this function to fail is invalid state
|
||||||
|
* ( not active ) */
|
||||||
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
|
rtp_start_receiving(call->rtps[audio_index]);
|
||||||
|
}
|
||||||
|
} break;
|
||||||
|
|
||||||
|
case TOXAV_CALL_CONTROL_UNMUTE_VIDEO: {
|
||||||
|
if (!call->active) {
|
||||||
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (call->msi_call->self_capabilities & ~msi_CapRVideo) {
|
||||||
|
if (msi_change_capabilities(call->msi_call, call->
|
||||||
|
msi_call->self_capabilities | msi_CapRVideo) == -1) {
|
||||||
|
/* The only reason for this function to fail is invalid state
|
||||||
|
* ( not active ) */
|
||||||
|
rc = TOXAV_ERR_CALL_CONTROL_FRIEND_NOT_IN_CALL;
|
||||||
|
goto END;
|
||||||
|
}
|
||||||
|
|
||||||
|
rtp_start_receiving(call->rtps[video_index]);
|
||||||
|
}
|
||||||
} break;
|
} break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -558,8 +636,6 @@ void toxav_callback_receive_audio_frame(ToxAV* av, toxav_receive_audio_frame_cb*
|
||||||
* :: Internal
|
* :: Internal
|
||||||
*
|
*
|
||||||
******************************************************************************/
|
******************************************************************************/
|
||||||
/** TODO:
|
|
||||||
*/
|
|
||||||
int callback_invite(void* toxav_inst, MSICall* call)
|
int callback_invite(void* toxav_inst, MSICall* call)
|
||||||
{
|
{
|
||||||
ToxAV* toxav = toxav_inst;
|
ToxAV* toxav = toxav_inst;
|
||||||
|
@ -586,15 +662,20 @@ int callback_start(void* toxav_inst, MSICall* call)
|
||||||
|
|
||||||
ToxAVCall* av_call = call_get(toxav, call->friend_id);
|
ToxAVCall* av_call = call_get(toxav, call->friend_id);
|
||||||
|
|
||||||
if (av_call == NULL || !call_prepare_transmission(av_call)) {
|
if (av_call == NULL) {
|
||||||
|
/* Should this ever happen? */
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!call_prepare_transmission(av_call)) {
|
||||||
|
callback_error(toxav_inst, call);
|
||||||
call_remove(av_call);
|
call_remove(av_call);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
TOXAV_CALL_STATE state = capabilities_to_state(av_call->msi_call->peer_capabilities);
|
|
||||||
|
|
||||||
if (toxav->scb.first)
|
if (toxav->scb.first)
|
||||||
toxav->scb.first(toxav, call->friend_id, state, toxav->scb.second);
|
toxav->scb.first(toxav, call->friend_id,
|
||||||
|
capabilities_to_state(call->peer_capabilities), toxav->scb.second);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -603,18 +684,19 @@ int callback_end(void* toxav_inst, MSICall* call)
|
||||||
{
|
{
|
||||||
ToxAV* toxav = toxav_inst;
|
ToxAV* toxav = toxav_inst;
|
||||||
|
|
||||||
call_kill_transmission(call->av_call);
|
|
||||||
call_remove(call->av_call);
|
|
||||||
|
|
||||||
if (toxav->scb.first)
|
if (toxav->scb.first)
|
||||||
toxav->scb.first(toxav, call->friend_id, TOXAV_CALL_STATE_END, toxav->scb.second);
|
toxav->scb.first(toxav, call->friend_id, TOXAV_CALL_STATE_END, toxav->scb.second);
|
||||||
|
|
||||||
|
call_kill_transmission(call->av_call);
|
||||||
|
call_remove(call->av_call);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int callback_error(void* toxav_inst, MSICall* call)
|
int callback_error(void* toxav_inst, MSICall* call)
|
||||||
{
|
{
|
||||||
ToxAV* toxav = toxav_inst;
|
ToxAV* toxav = toxav_inst;
|
||||||
|
|
||||||
if (toxav->scb.first)
|
if (toxav->scb.first)
|
||||||
toxav->scb.first(toxav, call->friend_id, TOXAV_CALL_STATE_ERROR, toxav->scb.second);
|
toxav->scb.first(toxav, call->friend_id, TOXAV_CALL_STATE_ERROR, toxav->scb.second);
|
||||||
|
|
||||||
|
@ -633,14 +715,16 @@ int callback_capabilites(void* toxav_inst, MSICall* call)
|
||||||
|
|
||||||
TOXAV_CALL_STATE capabilities_to_state(uint8_t capabilities)
|
TOXAV_CALL_STATE capabilities_to_state(uint8_t capabilities)
|
||||||
{
|
{
|
||||||
if ((capabilities & msi_CapSAudio) && (capabilities & msi_CapSVideo))
|
if (capabilities == 0)
|
||||||
|
return TOXAV_CALL_STATE_PAUSED;
|
||||||
|
else if ((capabilities & msi_CapSAudio) && (capabilities & msi_CapSVideo))
|
||||||
return TOXAV_CALL_STATE_SENDING_AV;
|
return TOXAV_CALL_STATE_SENDING_AV;
|
||||||
else if (capabilities & msi_CapSAudio)
|
else if (capabilities & msi_CapSAudio)
|
||||||
return TOXAV_CALL_STATE_SENDING_A;
|
return TOXAV_CALL_STATE_SENDING_A;
|
||||||
else if (capabilities & msi_CapSVideo)
|
else if (capabilities & msi_CapSVideo)
|
||||||
return TOXAV_CALL_STATE_SENDING_V;
|
return TOXAV_CALL_STATE_SENDING_V;
|
||||||
else
|
|
||||||
return TOXAV_CALL_STATE_PAUSED;
|
return TOXAV_CALL_STATE_NOT_SENDING;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool audio_bitrate_invalid(uint32_t bitrate)
|
bool audio_bitrate_invalid(uint32_t bitrate)
|
||||||
|
@ -798,8 +882,6 @@ bool call_prepare_transmission(ToxAVCall* call)
|
||||||
goto MUTEX_INIT_ERROR;
|
goto MUTEX_INIT_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t capabilities = call->msi_call->self_capabilities;
|
|
||||||
|
|
||||||
call->cs = cs_new(call->msi_call->peer_vfpsz);
|
call->cs = cs_new(call->msi_call->peer_vfpsz);
|
||||||
|
|
||||||
if ( !call->cs ) {
|
if ( !call->cs ) {
|
||||||
|
@ -813,8 +895,7 @@ bool call_prepare_transmission(ToxAVCall* call)
|
||||||
memcpy(&call->cs->acb, &av->acb, sizeof(av->acb));
|
memcpy(&call->cs->acb, &av->acb, sizeof(av->acb));
|
||||||
memcpy(&call->cs->vcb, &av->vcb, sizeof(av->vcb));
|
memcpy(&call->cs->vcb, &av->vcb, sizeof(av->vcb));
|
||||||
|
|
||||||
if (capabilities & msi_CapSAudio || capabilities & msi_CapRAudio) { /* Prepare audio sending */
|
{ /* Prepare audio */
|
||||||
|
|
||||||
call->rtps[audio_index] = rtp_new(rtp_TypeAudio, av->m, call->friend_id);
|
call->rtps[audio_index] = rtp_new(rtp_TypeAudio, av->m, call->friend_id);
|
||||||
|
|
||||||
if ( !call->rtps[audio_index] ) {
|
if ( !call->rtps[audio_index] ) {
|
||||||
|
@ -824,12 +905,12 @@ bool call_prepare_transmission(ToxAVCall* call)
|
||||||
|
|
||||||
call->rtps[audio_index]->cs = call->cs;
|
call->rtps[audio_index]->cs = call->cs;
|
||||||
|
|
||||||
if (cs_enable_audio_sending(call->cs, call->s_audio_b, 2) != 0) {
|
/* Only enable sending if bitrate is defined */
|
||||||
|
if (call->s_audio_b > 0 && cs_enable_audio_sending(call->cs, call->s_audio_b, 2) != 0) {
|
||||||
LOGGER_WARNING("Failed to enable audio sending!");
|
LOGGER_WARNING("Failed to enable audio sending!");
|
||||||
goto FAILURE;
|
goto FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (capabilities & msi_CapRAudio) {
|
|
||||||
if (cs_enable_audio_receiving(call->cs) != 0) {
|
if (cs_enable_audio_receiving(call->cs) != 0) {
|
||||||
LOGGER_WARNING("Failed to enable audio receiving!");
|
LOGGER_WARNING("Failed to enable audio receiving!");
|
||||||
goto FAILURE;
|
goto FAILURE;
|
||||||
|
@ -837,9 +918,8 @@ bool call_prepare_transmission(ToxAVCall* call)
|
||||||
|
|
||||||
rtp_start_receiving(call->rtps[audio_index]);
|
rtp_start_receiving(call->rtps[audio_index]);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
if (capabilities & msi_CapSVideo || capabilities & msi_CapRVideo) { /* Prepare video rtp */
|
{ /* Prepare video */
|
||||||
call->rtps[video_index] = rtp_new(rtp_TypeVideo, av->m, call->friend_id);
|
call->rtps[video_index] = rtp_new(rtp_TypeVideo, av->m, call->friend_id);
|
||||||
|
|
||||||
if ( !call->rtps[video_index] ) {
|
if ( !call->rtps[video_index] ) {
|
||||||
|
@ -849,12 +929,13 @@ bool call_prepare_transmission(ToxAVCall* call)
|
||||||
|
|
||||||
call->rtps[video_index]->cs = call->cs;
|
call->rtps[video_index]->cs = call->cs;
|
||||||
|
|
||||||
if (cs_enable_video_sending(call->cs, call->s_video_b) != 0) {
|
/* Only enable sending if bitrate is defined */
|
||||||
|
if (call->s_video_b > 0 && cs_enable_video_sending(call->cs, call->s_video_b) != 0) {
|
||||||
LOGGER_WARNING("Failed to enable video sending!");
|
LOGGER_WARNING("Failed to enable video sending!");
|
||||||
goto FAILURE;
|
goto FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (capabilities & msi_CapRVideo) {
|
|
||||||
if (cs_enable_video_receiving(call->cs) != 0) {
|
if (cs_enable_video_receiving(call->cs) != 0) {
|
||||||
LOGGER_WARNING("Failed to enable video receiving!");
|
LOGGER_WARNING("Failed to enable video receiving!");
|
||||||
goto FAILURE;
|
goto FAILURE;
|
||||||
|
@ -862,13 +943,12 @@ bool call_prepare_transmission(ToxAVCall* call)
|
||||||
|
|
||||||
rtp_start_receiving(call->rtps[audio_index]);
|
rtp_start_receiving(call->rtps[audio_index]);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
call->active = 1;
|
call->active = 1;
|
||||||
pthread_mutex_unlock(call->mutex_control);
|
pthread_mutex_unlock(call->mutex_control);
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
FAILURE:
|
FAILURE:
|
||||||
rtp_kill(call->rtps[audio_index]);
|
rtp_kill(call->rtps[audio_index]);
|
||||||
call->rtps[audio_index] = NULL;
|
call->rtps[audio_index] = NULL;
|
||||||
rtp_kill(call->rtps[video_index]);
|
rtp_kill(call->rtps[video_index]);
|
||||||
|
@ -883,7 +963,7 @@ bool call_prepare_transmission(ToxAVCall* call)
|
||||||
pthread_mutex_unlock(call->mutex_control);
|
pthread_mutex_unlock(call->mutex_control);
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
MUTEX_INIT_ERROR:
|
MUTEX_INIT_ERROR:
|
||||||
pthread_mutex_unlock(call->mutex_control);
|
pthread_mutex_unlock(call->mutex_control);
|
||||||
LOGGER_ERROR("Mutex initialization failed!\n");
|
LOGGER_ERROR("Mutex initialization failed!\n");
|
||||||
return false;
|
return false;
|
||||||
|
|
|
@ -246,7 +246,7 @@ void toxav_callback_call_state(ToxAV *av, toxav_call_state_cb *function, void *u
|
||||||
typedef enum TOXAV_CALL_CONTROL {
|
typedef enum TOXAV_CALL_CONTROL {
|
||||||
/**
|
/**
|
||||||
* Resume a previously paused call. Only valid if the pause was caused by this
|
* Resume a previously paused call. Only valid if the pause was caused by this
|
||||||
* client. Not valid before the call is accepted.
|
* client, if not, this control is ignored. Not valid before the call is accepted.
|
||||||
*/
|
*/
|
||||||
TOXAV_CALL_CONTROL_RESUME,
|
TOXAV_CALL_CONTROL_RESUME,
|
||||||
/**
|
/**
|
||||||
|
@ -269,7 +269,19 @@ typedef enum TOXAV_CALL_CONTROL {
|
||||||
* compliance, this will cause the `receive_video_frame` event to stop being
|
* compliance, this will cause the `receive_video_frame` event to stop being
|
||||||
* triggered on receiving an video frame from the friend.
|
* triggered on receiving an video frame from the friend.
|
||||||
*/
|
*/
|
||||||
TOXAV_CALL_CONTROL_MUTE_VIDEO
|
TOXAV_CALL_CONTROL_MUTE_VIDEO,
|
||||||
|
/**
|
||||||
|
* Notify the friend that we are AGAIN ready to handle incoming audio.
|
||||||
|
* This control will not work if the call is not started with audio
|
||||||
|
* initiated.
|
||||||
|
*/
|
||||||
|
TOXAV_CALL_CONTROL_UNMUTE_AUDIO,
|
||||||
|
/**
|
||||||
|
* Notify the friend that we are AGAIN ready to handle incoming video.
|
||||||
|
* This control will not work if the call is not started with video
|
||||||
|
* initiated.
|
||||||
|
*/
|
||||||
|
TOXAV_CALL_CONTROL_UNMUTE_VIDEO
|
||||||
} TOXAV_CALL_CONTROL;
|
} TOXAV_CALL_CONTROL;
|
||||||
typedef enum TOXAV_ERR_CALL_CONTROL {
|
typedef enum TOXAV_ERR_CALL_CONTROL {
|
||||||
TOXAV_ERR_CALL_CONTROL_OK,
|
TOXAV_ERR_CALL_CONTROL_OK,
|
||||||
|
@ -296,7 +308,11 @@ typedef enum TOXAV_ERR_CALL_CONTROL {
|
||||||
* other party paused the call. The call will resume after both parties sent
|
* other party paused the call. The call will resume after both parties sent
|
||||||
* the RESUME control.
|
* the RESUME control.
|
||||||
*/
|
*/
|
||||||
TOXAV_ERR_CALL_CONTROL_ALREADY_PAUSED
|
TOXAV_ERR_CALL_CONTROL_ALREADY_PAUSED,
|
||||||
|
/**
|
||||||
|
* Tried to unmute a call that was not already muted.
|
||||||
|
*/
|
||||||
|
TOXAV_ERR_CALL_CONTROL_NOT_MUTED
|
||||||
} TOXAV_ERR_CALL_CONTROL;
|
} TOXAV_ERR_CALL_CONTROL;
|
||||||
/**
|
/**
|
||||||
* Sends a call control command to a friend.
|
* Sends a call control command to a friend.
|
||||||
|
|
Loading…
Reference in New Issue
Block a user