diff -r f345bda72bc4 -r 43e37759235e Symbian3/Examples/guid-6013a680-57f9-415b-8851-c4fa63356636/mmfrawformat_8cpp-source.html --- a/Symbian3/Examples/guid-6013a680-57f9-415b-8851-c4fa63356636/mmfrawformat_8cpp-source.html Tue Mar 30 11:56:28 2010 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,788 +0,0 @@ - - -TB10.1 Example Applications: examples/Multimedia/MmfExFormatPlugin/mmfrawformat.cpp Source File - - - - -

examples/Multimedia/MmfExFormatPlugin/mmfrawformat.cpp

00001 // Copyright (c) 2002-2009 Nokia Corporation and/or its subsidiary(-ies).
-00002 // All rights reserved.
-00003 // This component and the accompanying materials are made available
-00004 // under the terms of "Eclipse Public License v1.0"
-00005 // which accompanies this distribution, and is available
-00006 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
-00007 //
-00008 // Initial Contributors:
-00009 // Nokia Corporation - initial contribution.
-00010 //
-00011 // Contributors:
-00012 //
-00013 // Description:
-00014 //
-00015 
-00016 // MMF framework headers
-00017 #include <mmffile.h>
-00018 #include <ecom.h>
-00019 #include <mmfformatimplementationuids.hrh>
-00020 #include <mmffourcc.h>
-00021 
-00022 #include "mmfrawformat.h"
-00023 #include "UIDs.hrh"
-00024 
-00025 const TUint KFormatDefaultFrameSize(0x1000); //Set default frame size to 4 K
-00026 const TUint KDefineIOBufferSize(0x0200); //easy to read clip buffer size
-00027 const TUint KOneSecondInMicroSeconds(1000000); //1 Second
-00028 const TUint KMono(1);
-00029 const TUint KStereo(2);
-00030 //this defines the valid sample rates for RAW
-00031 const TUint KRawSampleRates[] = { 8000, 11025, 22050, 44100 };
-00032 
-00033 
-00034 //
-00035 // CMMFRawFormatRead
-00036 //
-00037 
-00038 // Factory function
-00039 CMMFFormatDecode* CMMFRawFormatRead::NewL(MDataSource* aSource)
-00040         {
-00041         if ((aSource->DataSourceType()==KUidMmfDescriptorSource)||
-00042                         (aSource->DataSourceType()==KUidMmfFileSource))
-00043                 {//currently only files and descriptor MDataSources are supported
-00044                 CMMFRawFormatRead* self = new(ELeave)CMMFRawFormatRead;
-00045                 CleanupStack::PushL(self);
-00046                 self->ConstructL(aSource);
-00047                 CleanupStack::Pop();
-00048                 return self;
-00049                 }
-00050         else return NULL;
-00051         }
-00052 
-00053 // Destructor
-00054 CMMFRawFormatRead::~CMMFRawFormatRead()
-00055         {
-00056         delete iBuffer;
-00057         }
-00058         
-00059 // Second-phase constructor
-00060 void CMMFRawFormatRead::ConstructL(MDataSource* aSource)
-00061         {
-00062         // tell clip we're using it
-00063         iClip = aSource;
-00064         User::LeaveIfError(iClip->SourceThreadLogon(*this));
-00065         iClip->SourcePrimeL();
-00066         iFrameSize = KFormatDefaultFrameSize;
-00067         iClipLength = (static_cast<CMMFClip*>(iClip))->Size();
-00068         }
-00069 
-00070 // Implementing MDataSource
-00071 
-00072 // Handle request to fill buffer with data from clip
-00073 void CMMFRawFormatRead::FillBufferL(CMMFBuffer* aBuffer, MDataSink* aConsumer, TMediaId aMediaId )
-00074         {       
-00075         // check media id & pass onto the clip
-00076         if (aMediaId.iMediaType != KUidMediaTypeAudio) User::Leave(KErrNotSupported); 
-00077         iDataPath = aConsumer;
-00078         //assumes first frame is frame 1
-00079         TUint position = ((aBuffer->FrameNumber()-1)*iFrameSize)+iStartPosition;
-00080         (static_cast<CMMFClip*>(iClip))->ReadBufferL(aBuffer, position, this);
-00081         // notified of when buffer is full by BufferFilledL
-00082         }
-00083 
-00084 // creates the buffer for the source
-00085 // This overload supplies the sink buffer, as optimal source buffer size creation may depend on this
-00086 CMMFBuffer* CMMFRawFormatRead::CreateSourceBufferL(TMediaId aMediaId, CMMFBuffer& aSinkBuffer, TBool &aReference)
-00087         {
-00088         if (aMediaId.iMediaType == KUidMediaTypeAudio) 
-00089                 {
-00090                 NegotiateSourceBufferL(aSinkBuffer); //sets frame size to match sink buffer
-00091                 return CreateSourceBufferL(aMediaId, aReference);
-00092                 }
-00093         else User::Leave(KErrNotSupported);
-00094         return NULL;
-00095         }
-00096 
-00097 // creates the buffer for the source
-00098 CMMFBuffer* CMMFRawFormatRead::CreateSourceBufferL(TMediaId aMediaId, TBool &aReference)
-00099         {
-00100         if (aMediaId.iMediaType == KUidMediaTypeAudio) 
-00101                 {
-00102                 // assume default frame size if haven't determined a better one
-00103                 if (!iFrameSize) iFrameSize = KFormatDefaultFrameSize;
-00104                 // sets aReference to false if a new CMMFBuffer is returned
-00105                 aReference = EFalse;
-00106                 return CreateSourceBufferOfSizeL(iFrameSize);
-00107                 }
-00108         else User::Leave(KErrNotSupported);
-00109         return NULL;
-00110         }
-00111 
-00112 // Helper function to create and zero fill a buffer of specified size
-00113 CMMFDataBuffer* CMMFRawFormatRead::CreateSourceBufferOfSizeL(TUint aSize)
-00114         {
-00115         //needs to create source buffer
-00116         CMMFDataBuffer* buffer = CMMFDataBuffer::NewL(aSize);
-00117         buffer->Data().FillZ(aSize);
-00118         return buffer;
-00119         }
-00120 
-00121 // Helper function to determine best source buffer size
-00122 void CMMFRawFormatRead::NegotiateSourceBufferL(CMMFBuffer& aSinkBuffer)
-00123         {
-00124         // if sink buffer has a fixed size use this to determine source buffer size
-00125         if (aSinkBuffer.Type() == KUidMmfDataBuffer)
-00126                 {
-00127                 // RAW is linear data, so can set target buffer to sink buffer size
-00128                 TUint sinkBufferLength = (static_cast<CMMFDataBuffer&>(aSinkBuffer)).Data().MaxLength();
-00129                 if (sinkBufferLength == 0) sinkBufferLength = KFormatDefaultFrameSize;
-00130                 iFrameSize = sinkBufferLength; 
-00131                 CalculateFrameTimeInterval();
-00132                 }
-00133         else 
-00134                 User::Leave(KErrNotSupported);
-00135         }
-00136 
-00137 // returns the codec FourCC code for the mediaId
-00138 TFourCC CMMFRawFormatRead::SourceDataTypeCode(TMediaId aMediaId)
-00139         {
-00140         if (aMediaId.iMediaType == KUidMediaTypeAudio) return iFourCC;
-00141         else return TFourCC(); //defaults to 'NULL' fourCC
-00142         }
-00143 
-00144 // sets the codec FourCC code for the mediaId
-00145 TInt CMMFRawFormatRead::SetSourceDataTypeCode(TFourCC aSinkFourCC, TMediaId aMediaId)
-00146         {
-00147         if (aMediaId.iMediaType != KUidMediaTypeAudio) return KErrNotSupported;
-00148         else iFourCC = aSinkFourCC;
-00149         
-00150         if ((iFourCC == KMMFFourCCCodePCM16) || 
-00151                 (iFourCC == KMMFFourCCCodePCM16B) || 
-00152                 (iFourCC == KMMFFourCCCodePCMU16)) 
-00153                         iBitsPerSample = 16;
-00154         else if ((iFourCC == KMMFFourCCCodeIMAD) || 
-00155                 (iFourCC == KMMFFourCCCodeIMAS)) 
-00156                         iBitsPerSample = 4;
-00157         else 
-00158                         iBitsPerSample = 8; //default to 8
-00159         return KErrNone;
-00160         }
-00161 
-00162 // Initiate use of the interface 
-00163 TInt CMMFRawFormatRead::SourceThreadLogon(MAsyncEventHandler& aEventHandler)
-00164         {//pass through to source clip
-00165         return(iClip->SourceThreadLogon(aEventHandler));
-00166         }
-00167 
-00168 // Prepare clip
-00169 void CMMFRawFormatRead::SourcePrimeL()
-00170         {
-00171         iClip->SourcePrimeL();
-00172         CalculateFrameTimeInterval();
-00173         }
-00174 
-00175 // Play clip
-00176 void CMMFRawFormatRead::SourcePlayL()
-00177         {
-00178         iClip->SourcePlayL();
-00179         }
-00180 
-00181 // Pause clip
-00182 void CMMFRawFormatRead::SourcePauseL()
-00183         {
-00184         iClip->SourcePauseL(); //propagate state change down to clip
-00185         }
-00186 
-00187 // Stop clip
-00188 void CMMFRawFormatRead::SourceStopL()
-00189         {
-00190         iClip->SourceStopL();
-00191         }
-00192 
-00193 // End use of the interface
-00194 void CMMFRawFormatRead::SourceThreadLogoff()
-00195         {
-00196         iClip->SourceThreadLogoff();
-00197         }
-00198 
-00199 // from MDataSink
-00200 
-00201 // called by MDataSource to pass back full buffer to the sink
-00202 void CMMFRawFormatRead::BufferFilledL(CMMFBuffer* aBuffer)
-00203         {
-00204         //set position
-00205         TTimeIntervalMicroSeconds position = //assumes frame numbers begin at frame 1
-00206                 TTimeIntervalMicroSeconds(TInt64(aBuffer->FrameNumber()-1)*iFrameTimeInterval.Int64());
-00207         aBuffer->SetTimeToPlay(position);
-00208         iDataPath->BufferFilledL(aBuffer);      
-00209         }
-00210 
-00211 
-00212 // from CMMFFormatDecode
-00213 
-00214 // returns number of streams
-00215 TUint CMMFRawFormatRead::Streams(TUid aMediaType) const
-00216         {
-00217         //need to check aMediaType for audio
-00218         if (aMediaType == KUidMediaTypeAudio) return 1; //raw files can only have 1 audio stream
-00219         else return 0;
-00220         }
-00221 
-00222 // returns the time interval for one frame
-00223 TTimeIntervalMicroSeconds CMMFRawFormatRead::FrameTimeInterval(TMediaId aMediaId) const
-00224         {
-00225         if (aMediaId.iMediaType == KUidMediaTypeAudio) return iFrameTimeInterval;
-00226         else return TTimeIntervalMicroSeconds(0);
-00227         }
-00228 
-00229 // returns the duration of the source clip
-00230 TTimeIntervalMicroSeconds CMMFRawFormatRead::Duration(TMediaId aMediaId) const
-00231         {
-00232         if ((aMediaId.iMediaType == KUidMediaTypeAudio) && 
-00233                 (iClipLength) && (iSampleRate) && (iBitsPerSample) && (iChannels))
-00234                 {//we have enough values to calculate the duration
-00235                 TInt64 clipLength(iClipLength);
-00236                 clipLength*=KOneSecondInMicroSeconds;
-00237                 TTimeIntervalMicroSeconds duration = TTimeIntervalMicroSeconds(clipLength/iSampleRate);
-00238                 duration = TTimeIntervalMicroSeconds(duration.Int64()/(iBitsPerSample*iChannels));
-00239                 duration = TTimeIntervalMicroSeconds(duration.Int64()*8);
-00240                 return duration;
-00241                 }
-00242         else return TTimeIntervalMicroSeconds(0);
-00243         }
-00244 
-00245 // helper function: calculates time between frames
-00246 void CMMFRawFormatRead::CalculateFrameTimeInterval()
-00247         {
-00248         if ((iFrameSize) && (iSampleRate) && (iBitsPerSample) && (iChannels))
-00249                 {
-00250                 iFrameTimeInterval = TTimeIntervalMicroSeconds((iFrameSize*KOneSecondInMicroSeconds)/iSampleRate);
-00251                 iFrameTimeInterval = 
-00252                         TTimeIntervalMicroSeconds(iFrameTimeInterval.Int64()/(iBitsPerSample*iChannels));
-00253                 iFrameTimeInterval = TTimeIntervalMicroSeconds(iFrameTimeInterval.Int64()*8);
-00254                 }
-00255         }
-00256 
-00257 // called by sink to suggest a source buffer size
-00258 void CMMFRawFormatRead::SuggestSourceBufferSize(TUint aSuggestedBufferSize)
-00259         {
-00260         iFrameSize = aSuggestedBufferSize; //set source format frame size to buffer size suggested by sink
-00261         CalculateFrameTimeInterval();
-00262         }
-00263 
-00264 // set the number of channels
-00265 TInt CMMFRawFormatRead::SetNumChannels(TUint aChannels)
-00266         {
-00267         TInt error = KErrNone;
-00268         if ((aChannels ==  KMono)||(aChannels == KStereo)) iChannels = aChannels;
-00269         else error = KErrNotSupported; //only alow one or two channels
-00270         return error;
-00271         }
-00272 
-00273 // set the sample rate
-00274 TInt CMMFRawFormatRead::SetSampleRate(TUint aSampleRate)
-00275         {
-00276         TInt status = KErrNotSupported;
-00277         //we'll iterate through the valid sample table
-00278         TInt i = sizeof(KRawSampleRates) / sizeof(TUint);
-00279                 
-00280         while ((i--) && (status != KErrNone))
-00281                 {
-00282                 if (aSampleRate == KRawSampleRates[i])
-00283                         {
-00284                         iSampleRate = aSampleRate;
-00285                         status = KErrNone;
-00286                         }
-00287                 }
-00288         return status;
-00289         }
-00290 
-00291 // helper function to read from clip
-00292 void CMMFRawFormatRead::DoReadL(TInt aReadPosition)
-00293         {
-00294         STATIC_CAST(CMMFClip*,iClip)->ReadBufferL(iBuffer,aReadPosition);
-00295         }
-00296 
-00297 // get the supported sample rates
-00298 void CMMFRawFormatRead::GetSupportedSampleRatesL(RArray<TUint>& aSampleRates)
-00299         {
-00300         aSampleRates.Reset();
-00301 
-00302         // Iterate through the valid sample table and append each value to aSampleRates
-00303         TInt i = sizeof(KRawSampleRates) / sizeof(TUint);
-00304         
-00305         while (i--)
-00306                 {
-00307                 User::LeaveIfError(aSampleRates.Append(KRawSampleRates[i]));
-00308                 }
-00309         }
-00310 
-00311 // get the supported channel number options
-00312 void CMMFRawFormatRead::GetSupportedNumChannelsL(RArray<TUint>& aNumChannels)
-00313         {
-00314         aNumChannels.Reset();
-00315         User::LeaveIfError(aNumChannels.Append(KMono));
-00316         User::LeaveIfError(aNumChannels.Append(KStereo));
-00317         }
-00318 
-00319 // get the supported codecs
-00320 void CMMFRawFormatRead::GetSupportedDataTypesL(TMediaId aMediaId, RArray<TFourCC>& aDataTypes)
-00321         {
-00322         if (aMediaId.iMediaType != KUidMediaTypeAudio)
-00323                 User::Leave(KErrNotSupported);
-00324         aDataTypes.Reset();
-00325         User::LeaveIfError(aDataTypes.Append(KMMFFourCCCodePCM16));
-00326         User::LeaveIfError(aDataTypes.Append(KMMFFourCCCodePCM16B));
-00327         User::LeaveIfError(aDataTypes.Append(KMMFFourCCCodePCMU16));
-00328         User::LeaveIfError(aDataTypes.Append(KMMFFourCCCodeIMAD));
-00329         User::LeaveIfError(aDataTypes.Append(KMMFFourCCCodeIMAS));
-00330         }
-00331 
-00332 
-00333 //
-00334 // CMMFRawFormatWrite
-00335 //
-00336 
-00337 // Factory function
-00338 CMMFFormatEncode* CMMFRawFormatWrite::NewL(MDataSink* aSink)
-00339         {
-00340         if ((aSink->DataSinkType()==KUidMmfDescriptorSink)||
-00341                         (aSink->DataSinkType()==KUidMmfFileSink))
-00342                 {//currently only files and descriptor MDataSources are supported
-00343                 CMMFRawFormatWrite* self = new(ELeave)CMMFRawFormatWrite;
-00344                 CleanupStack::PushL(self);
-00345                 self->ConstructL(aSink);
-00346                 CleanupStack::Pop();
-00347                 return STATIC_CAST(CMMFFormatEncode*, self);
-00348                 }
-00349         else return NULL;
-00350         }
-00351 
-00352 // destructor
-00353 CMMFRawFormatWrite::~CMMFRawFormatWrite()
-00354         {
-00355         delete iBuffer;
-00356         delete iConvertBuffer;
-00357         delete iChannelAndSampleRateConverterFactory;
-00358         }
-00359         
-00360 // second-phase construction    
-00361 void CMMFRawFormatWrite::ConstructL(MDataSink* aSink)
-00362         {
-00363         iClip = aSink;
-00364         //first need to check if sink clip already exists to get settings.
-00365         User::LeaveIfError(iClip->SinkThreadLogon(*this));
-00366         iClip->SinkPrimeL();
-00367         iBuffer = CreateSinkBufferOfSizeL(KDefineIOBufferSize); //512 easiest file size to read
-00368         DoReadL(0);//read from beginning of clip
-00369         if (iBuffer->Data().Size()> 0)
-00370                 {
-00371                 iClipAlreadyExists = ETrue;
-00372                 //There is no header, so data size is the same as the clip size in this case.
-00373                 iDataSize = iClipLength = STATIC_CAST(CMMFClip*,iClip)->Size();
-00374                 }
-00375         iFrameSize = KFormatDefaultFrameSize;
-00376         }
-00377 
-00378 // from MDataSink
-00379 
-00380 // sink thread attaches
-00381 TInt CMMFRawFormatWrite::SinkThreadLogon(MAsyncEventHandler& aEventHandler)
-00382         {//pass through to sink clip
-00383         return(iClip->SinkThreadLogon(aEventHandler));
-00384         }
-00385 
-00386 // helper function: calculates time between frames
-00387 void CMMFRawFormatWrite::CalculateFrameTimeInterval()
-00388         {
-00389         if ((iFrameSize) && (iSampleRate) && (iBitsPerSample) && (iChannels))
-00390                 {
-00391                 iFrameTimeInterval = TTimeIntervalMicroSeconds((iFrameSize*KOneSecondInMicroSeconds)/iSampleRate);
-00392                 iFrameTimeInterval = 
-00393                         TTimeIntervalMicroSeconds((iFrameTimeInterval.Int64())/(iBitsPerSample*iChannels));
-00394                 iFrameTimeInterval = TTimeIntervalMicroSeconds(iFrameTimeInterval.Int64()*8);
-00395                 }
-00396         }
-00397 
-00398 // called if sink setup depends on source
-00399 void CMMFRawFormatWrite::Negotiate(MDataSource& aSource)
-00400         {
-00401         if (aSource.DataSourceType() == KUidMmfAudioInput)
-00402                 {
-00403                 // could query the audio capabilities from DevSound for the settings below
-00404                 iSourceSampleRate = 8000; // assume 8KHz for now
-00405                 iSourceChannels = 1; //assume mono
-00406                 iSourceFourCC.Set(KMMFFourCCCodePCM16); //16 bit PCM
-00407                 }
-00408         else if (aSource.DataSourceType() == KUidMmfFormatDecode)
-00409                 {//source is a clip so for now set sink settings to match source
-00410                 iSourceSampleRate = ((CMMFFormatDecode&)aSource).SampleRate();
-00411                 iSourceChannels = ((CMMFFormatDecode&)aSource).NumChannels();
-00412                 iSourceFourCC.Set(aSource.SourceDataTypeCode(TMediaId(KUidMediaTypeAudio)));
-00413                 iSourceWillSampleConvert = STATIC_CAST(CMMFFormatDecode&, aSource).SourceSampleConvert();
-00414                 ((CMMFFormatDecode&)aSource).SuggestSourceBufferSize(iFrameSize); //for now suggest format src takes same buf size as sink??
-00415                 //make the start position the end of the clip
-00416                 }
-00417         else return;
-00418         //set default sink parameters to be the same as the source
-00419         if (iClipAlreadyExists) iStartPosition = iClipLength;
-00420         if (!iSampleRate) iSampleRate = iSourceSampleRate; //might have already been set by custom command
-00421         if (!iChannels) iChannels = iSourceChannels;
-00422         if (!iBitsPerSample)
-00423                 {
-00424                 iFourCC.Set(iSourceFourCC);
-00425                 if ((iFourCC == KMMFFourCCCodePCM16) ||
-00426                         (iFourCC == KMMFFourCCCodePCM16B) ||
-00427                         (iFourCC == KMMFFourCCCodePCMU16))
-00428                                 iBitsPerSample = 16;            
-00429                 else if ((iFourCC == KMMFFourCCCodeIMAD) || 
-00430                         (iFourCC == KMMFFourCCCodeIMAS))
-00431                                 iBitsPerSample = 4;     
-00432                 else 
-00433                                 iBitsPerSample = 8; //default to 8
-00434                 }
-00435         CalculateFrameTimeInterval();
-00436         }
-00437 
-00438 // Prime the sink to be accessed
-00439 void CMMFRawFormatWrite::SinkPrimeL()
-00440         {
-00441         iClip->SinkPrimeL(); //propagate state change down to clip
-00442         CalculateFrameTimeInterval();
-00443         }
-00444 
-00445 // Play the sink
-00446 void CMMFRawFormatWrite::SinkPlayL()
-00447         {
-00448         iClip->SinkPlayL(); //propagate state change down to clip
-00449         if ((iChannels != iSourceChannels) || (iSampleRate != iSourceSampleRate) && (!iSourceWillSampleConvert))
-00450                 {//the source channels & sample rate don't match the formats - therefore need to do a conversion 
-00451                 //currently only pcm16 is supported so return with an error if format not pcm16
-00452                 if (iFourCC != KMMFFourCCCodePCM16) User::Leave(KErrNotSupported);
-00453                 iChannelAndSampleRateConverterFactory 
-00454                         = new(ELeave)CMMFChannelAndSampleRateConverterFactory;
-00455                 iChannelAndSampleRateConverter = 
-00456                         iChannelAndSampleRateConverterFactory->CreateConverterL( iSourceSampleRate, iSourceChannels, 
-00457                                                                                                                                         iSampleRate, iChannels);
-00458                 //need to create an intermediate buffer in which to place the converted data
-00459                 TUint convertedBufferFrameSize = (iFrameSize*iChannels)/iSourceChannels;
-00460                 iConvertBuffer = CreateSinkBufferOfSizeL(convertedBufferFrameSize);
-00461                 }
-00462         iFileHasChanged = ETrue; //file will change if we start playing to it
-00463         }
-00464 
-00465 // Pause the sink
-00466 void CMMFRawFormatWrite::SinkPauseL()
-00467         {
-00468         iClip->SinkPauseL(); //propagate state change down to clip
-00469         }
-00470 
-00471 // Stop the sink
-00472 void CMMFRawFormatWrite::SinkStopL()
-00473         {
-00474         iClip->SinkStopL(); //propagate state change down to clip
-00475         }
-00476 
-00477 // Detach from the sink
-00478 void CMMFRawFormatWrite::SinkThreadLogoff()
-00479         {
-00480         iClip->SinkThreadLogoff(); //propagate down to clip
-00481         }
-00482 
-00483 // Called by the CMMFDataPath to add a buffer to a clip
-00484 void CMMFRawFormatWrite::EmptyBufferL(CMMFBuffer* aBuffer, MDataSource* aSupplier, TMediaId aMediaId)
-00485         {
-00486         //since raw always contains linear audio the sink buffer size can set the source buffer size
-00487 
-00488         //check media id &pass onto clip
-00489         if (aMediaId.iMediaType!=KUidMediaTypeAudio) User::Leave(KErrNotSupported); 
-00490         iDataPath = aSupplier;
-00491 
-00492         // Check we haven't exceeded any set maximum on our clip length
-00493         if (iMaximumClipSize > 0)
-00494                 {
-00495                 // Find the current clip size
-00496                 TInt currentClipLength = STATIC_CAST(CMMFClip*, iClip)->Size();
-00497                 TInt bufferSize = aBuffer->BufferSize();
-00498                 if ((currentClipLength + bufferSize) >= iMaximumClipSize)
-00499                         User::Leave(KErrEof);
-00500                 }
-00501 
-00502         //assumes first frame is frame 1
-00503         iBufferToEmpty = aBuffer; //save this so it can be returned to datapath
-00504         TInt position = ((aBuffer->FrameNumber()-1)*iFrameSize)+iStartPosition;
-00505         if (position < (TInt)iStartPosition) position = iStartPosition; //can't write before start of header
-00506         if ((iChannelAndSampleRateConverter) && (!iSourceWillSampleConvert))
-00507                 {//need to perform channel & sample rate conversion before writing to clip
-00508                 iFrameSize = iChannelAndSampleRateConverter->Convert(*(CMMFDataBuffer*)aBuffer,*iConvertBuffer);
-00509                 STATIC_CAST(CMMFClip*,iClip)->WriteBufferL(iConvertBuffer, position, this);
-00510                 }
-00511         else
-00512                 {//no need to convert the data
-00513                 STATIC_CAST(CMMFClip*,iClip)->WriteBufferL(aBuffer, position, this);
-00514                 }
-00515         iPos = position; //save current write position
-00516         }
-00517 
-00518 // helper function to create buffer of specficed size
-00519 CMMFDataBuffer* CMMFRawFormatWrite::CreateSinkBufferOfSizeL(TUint aSize)
-00520         {
-00521         //needs to create source buffer
-00522         CMMFDataBuffer* buffer = CMMFDataBuffer::NewL(aSize);
-00523         buffer->Data().FillZ(aSize);
-00524         iBufferCreated = ETrue;
-00525         return buffer;
-00526         }
-00527 
-00528 // create buffer to receive data
-00529 CMMFBuffer* CMMFRawFormatWrite::CreateSinkBufferL(TMediaId aMediaId, TBool &aReference)
-00530         {
-00531         if (aMediaId.iMediaType == KUidMediaTypeAudio) 
-00532                 {
-00533                 if (!iFrameSize) iFrameSize = KFormatDefaultFrameSize;
-00534                 aReference = EFalse;
-00535                 return CreateSinkBufferOfSizeL(iFrameSize);
-00536                 }
-00537         else User::Leave(KErrNotSupported);
-00538         return NULL;
-00539         }
-00540 
-00541 // gets the codec type
-00542 TFourCC CMMFRawFormatWrite::SinkDataTypeCode(TMediaId aMediaId)
-00543         {
-00544         if (aMediaId.iMediaType == KUidMediaTypeAudio) return iFourCC;
-00545         else return TFourCC(); //defaults to 'NULL' fourCC
-00546         }
-00547 
-00548 // sets the codec type
-00549 TInt CMMFRawFormatWrite::SetSinkDataTypeCode(TFourCC aSinkFourCC, TMediaId aMediaId)
-00550         {
-00551         if (aMediaId.iMediaType != KUidMediaTypeAudio) return KErrNotSupported;
-00552         else iFourCC = aSinkFourCC;
-00553         
-00554         if ((iFourCC == KMMFFourCCCodePCM16) || 
-00555                 (iFourCC == KMMFFourCCCodePCM16B) ||
-00556                 (iFourCC == KMMFFourCCCodePCMU16)) 
-00557                         iBitsPerSample = 16;
-00558         else if ((iFourCC == KMMFFourCCCodeIMAD) ||
-00559                 (iFourCC == KMMFFourCCCodeIMAS)) 
-00560                         iBitsPerSample = 4;
-00561         else 
-00562                         iBitsPerSample = 8; //default to 8
-00563 
-00564         return KErrNone;
-00565         }
-00566 
-00567 // helper function to read data from clip
-00568 void CMMFRawFormatWrite::DoReadL(TInt aReadPosition)
-00569         {
-00570         STATIC_CAST(CMMFClip*,iClip)->ReadBufferL(iBuffer,aReadPosition);
-00571         }
-00572 
-00573 // helper function to write data to clip
-00574 void CMMFRawFormatWrite::DoWriteL(TInt aWritePosition)
-00575         {
-00576         STATIC_CAST(CMMFClip*,iClip)->WriteBufferL(iBuffer,aWritePosition);
-00577         }
-00578 
-00579 
-00580 // from MDataSource
-00581 
-00582 // called by MDataSink to pass back emptied buffer to the source
-00583 void CMMFRawFormatWrite::BufferEmptiedL(CMMFBuffer* aBuffer)
-00584         {
-00585         iDataSize+=aBuffer->BufferSize(); //total bytes written
-00586         iPos += aBuffer->BufferSize(); //total bytes written so far - iPos is not always = iDataSize due to repositions
-00587         if (iMaxPos < iPos) iMaxPos = iPos; //need iMaxPos incase we write data then repos to an earlier pos in the clip
-00588         if (iBufferToEmpty != aBuffer) iDataPath->BufferEmptiedL(iBufferToEmpty); //need to return same buffer
-00589         else iDataPath->BufferEmptiedL(aBuffer);
-00590         }
-00591 
-00592 
-00593 // from CMMFFormatEncode
-00594 
-00595 // set the number of channels 
-00596 TInt CMMFRawFormatWrite::SetNumChannels(TUint aChannels)
-00597         {
-00598         TInt error = KErrNone;
-00599         if ((aChannels ==  KMono)||(aChannels == KStereo)) iChannels = aChannels;
-00600         else error = KErrNotSupported; //only alow one or two channels
-00601         return error;
-00602         }
-00603 
-00604 // set the sample rate
-00605 TInt CMMFRawFormatWrite::SetSampleRate(TUint aSampleRate)
-00606         {
-00607         TInt status = KErrNotSupported;
-00608         //we'll iterate through the valid sample table
-00609         TInt i = sizeof(KRawSampleRates) / sizeof(TUint);
-00610                 
-00611         while ((i--) && (status != KErrNone))
-00612                 {
-00613                 if (aSampleRate == KRawSampleRates[i])
-00614                         {
-00615                         iSampleRate = aSampleRate;
-00616                         status = KErrNone;
-00617                         }
-00618                 }
-00619         return status;
-00620         }
-00621 
-00622 // get the frame interval
-00623 TTimeIntervalMicroSeconds CMMFRawFormatWrite::FrameTimeInterval(TMediaId aMediaId) const
-00624         {
-00625         if (aMediaId.iMediaType == KUidMediaTypeAudio) return iFrameTimeInterval;
-00626         else return TTimeIntervalMicroSeconds(0);
-00627         }
-00628 
-00629 // returns the duration of the source clip
-00630 TTimeIntervalMicroSeconds CMMFRawFormatWrite::Duration(TMediaId aMediaId) const
-00631         {
-00632         if ((aMediaId.iMediaType == KUidMediaTypeAudio) 
-00633                 && (iDataSize) && (iSampleRate) && (iBitsPerSample) && (iChannels))
-00634                 {
-00635                 TInt64 clipLength(iDataSize);
-00636                 clipLength*=KOneSecondInMicroSeconds;
-00637                 TTimeIntervalMicroSeconds duration = TTimeIntervalMicroSeconds(clipLength/iSampleRate);
-00638                 duration = 
-00639                         TTimeIntervalMicroSeconds(duration.Int64()/(iBitsPerSample*iChannels));
-00640                 duration = TTimeIntervalMicroSeconds(duration.Int64()*8);
-00641                 return duration;
-00642                 }
-00643         else return TTimeIntervalMicroSeconds(0);
-00644         }
-00645 
-00646 // Calculate and return the number of bytes used for on second of audio.
-00647 TInt64 CMMFRawFormatWrite::BytesPerSecond() 
-00648         {
-00649         TInt64 bitsPerSecond = iSampleRate * iBitsPerSample * iChannels ;
-00650         TInt64 bytesPerSecond = bitsPerSecond/8;
-00651         return bytesPerSecond ;
-00652         }
-00653 
-00654 // Shortens the clip from the position specified to the end specified.
-00655 void CMMFRawFormatWrite::CropL(TTimeIntervalMicroSeconds aPosition, TBool aToEnd )
-00656         {
-00657         // Does clip have any size to crop
-00658         if (!(STATIC_CAST(CMMFClip*,iClip)->Size())) User::Leave(KErrNotFound); //no clip to crop or clip is 0 bytes.
-00659 
-00660 
-00661         // Is aPosition between the start and the end?
-00662         if ( ( aPosition < TTimeIntervalMicroSeconds(0) ) || ( aPosition >= Duration( KUidMediaTypeAudio) ) ) 
-00663                 User::Leave( KErrArgument ) ;
-00664 
-00665         // Convert aPostion to cropPosition in bytes
-00666 
-00667         TInt64 cropPosition64 = 
-00668                 TInt64( ( aPosition.Int64() * iSampleRate * (iBitsPerSample/8) * iChannels ) /KOneSecondInMicroSeconds);
-00669         TUint cropPosition = I64INT(cropPosition64);
-00670 
-00671         // Does cropPosition need adjustment to retain integrity?  (assume not)
-00672 
-00673         TUint dataSize ;  // This will be the size of the data left after cropping.
-00674 
-00675         if ( !aToEnd )
-00676                 {
-00677                 // Shift the data physically
-00678                 // move the data in blocks
-00679                 // Create a CMMFDataBuffer and use CMMFClip to shift the data
-00680                 dataSize = iMaxPos - cropPosition ;
-00681                 if (( dataSize > 0 ) && (aPosition != TTimeIntervalMicroSeconds(0)))
-00682                         {
-00683                         TUint bufSize = ( dataSize < KDefineIOBufferSize ? dataSize : KDefineIOBufferSize ) ; //max bufSize 512
-00684                         CMMFDataBuffer* buffer = CMMFDataBuffer::NewL(bufSize) ;
-00685                         CleanupStack::PushL( buffer ) ;
-00686 
-00687                         TUint rPos = cropPosition ; // read position
-00688                         TUint wPos = 0;
-00689                         TInt dataToShift = ETrue ;
-00690                         while ( dataToShift )
-00691                                 {
-00692                                 STATIC_CAST( CMMFClip*, iClip )->ReadBufferL( buffer, rPos ) ;  // synchronous calls
-00693                                 STATIC_CAST( CMMFClip*, iClip )->WriteBufferL( buffer, wPos ) ;
-00694                                 if ( rPos > iMaxPos ) 
-00695                                         dataToShift = EFalse ;  // past the end:  Done
-00696                                 else
-00697                                         { // shift the pointers
-00698                                         rPos += bufSize ;
-00699                                         wPos += bufSize ;
-00700                                         }
-00701                                 }// while data to shift
-00702                         CleanupStack::PopAndDestroy( ) ; // buffer
-00703                         }// if data to shift
-00704                 }// crop to start
-00705         else // crop to end
-00706                 dataSize = cropPosition ;
-00707 
-00708         iDataSize = dataSize ;
-00709         iMaxPos = dataSize ;
-00710 
-00711         // Do the physical chop
-00712         if ( iClip->DataSinkType() == KUidMmfFileSink )
-00713                 {
-00714                 STATIC_CAST( CMMFFile*, iClip )->FileL().SetSize( iMaxPos ) ;
-00715                 iClipLength = iMaxPos; 
-00716                 }
-00717         }
-00718 
-00719 // get the supported sample rates
-00720 void CMMFRawFormatWrite::GetSupportedSampleRatesL(RArray<TUint>& aSampleRates)
-00721         {
-00722         aSampleRates.Reset();
-00723 
-00724         // Iterate through the valid sample table and append each value to aSampleRates
-00725         TInt i = sizeof(KRawSampleRates) / sizeof(TUint);
-00726         
-00727         while (i--)
-00728                 {
-00729                 User::LeaveIfError(aSampleRates.Append(KRawSampleRates[i]));
-00730                 }
-00731         }
-00732 
-00733 // get the supported channel number options
-00734 void CMMFRawFormatWrite::GetSupportedNumChannelsL(RArray<TUint>& aNumChannels)
-00735         {
-00736         aNumChannels.Reset();
-00737         User::LeaveIfError(aNumChannels.Append(KMono));
-00738         User::LeaveIfError(aNumChannels.Append(KStereo));
-00739         }
-00740 
-00741 // set maximum clip size
-00742 void CMMFRawFormatWrite::SetMaximumClipSize(TInt aBytes)
-00743         {
-00744         iMaximumClipSize = aBytes;
-00745         }
-00746 
-00747 // get the supported codecs
-00748 void CMMFRawFormatWrite::GetSupportedDataTypesL(TMediaId aMediaId, RArray<TFourCC>& aDataTypes)
-00749         {
-00750         if (aMediaId.iMediaType != KUidMediaTypeAudio)
-00751                 User::Leave(KErrNotSupported);
-00752         aDataTypes.Reset();
-00753         User::LeaveIfError(aDataTypes.Append(KMMFFourCCCodePCM16));
-00754         User::LeaveIfError(aDataTypes.Append(KMMFFourCCCodePCM16B));
-00755         User::LeaveIfError(aDataTypes.Append(KMMFFourCCCodePCMU16));
-00756         User::LeaveIfError(aDataTypes.Append(KMMFFourCCCodeIMAD));
-00757         User::LeaveIfError(aDataTypes.Append(KMMFFourCCCodeIMAS));
-00758         }
-00759 
-00760 
-00761 // __________________________________________________________________________
-00762 // Exported proxy for instantiation method resolution
-00763 // Define the interface UIDs
-00764 
-00765 const TImplementationProxy ImplementationTable[] = 
-00766         {
-00767                 IMPLEMENTATION_PROXY_ENTRY(KRawDecoder, CMMFRawFormatRead::NewL),
-00768                 IMPLEMENTATION_PROXY_ENTRY(KRawEncoder, CMMFRawFormatWrite::NewL)
-00769         };
-00770 
-00771 EXPORT_C const TImplementationProxy* ImplementationGroupProxy(TInt& aTableCount)
-00772         {
-00773         aTableCount = sizeof(ImplementationTable) / sizeof(TImplementationProxy);
-00774 
-00775         return ImplementationTable;
-00776         }
-

Generated on Thu Jan 21 10:32:59 2010 for TB10.1 Example Applications by  - -doxygen 1.5.3
- -