📄 filemembers.cxx
字号:
/*
* filemembers.cxx
*
* Various file-based Members for OpenMCU
*
* Copyright (C) 2003 Post Increment
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.0 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS"
* basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
* the License for the specific language governing rights and limitations
* under the License.
*
* The Original Code is Portable Windows Library.
*
* The Initial Developer of the Original Code is Post Increment
*
* Portions of ths code were written by by Post Increment (http://www.postincrement.com)
* with the assistance of funding from Stonevoice, slc. http://www.stonevoice.com
*
* Portions of this code were written by Post Increment (http://www.postincrement.com)
* with the assistance of funding from Citron Networks (http://www.citron.com.tw)
*
* Portions are Copyright (C) 1993 Free Software Foundation, Inc.
* All Rights Reserved.
*
* Contributor(s): Derek J Smithies (derek@indranet.co.nz)
* Craig Southeren (craig@postincrement.com)
*
* $Log: filemembers.cxx,v $
* Revision 1.1 2007/10/17 19:44:29 shorne
* Initial Commit
*
* Revision 2.4 2006/08/02 06:24:53 csoutheren
* Add provision for recording input audio
*
* Revision 2.3 2006/06/09 04:39:59 csoutheren
* Migrated VideoBranch to main trunk
*
* Revision 2.2.2.5 2006/05/31 08:48:02 csoutheren
* Fixed crash on second call when entry/exit files do not exist
* Fix crash when Cisco HOLD used. Thanks to Christian Bongiovanni of Stonevoice
*
* Revision 2.2.2.4 2006/04/06 01:11:16 csoutheren
* Latest sources include
* - premedia blanking and optional image display
* - ablity to defer conference join for authentication if required
* - more bulletproofing on conference join
* - new video copy/fill functions
*
* Revision 1.1 2006/03/31 07:36:12 craigs
* New version with PINs and premedia blanking
*
* Revision 2.2.2.2 2006/03/28 05:13:38 csoutheren
* Normalised file headers
* Fixed problem with QCIF video
* Seperated H.323 and MCU process functions into seperate files
*
* Revision 2.2.2.1 2006/03/06 05:45:30 csoutheren
* Start of implementation for video. Still in progress
*
* Revision 2.2 2006/01/16 09:43:05 csoutheren
* Fixed problem with crashes at end of playing files
*
* Revision 2.1 2004/05/26 06:54:31 csoutheren
* Changed to be a PHTTPServiceProcess
* Added ability to play WAV files on member entry and exit
* Added additional documentation on all classes
* Preparation for re-introducing video
*
*/
#include <ptlib.h>
#include "conference.h"
#include "filemembers.h"
ConferenceSoundCardMember::ConferenceSoundCardMember(Conference * _conference)
#ifdef _WIN32
#pragma warning(push)
#pragma warning(disable:4355)
#endif
: ConferenceMember(_conference, this)
#ifdef _WIN32
#pragma warning(pop)
#endif
{
// open the default audio device
PString deviceName = PSoundChannel::GetDefaultDevice(PSoundChannel::Player);
soundDevice.Open(deviceName, PSoundChannel::Player, 1, 8000, 16);
// start a thread to read from the conference and write to default audio device
if (!soundDevice.IsOpen()) {
thread = NULL;
return;
}
running = TRUE;
thread = PThread::Create(PCREATE_NOTIFIER(Thread), 0, PThread::AutoDeleteThread);
conference->AddMember(this);
}
ConferenceSoundCardMember::~ConferenceSoundCardMember()
{
Unlisten();
}
void ConferenceSoundCardMember::Unlisten()
{
if (conference->RemoveMember(this))
conference->GetManager().RemoveConference(conference->GetID());
if ((thread != NULL) && running) {
running = FALSE;
thread->WaitForTermination();
thread = NULL;
}
}
void ConferenceSoundCardMember::Thread(PThread &, INT)
{
PAdaptiveDelay audioDelay;
PBYTEArray pcmData(480);
soundDevice.SetBuffers(480, 3);
while (running) {
// read a block of data
ReadAudio(pcmData.GetPointer(), pcmData.GetSize());
// write the data to the sound card
if (soundDevice.IsOpen())
soundDevice.Write(pcmData.GetPointer(), pcmData.GetSize());
audioDelay.Delay(pcmData.GetSize() / 16);
}
ConferenceManager & mgr = conference->GetManager();
mgr.RemoveMember(conference->GetID(), this);
}
///////////////////////////////////////////////////////////////////////////
ConferenceFileMember::ConferenceFileMember(Conference * _conference, const PFilePath & _fn, PFile::OpenMode _mode)
#ifdef _WIN32
#pragma warning(push)
#pragma warning(disable:4355)
#endif
: ConferenceMember(_conference, (void *)this), mode(_mode)
#ifdef _WIN32
#pragma warning(pop)
#endif
{
filenames.push_back(_fn);
Construct();
}
ConferenceFileMember::ConferenceFileMember(Conference * _conference, const FilenameList & _fns, PFile::OpenMode _mode)
#ifdef _WIN32
#pragma warning(push)
#pragma warning(disable:4355)
#endif
: ConferenceMember(_conference, (void *)this), mode(_mode)
#ifdef _WIN32
#pragma warning(pop)
#endif
{
filenames = _fns;
Construct();
}
void ConferenceFileMember::Construct()
{
thread = NULL;
running = FALSE;
// open the first file
if (!QueueNext())
return;
running = TRUE;
conference->AddMember(this);
if (mode == PFile::WriteOnly)
thread = PThread::Create(PCREATE_NOTIFIER(WriteThread), 0, PThread::AutoDeleteThread);
else
thread = PThread::Create(PCREATE_NOTIFIER(ReadThread), 0, PThread::AutoDeleteThread);
}
ConferenceFileMember::~ConferenceFileMember()
{
Unlisten();
}
BOOL ConferenceFileMember::QueueNext()
{
if (filenames.size() == 0)
return FALSE;
currentFilename = filenames.front();
filenames.pop_front();
if (!file.Open(currentFilename, mode)) {
PTRACE(1, "Cannot open WAV file " << currentFilename);
return FALSE;
}
PTRACE(1, "Playing WAV file " << currentFilename);
return TRUE;
}
void ConferenceFileMember::Unlisten()
{
if (conference->RemoveMember(this))
conference->GetManager().RemoveConference(conference->GetID());
if ((thread != NULL) && running) {
running = FALSE;
thread->WaitForTermination();
thread = NULL;
}
}
void ConferenceFileMember::WriteThread(PThread &, INT)
{
PBYTEArray pcmData(480);
PAdaptiveDelay audioDelay;
while (running) {
// read a block of data
ReadAudio(pcmData.GetPointer(), pcmData.GetSize());
// write to the file
if (file.IsOpen())
file.Write(pcmData.GetPointer(), pcmData.GetSize());
// and delay
audioDelay.Delay(pcmData.GetSize() / 16);
}
ConferenceManager & mgr = conference->GetManager();
mgr.RemoveMember(conference->GetID(), this);
}
void ConferenceFileMember::ReadThread(PThread &, INT)
{
PBYTEArray pcmData(480);
PAdaptiveDelay audioDelay;
while (running) {
if (!file.IsOpen())
break;
// read a block of data from the file
if (!file.Read(pcmData.GetPointer(), pcmData.GetSize())) {
if (!QueueNext())
break;
else
continue;
}
// read a block of data
WriteAudio(pcmData.GetPointer(), pcmData.GetSize());
// and delay
audioDelay.Delay(pcmData.GetSize() / 16);
}
ConferenceManager & mgr = conference->GetManager();
mgr.RemoveMember(conference->GetID(), this);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -