Sending my own audio frames

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



You need to connect it to the port associated with the active call as  
well. PJ is very flexible with audio routing, so you need to  
explicitly connect up everything that should "hear" your source. Your  
player should connect to the user's speakers and the call or calls in  
progress.

Norman Franke
Answering Service for Directors, Inc.
www.myasd.com

On Jan 12, 2009, at 2:15 PM, Rafael Maia wrote:

>
> Thanks alot for your source code Norman, it has been a big boost to  
> my code development...
>
>
> I am having a diferent problem now.
> I can ear the sound frames i added on my sound speakers, but i am  
> not sending them in the RTP session.
> I did the following:
>
> pjmedia_conf_add_port(conference_bridge, pool_vars, &port, NULL,  
> &slot);
> pjmedia_conf_connect_port(conference_bridge, slot, inSlot, 0);
>
>
> I have tested putting frames on the master_port directly, and the  
> saound frames are sent throw RTP:
>
> pjmedia_port* master =  
> pjmedia_conf_get_master_port(conference_bridge);
> pjmedia_port_put_frame(master, &frame);
>
>
> ...but i don't think this is the proper way to do it
>
> Can anyone help?
> How should i send the audio frames?
>
> Thanks in advance for any help....
>
>
> Rafael Maia
>
>
>
>
>
> From: norman@xxxxxxxxx
> To: pjsip at lists.pjsip.org
> Date: Fri, 9 Jan 2009 18:48:10 -0500
> Subject: Re: Sending my own audio frames
>
> You can use pjmedia_splitcomb_create_rev_channel to reverse the put/ 
> get semantics. I do that elsewhere and it works.
>
> I did then add it to the conference bridge.
>
> Sadly, my code isn't easy to extract and is very C++ using boost and  
> a custom string library.
>
> typedef bool (*GetSamplesPtr)(void * inBuf, uint32_t * ioByteSize,  
> pj_timestamp * inTime);
>
> PlayPort::PlayPort(
> unsigned sampling_rate,
> unsigned channel_count,
> unsigned samples_per_frame,
> unsigned bits_per_sample
> )
> : pool(NULL), mCallIndex(INVALID_CALL_INDEX)
> {
>     const pj_str_t name = pj_str("file");
>
>     pool = pjsua_pool_create("asd_player", 4000, 4000);
>     assert(pool);
>
>     pj_strdup2(pool, &base.info.name, "asd_player");
>
>     base.get_frame = &file_get_frame_get;
>     base.put_frame = &file_put_frame_get;
>     base.on_destroy = &file_on_destroy_get;
>
>     pjmedia_port_info_init(&base.info, &name, SIGNATURE,  
> sampling_rate, channel_count, bits_per_sample, samples_per_frame);
>
>     port_is_open = true;
>     options = 0;
> }
>
> PlayPort::~PlayPort()
> {
>     Close();
>
>     if (pool) {
>         pj_pool_release(pool);
>         pool = NULL;
>     }
> }
>
> pj_status_t PlayPort::Open(SInt32 inCallIndex, float inVolume,  
> GetSamplesPtr inFunc)
> {
>     pj_status_t status;
>
>     status = pjsua_conf_add_port(pool, &base, &slot);
>     if (status != PJ_SUCCESS) {
>         pjmedia_port_destroy(&base);
>         return status;
>     }
>
>     mCallIndex = inCallIndex;
>
>     status = pjsua_conf_adjust_rx_level(slot, inVolume);
>
>     port_func = inFunc;
>     return status;
> }
>
> void PlayPort::Close(void)
> {
>     file_on_destroy_get(&base);
> }
>
> bool PlayPort::IsOpen(void)
> {
>     return port_is_open && slot >= 0;
> }
>
> pj_status_t PlayPort::ConnectTo(int inSlot)
> {
>     return pjsua_conf_connect(slot, inSlot);
> }
>
> pj_status_t PlayPort::DisconnectFrom(int inSlot)
> {
>     return pjsua_conf_disconnect(slot, inSlot);
> }
>
> // Class static
> pj_status_t PlayPort::file_on_destroy_get(pjmedia_port *this_port)
> {
>     // As the first element in a non-virtual class...
>     PlayPort *fport = (PlayPort *) this_port;
>     boost::recursive_mutex::scoped_lock l(fport->m);
>
>     pj_assert(this_port->info.signature == SIGNATURE);
>
>     if (fport->port_is_open) {
>      fport->port_is_open = false; // Prevents a recursive callback
>
>         fport->port_func = NULL;
>         pjsua_conf_remove_port(fport->slot); // If it's already  
> removed, e.g. audio device changed, this crashes.
>         fport->slot = 0;
>         pjmedia_port_destroy(&fport->base);
>     }
>
>     return PJ_SUCCESS;
> }
>
> // Class static
> pj_status_t PlayPort::file_get_frame_get(pjmedia_port *this_port,  
> pjmedia_frame *frame)
> {
>     // As the first element in a non-virtual class...
>     PlayPort *fport = (PlayPort *) this_port;
>
>     pj_assert(this_port->info.signature == SIGNATURE);
>
>     if (frame->size == 0) return PJ_SUCCESS;
>     if (! fport->port_func) return PJ_EEOF;
>
>     pj_size_t frame_size = frame->size;
>     if ((*fport->port_func)(frame->buf, &frame_size,  
> (PJSUA_Timestamp *) &frame->timestamp)) {
>         if (frame_size < frame->size) {
>             bzero((UInt8*)frame->buf + frame_size, frame->size -  
> frame_size);
>         }
>         frame->timestamp.u64 = 0;
>         frame->type = PJMEDIA_FRAME_TYPE_AUDIO;
>         return PJ_SUCCESS;
>     }
>     file_on_destroy_get(this_port);
>     return PJ_EEOF;
> }
>
> // Class static
> pj_status_t PlayPort::file_put_frame_get(pjmedia_port *this_port,  
> const pjmedia_frame *frame)
> {
>     return PJ_EINVALIDOP;
> }
>
>
> Norman Franke
> Answering Service for Directors, Inc.
> www.myasd.com
>
> On Jan 9, 2009, at 1:27 PM, Rafael Maia wrote:
>
>
> Thanks for your anwser Norman.
>
> You are using a very diferent approach from mine. Could you provide  
> some more information ( or some source code ) ?
>
> My DirectShow sound reading routines are pushing audio frames that i  
> need to send throw PJSIP.
>
> So i need to call put_frame on a media port.
> How did you created this "Passive" port ?
>
> You also add it to the conference bridge, right ?
>
> Thanks in advance...
>
> Rafael Maia
>
>
>
> From: norman@xxxxxxxxx
> To: pjsip at lists.pjsip.org
> Date: Fri, 9 Jan 2009 12:17:19 -0500
> Subject: Re: Sending my own audio frames
>
> I use pjmedia_port_info_init to create a player port. Something like  
> this:
>
>     pool = pjsua_pool_create("MyPlayerPool", 4000, 4000);
>     pj_strdup2(pool, &base.info.name, "MyPlayer");
>
>     base.get_frame = &file_get_frame_get;
>     base.put_frame = &file_put_frame_get;
>     base.on_destroy = &file_on_destroy_get;
>
>     pjmedia_port_info_init(&base.info, &name, SIGNATURE,  
> sampling_rate, channel_count, bits_per_sample, samples_per_frame);
>
>
> This works well for playing files in a non-standard format that I  
> need to support. You put your sample generation code in  
> file_get_frame_get.
>
> Norman Franke
> Answering Service for Directors, Inc.
> www.myasd.com
>
> On Jan 9, 2009, at 9:24 AM, Rafael Maia wrote:
>
>
> Hi,
>
> i made a media player in DirectShow that captures PCM audio frames  
> from mp3 audio files.
>
> I need to send this audio frames to PJSIP. Can anyone help me?
>
> I have tried adding a passive_port to the conference bridge and it  
> did not worked.
>
> Now i am trying to use splitcomb. And i can send some noise.
>
> Here's a code sample:
>
> // 1? pjmedia_splitcom_create
> pj_status_t status = pjmedia_splitcomb_create(pool_vars,  
> nSamplesPerSec, nChannels, samplesPerFrame, wBitsPerSample, 0,  
> &p_splitcomb);
> // for each channel
> for(unsigned int i = 0; i < nChannels; i++)  {
>      unsigned int p_slot;
>      pjmedia_port* p_port;
>
>      // 2? pjmedia_splitcom_create_rev_channel
>      status = pjmedia_splitcomb_create_rev_channel(pool_vars,  
> p_splitcomb, i, 0, &p_port);
>
>      // 3? pjmedia_conf_add_port
>      status = pjmedia_conf_add_port(conference_bridge, pool_vars,  
> p_port, NULL, &p_slot);
> }
>
>
> And then, when i want to send an audio frame i do the following:
>
> pjmedia_port_put_frame(p_splitcomb, &frame);
>
>
>
> What is wrong with my code?
> Am i using splitcom correctly?
>
> Any help would be appreciated...
>
> Rafael Maia
>
>
> O jeito mais f?cil de manter a sua lista de amigos sempre em ordem!  
> Organize seus contatos!
> _______________________________________________
> Visit our blog: http://blog.pjsip.org
>
> pjsip mailing list
> pjsip at lists.pjsip.org
> http://lists.pjsip.org/mailman/listinfo/pjsip_lists.pjsip.org
>
>
> Not?cias direto do New York Times, gols do Lance, videocassetadas e  
> muitos outros v?deos no MSN Videos! Confira j?!  
> _______________________________________________
> Visit our blog: http://blog.pjsip.org
>
> pjsip mailing list
> pjsip at lists.pjsip.org
> http://lists.pjsip.org/mailman/listinfo/pjsip_lists.pjsip.org
>
>
> O jeito mais f?cil de manter a sua lista de amigos sempre em ordem!  
> Organize seus contatos!_______________________________________________
> Visit our blog: http://blog.pjsip.org
>
> pjsip mailing list
> pjsip at lists.pjsip.org
> http://lists.pjsip.org/mailman/listinfo/pjsip_lists.pjsip.org

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.pjsip.org/pipermail/pjsip_lists.pjsip.org/attachments/20090112/b9d96ecb/attachment-0001.html>


[Index of Archives]     [Asterisk Users]     [Asterisk App Development]     [Linux ARM Kernel]     [Linux ARM]     [Linux Omap]     [Fedora ARM]     [IETF Annouce]     [Security]     [Bugtraq]     [Linux]     [Linux OMAP]     [Linux MIPS]     [Linux API]
  Powered by Linux