Skip to content
Snippets Groups Projects
Commit 50d6c312 authored by jpbl's avatar jpbl
Browse files

we can handle incomming calls

parent 087b7e8e
No related branches found
No related tags found
No related merge requests found
......@@ -27,17 +27,25 @@
Call::Call(const std::string &sessionId,
const std::string &callId)
const std::string &callId,
bool incomming)
: mSessionId(sessionId)
, mId(callId)
, mIsIncomming(incomming)
{}
Call::Call(const Session &session,
const std::string &callId)
const std::string &callId,
bool incomming)
: mSessionId(session.id())
, mId(callId)
, mIsIncomming(incomming)
{}
bool
Call::isIncomming()
{return mIsIncomming;}
std::string
Call::call(const std::string &to)
{
......@@ -50,6 +58,7 @@ Call::call(const std::string &to)
std::string
Call::answer()
{
mIsIncomming = false;
std::list< std::string> args;
args.push_back(mId);
return Requester::instance().send(mSessionId, "answer", args);
......@@ -90,11 +99,21 @@ Call::unhold()
std::string
Call::refuse()
{
mIsIncomming = false;
std::list< std::string> args;
args.push_back(mId);
return Requester::instance().send(mSessionId, "refuse", args);
}
std::string
Call::notAvailable()
{
mIsIncomming = false;
std::list< std::string> args;
args.push_back(mId);
return Requester::instance().send(mSessionId, "notavailable", args);
}
std::string
Call::sendDtmf(char c)
{
......
......@@ -29,9 +29,17 @@ class Call
{
public:
Call(const std::string &sessionId,
const std::string &callId);
const std::string &callId,
bool incomming = false);
Call(const Session &session,
const std::string &callId);
const std::string &callId,
bool incomming = false);
/**
* This function returns true if the
* call is waiting to be picked up.
*/
bool isIncomming();
std::string id()
{return mId;}
......@@ -72,6 +80,14 @@ class Call
*/
std::string refuse();
/**
* This function will set this client to be
* not able to receive the call. It means that
* the phone can still ring. But if every client
* sent notavailable, then it will be refused.
*/
std::string notAvailable();
/**
* This function will send a tone to the line.
......@@ -91,6 +107,8 @@ class Call
* This is the unique identifier of the call.
*/
std::string mId;
bool mIsIncomming;
};
#endif
#include "globals.h"
#include "Call.hpp"
#include "Event.hpp"
#include "PhoneLineManager.hpp"
Event::Event(const std::string &code,
const std::list< std::string > &args)
: mCode(code)
, mUnusedArgs(args)
, mArgs(args)
{}
......@@ -21,21 +24,63 @@ Event::toString()
return output;
}
HangupEvent::HangupEvent(const std::string &code,
const std::list< std::string > &args)
CallRelatedEvent::CallRelatedEvent(const std::string &code,
const std::list< std::string > &args)
: Event(code, args)
{
if(args.size() != 0) {
mCallId = *args.begin();
std::list< std::string > l(getUnusedArgs());
if(l.size() != 0) {
mCallId = *l.begin();
l.pop_front();
setUnusedArgs(l);
}
}
std::string
CallRelatedEvent::getCallId()
{
return mCallId;
}
HangupEvent::HangupEvent(const std::string &code,
const std::list< std::string > &args)
: CallRelatedEvent(code, args)
{}
void
HangupEvent::execute()
{
if(mCallId.size() > 0) {
_debug("Hangup Event received for call ID: %s.\n", mCallId.c_str());
PhoneLineManager::instance().hangup(mCallId);
std::string id = getCallId();
if(id.size() > 0) {
_debug("Hangup Event received for call ID: %s.\n", id.c_str());
PhoneLineManager::instance().hangup(id);
}
else {
_debug("Hangup Event invalid (missing call ID): %s\n", toString().c_str());
}
}
IncommingEvent::IncommingEvent(const std::string &code,
const std::list< std::string > &args)
: CallRelatedEvent(code, args)
{
std::list< std::string > l;
if(getUnusedArgs().size() >= 3) {
mAccountId = *l.begin();
l.pop_front();
mOrigin = *l.begin();
l.pop_front();
setUnusedArgs(l);
}
}
void
IncommingEvent::execute()
{
std::string id = getCallId();
if(id.size() > 0) {
_debug("Hangup Event received for call ID: %s.\n", id.c_str());
PhoneLineManager::instance().incomming(mAccountId, mOrigin, getCallId());
}
else {
_debug("Event invalid: %s\n", toString().c_str());
......
......@@ -35,22 +35,50 @@ public:
virtual std::string toString();
std::list< std::string > getUnusedArgs()
{return mUnusedArgs;}
void setUnusedArgs(const std::list< std::string > &args)
{mUnusedArgs = args;}
private:
std::string mCode;
std::list< std::string > mUnusedArgs;
std::list< std::string > mArgs;
};
class CallRelatedEvent : public Event
{
public:
CallRelatedEvent(const std::string &code,
const std::list< std::string > &args);
std::string getCallId();
private:
std::string mCallId;
};
class HangupEvent : public Event
class HangupEvent : public CallRelatedEvent
{
public:
HangupEvent(const std::string &code,
const std::list< std::string > &args);
virtual void execute();
};
class IncommingEvent : public CallRelatedEvent
{
public:
IncommingEvent(const std::string &code,
const std::list< std::string > &args);
virtual void execute();
private:
std::string mCallId;
std::string mAccountId;
std::string mOrigin;
};
......
......@@ -44,7 +44,12 @@ PhoneLine::select()
mSelected = true;
if(mCall) {
mCall->unhold();
if(mCall->isIncomming()) {
mCall->answer();
}
else {
mCall->unhold();
}
}
emit selected();
......@@ -68,6 +73,18 @@ PhoneLine::unselect()
}
}
void
PhoneLine::incomming(const Call &call)
{
if(mCall) {
_debug("PhoneLine %d: Trying to set an incomming call to an active call.\n", mLine);
}
else {
mCall = new Call(call);
emit backgrounded();
}
}
void
PhoneLine::clear()
{
......@@ -138,6 +155,8 @@ PhoneLine::hangup()
mCall = NULL;
}
//This is a hack for unselect;
mSelected = true;
unselect();
}
......
......@@ -54,6 +54,8 @@ public:
void sendKey(Qt::Key c);
public slots:
void incomming(const Call &call);
/**
* Clears the buffer of the line.
*/
......
#include "PhoneLineLocker.hpp"
#include "PhoneLine.hpp"
PhoneLineLocker::PhoneLineLocker(PhoneLine *line)
PhoneLineLocker::PhoneLineLocker(PhoneLine *line, bool lock)
: mPhoneLine(line)
{
if(mPhoneLine) {
if(mPhoneLine && lock) {
mPhoneLine->lock();
}
}
......
......@@ -17,7 +17,7 @@ public:
* Retreive the "line" PhoneLine and
* locks it.
*/
PhoneLineLocker(PhoneLine *line);
PhoneLineLocker(PhoneLine *line, bool lock = true);
/**
* Unlock the currently locked PhoneLine.
......
......@@ -4,6 +4,7 @@
#include "globals.h"
#include "Call.hpp"
#include "Event.hpp"
#include "PhoneLine.hpp"
#include "PhoneLineLocker.hpp"
......@@ -14,6 +15,7 @@ PhoneLineManagerImpl::PhoneLineManagerImpl()
, mCurrentLine(NULL)
{
EventFactory::instance().registerEvent< HangupEvent >("002");
EventFactory::instance().registerEvent< IncommingEvent >("001");
mSession.getEvents();
}
......@@ -34,7 +36,7 @@ PhoneLineManagerImpl::setNbLines(unsigned int nb)
}
PhoneLine *
PhoneLineManagerImpl::selectNextAvailableLine()
PhoneLineManagerImpl::getNextAvailableLine()
{
PhoneLine *selectedLine = NULL;
......@@ -43,18 +45,29 @@ PhoneLineManagerImpl::selectNextAvailableLine()
unsigned int i = 0;
while(i < mPhoneLines.size() && !selectedLine) {
PhoneLineLocker guard(mPhoneLines[i]);
mPhoneLines[i]->lock();
if(mPhoneLines[i]->isAvailable() &&
mPhoneLines[i] != mCurrentLine) {
selectedLine = mPhoneLines[i];
}
else {
mPhoneLines[i]->unlock();
i++;
}
}
return selectedLine;
}
PhoneLine *
PhoneLineManagerImpl::selectNextAvailableLine()
{
PhoneLine *selectedLine = getNextAvailableLine();
PhoneLineLocker guard(selectedLine, false);
// If we found one available line.
if(selectedLine) {
QMutexLocker guard(&mCurrentLineMutex);
if(mCurrentLine) {
PhoneLineLocker guard(mCurrentLine);
mCurrentLine->unselect();
......@@ -66,10 +79,14 @@ PhoneLineManagerImpl::selectNextAvailableLine()
PhoneLineLocker guard(mCurrentLine);
mCurrentLine->select();
}
}
return selectedLine;
}
PhoneLine *
PhoneLineManagerImpl::getPhoneLine(unsigned int line)
{
......@@ -241,3 +258,21 @@ PhoneLineManagerImpl::clear()
}
}
void
PhoneLineManagerImpl::incomming(const std::string &,
const std::string &,
const std::string &callId)
{
PhoneLine *selectedLine = getNextAvailableLine();
PhoneLineLocker guard(selectedLine, false);
Call call(mSession, callId, true);
if(selectedLine) {
selectedLine->incomming(call);
}
else {
_debug("There's no available lines here for the incomming call ID: %s.\n",
callId.c_str());
call.notAvailable();
}
}
......@@ -82,6 +82,11 @@ public slots:
*/
void call(const QString &to);
void incomming(const std::string &accountId,
const std::string &origin,
const std::string &callId);
/**
* This function will make a call on the
* current line. If there's no selected
......@@ -103,6 +108,16 @@ public slots:
*/
void clear();
/**
* This function will return the next available line.
* The line is locked, So you'll need to unlock it.
*/
PhoneLine *getNextAvailableLine();
/**
* This function will return the next available line.
* The line is NOT locked.
*/
PhoneLine *selectNextAvailableLine();
private:
......
......@@ -17,6 +17,9 @@ SFLPhoneApp::SFLPhoneApp(int argc, char **argv)
Requester::instance().registerObject< Request >(std::string("playtone"));
Requester::instance().registerObject< Request >(std::string("playdtmf"));
Requester::instance().registerObject< EventRequest >(std::string("getevents"));
Requester::instance().registerObject< CallRelatedRequest >(std::string("answer"));
Requester::instance().registerObject< CallRelatedRequest >(std::string("notavailable"));
Requester::instance().registerObject< CallRelatedRequest >(std::string("refuse"));
Requester::instance().registerObject< CallRelatedRequest >(std::string("senddtmf"));
Requester::instance().registerObject< CallRelatedRequest >(std::string("playdtmf"));
Requester::instance().registerObject< CallRelatedRequest >(std::string("call"));
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment