videoeditorengine/audioeditorengine/src/AudProcessorImpl.cpp
changeset 9 d87d32eab1a9
parent 0 951a5db380a0
equal deleted inserted replaced
0:951a5db380a0 9:d87d32eab1a9
     1 /*
       
     2 * Copyright (c) 2010 Ixonos Plc.
       
     3 * All rights reserved.
       
     4 * This component and the accompanying materials are made available
       
     5 * under the terms of the "Eclipse Public License v1.0"
       
     6 * which accompanies this distribution, and is available
       
     7 * at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     8 *
       
     9 * Initial Contributors:
       
    10 * Nokia Corporation - Initial contribution
       
    11 *
       
    12 * Contributors:
       
    13 * Ixonos Plc
       
    14 *
       
    15 * Description:  
       
    16 *
       
    17 */
       
    18 
       
    19 
       
    20 
       
    21 #include "AudProcessorImpl.h"
       
    22 #include "ProcAMRInFileHandler.h"
       
    23 
       
    24 #include "ProcMP4InFileHandler.h"
       
    25 #include "ProcADTSInFileHandler.h"
       
    26 #include "ProcMP3InFileHandler.h"
       
    27 #include "ProcAWBInFileHandler.h"
       
    28 #include "ProcWAVInFileHandler.h"
       
    29 
       
    30 
       
    31 #include "ProcAMRFrameHandler.h"
       
    32 #include "ProcAACFrameHandler.h"
       
    33 #include "ProcMP3FrameHandler.h"
       
    34 #include "ProcAWBFrameHandler.h"
       
    35 #include "ProcWAVFrameHandler.h"
       
    36 
       
    37 
       
    38 
       
    39 #include "AudCommon.h"
       
    40 #include "ProcTools.h"
       
    41 #include "AudPanic.h"
       
    42 
       
    43 // Debug print macro
       
    44 #if defined _DEBUG 
       
    45 #include <e32svr.h>
       
    46 #define PRINT(x) RDebug::Print x;
       
    47 #else
       
    48 #define PRINT(x)
       
    49 #endif
       
    50 
       
    51 const TInt KTimeEstimateTime = 2000; // 1000 ms
       
    52 
       
    53 CAudProcessorImpl* CAudProcessorImpl::NewL()
       
    54     {
       
    55 
       
    56 
       
    57     CAudProcessorImpl* self = new (ELeave) CAudProcessorImpl();
       
    58     CleanupStack::PushL(self);
       
    59     self->ConstructL();
       
    60     CleanupStack::Pop(self);
       
    61     return self;
       
    62     }
       
    63 
       
    64 CAudProcessorImpl* CAudProcessorImpl::NewLC()
       
    65     {
       
    66     CAudProcessorImpl* self = new (ELeave) CAudProcessorImpl();
       
    67     CleanupStack::PushL(self);
       
    68     self->ConstructL();
       
    69     return self;
       
    70     }
       
    71 
       
    72 CAudProcessorImpl::~CAudProcessorImpl() 
       
    73     {
       
    74     
       
    75 	PRINT((_L("CAudProcessorImpl::~CAudProcessorImpl() in")));
       
    76     TInt a = 0;
       
    77     
       
    78     for (a = 0; a < iInFiles.Count() ; a++) 
       
    79         {
       
    80         delete iInFiles[a];
       
    81         }
       
    82     iInFiles.Reset();
       
    83     
       
    84 	PRINT((_L("CAudProcessorImpl::~CAudProcessorImpl() deleted iInFiles")));
       
    85     delete iWAVFrameHandler; 
       
    86 
       
    87     iClipsWritten.Reset();
       
    88 
       
    89     iProcessingEvents.ResetAndDestroy();
       
    90 
       
    91 	PRINT((_L("CAudProcessorImpl::~CAudProcessorImpl() out")));
       
    92     }
       
    93     
       
    94 
       
    95 void CAudProcessorImpl::ConstructL() 
       
    96     {
       
    97     
       
    98     
       
    99 
       
   100     }
       
   101 
       
   102 CAudProcessorImpl::CAudProcessorImpl() : iInFiles(8), iSong(0), 
       
   103                                             iTimeLeft(0),
       
   104                                             iCurEvent(0),
       
   105                                             iProcessingEvents(8),
       
   106                                             iSongDurationMilliSeconds(0),
       
   107                                             iSongProcessedMilliSeconds(0)
       
   108                                         
       
   109     {
       
   110 
       
   111 
       
   112     }
       
   113 
       
   114 void CAudProcessorImpl::ProcessSongL(const CAudSong* aSong, TInt aRawFrameSize, TBool aGetTimeEstimation) 
       
   115 {
       
   116     PRINT((_L("CAudProcessorImpl::ProcessSongL in")));
       
   117 
       
   118     iGetTimeEstimation = aGetTimeEstimation;
       
   119     
       
   120     iSilenceStarted = EFalse;
       
   121     
       
   122     iSong = aSong;
       
   123     
       
   124     TInt clips = aSong->iClipArray.Count();
       
   125     
       
   126     
       
   127     // bitdepth always 16
       
   128     const TInt KBitDepth = 16;
       
   129     
       
   130     iWAVFrameHandler = CProcWAVFrameHandler::NewL(KBitDepth);
       
   131     
       
   132     // create inFileHandlers for each input clips--->
       
   133     for (TInt a = 0 ; a < clips ; a++) 
       
   134     {
       
   135         if (aSong->iClipArray[a]->Info()->Properties().iFileFormat == EAudFormatAMR) 
       
   136         {
       
   137             PRINT((_L("CAudProcessorImpl::ProcessSongL create AMRNB file handler")));
       
   138             CProcInFileHandler* inFileHandler = 
       
   139                 CProcAMRInFileHandler::NewL(aSong->iClipArray[a]->Info()->FileName(), 
       
   140                 aSong->iClipArray[a]->Info()->FileHandle(), aSong->iClipArray[a],
       
   141                 4096, iSong->OutputFileProperties().iSamplingRate,
       
   142                 iSong->OutputFileProperties().iChannelMode);
       
   143             
       
   144             iInFiles.Insert(inFileHandler, iInFiles.Count());
       
   145             inFileHandler->SetPropertiesL(aSong->iClipArray[a]->Info()->Properties());
       
   146             inFileHandler->SetPriority(aSong->iClipArray[a]->Priority());
       
   147         
       
   148             inFileHandler->SeekCutInFrame();
       
   149             
       
   150             if (IsDecodingRequired(aSong->OutputFileProperties(), 
       
   151                                    aSong->iClipArray[a]->Info()->Properties()))
       
   152                 {
       
   153                 inFileHandler->SetDecodingRequired(ETrue);
       
   154                 }
       
   155                 
       
   156                 
       
   157                 
       
   158             
       
   159         }            
       
   160         else if (aSong->iClipArray[a]->Info()->Properties().iFileFormat == EAudFormatMP4) 
       
   161         {
       
   162             PRINT((_L("CAudProcessorImpl::ProcessSongL create MP4 file handler")));
       
   163             CProcInFileHandler* inFileHandler = 
       
   164                 CProcMP4InFileHandler::NewL(aSong->iClipArray[a]->Info()->FileName(), 
       
   165                 aSong->iClipArray[a]->Info()->FileHandle(),
       
   166                 aSong->iClipArray[a],
       
   167                 4096, iSong->OutputFileProperties().iSamplingRate,
       
   168                 iSong->OutputFileProperties().iChannelMode);
       
   169             
       
   170             iInFiles.Insert(inFileHandler, iInFiles.Count());
       
   171             TAudFileProperties prororo;
       
   172             inFileHandler->GetPropertiesL(&prororo);
       
   173             inFileHandler->SetPriority(aSong->iClipArray[a]->Priority());
       
   174             inFileHandler->SeekCutInFrame();
       
   175             
       
   176             if (IsDecodingRequired(aSong->OutputFileProperties(), 
       
   177                                    aSong->iClipArray[a]->Info()->Properties()))
       
   178                 {
       
   179                 inFileHandler->SetDecodingRequired(ETrue);
       
   180                 }
       
   181             
       
   182             
       
   183             
       
   184         }
       
   185         
       
   186         else if (aSong->iClipArray[a]->Info()->Properties().iFileFormat == EAudFormatAAC_ADTS) 
       
   187         {
       
   188             PRINT((_L("CAudProcessorImpl::ProcessSongL create AAC ADTS file handler")));
       
   189             CProcInFileHandler* inFileHandler = 
       
   190                 CProcADTSInFileHandler::NewL(aSong->iClipArray[a]->Info()->FileName(), 
       
   191                 aSong->iClipArray[a]->Info()->FileHandle(),
       
   192                 aSong->iClipArray[a],
       
   193                 8092, iSong->OutputFileProperties().iSamplingRate,
       
   194                 iSong->OutputFileProperties().iChannelMode);
       
   195             TAudFileProperties pro;
       
   196             
       
   197             iInFiles.Insert(inFileHandler, iInFiles.Count());
       
   198             inFileHandler->GetPropertiesL(&pro);
       
   199             inFileHandler->SetPriority(aSong->iClipArray[a]->Priority());
       
   200             inFileHandler->SeekCutInFrame();
       
   201             
       
   202             if (IsDecodingRequired(aSong->OutputFileProperties(), 
       
   203                                    aSong->iClipArray[a]->Info()->Properties()))
       
   204                 {
       
   205                 inFileHandler->SetDecodingRequired(ETrue);
       
   206                 }
       
   207             
       
   208                 
       
   209             
       
   210         }
       
   211         else if (aSong->iClipArray[a]->Info()->Properties().iFileFormat == EAudFormatMP3) 
       
   212             {
       
   213             PRINT((_L("CAudProcessorImpl::ProcessSongL create MP3 file handler")));
       
   214             CProcInFileHandler* inFileHandler = 
       
   215                 CProcMP3InFileHandler::NewL(aSong->iClipArray[a]->Info()->FileName(), 
       
   216                 aSong->iClipArray[a]->Info()->FileHandle(), 
       
   217                 aSong->iClipArray[a],
       
   218                 4096, iSong->OutputFileProperties().iSamplingRate,
       
   219                 iSong->OutputFileProperties().iChannelMode);
       
   220             
       
   221             iInFiles.Insert(inFileHandler, iInFiles.Count());
       
   222             inFileHandler->SetPropertiesL(aSong->iClipArray[a]->Info()->Properties());
       
   223             inFileHandler->SetPriority(aSong->iClipArray[a]->Priority());
       
   224             inFileHandler->SeekCutInFrame();
       
   225             
       
   226             
       
   227             if (IsDecodingRequired(aSong->OutputFileProperties(), 
       
   228                                    aSong->iClipArray[a]->Info()->Properties()))
       
   229                 {
       
   230                 inFileHandler->SetDecodingRequired(ETrue);
       
   231                 }
       
   232             
       
   233             }
       
   234         else if (aSong->iClipArray[a]->Info()->Properties().iFileFormat == EAudFormatAMRWB) 
       
   235             {
       
   236             PRINT((_L("CAudProcessorImpl::ProcessSongL create AMRWB file handler")));
       
   237             CProcInFileHandler* inFileHandler = 
       
   238                 CProcAWBInFileHandler::NewL(aSong->iClipArray[a]->Info()->FileName(), 
       
   239                 aSong->iClipArray[a]->Info()->FileHandle(), 
       
   240                 aSong->iClipArray[a],
       
   241                 4096, iSong->OutputFileProperties().iSamplingRate,
       
   242                 iSong->OutputFileProperties().iChannelMode);
       
   243             
       
   244             iInFiles.Insert(inFileHandler, iInFiles.Count());
       
   245             inFileHandler->SetPropertiesL(aSong->iClipArray[a]->Info()->Properties());
       
   246             inFileHandler->SetPriority(aSong->iClipArray[a]->Priority());
       
   247             inFileHandler->SeekCutInFrame();
       
   248             
       
   249             if (IsDecodingRequired(aSong->OutputFileProperties(), 
       
   250                                    aSong->iClipArray[a]->Info()->Properties()))
       
   251                 {
       
   252                 inFileHandler->SetDecodingRequired(ETrue);
       
   253                 }
       
   254             
       
   255             }
       
   256         else if (aSong->iClipArray[a]->Info()->Properties().iFileFormat == EAudFormatWAV) 
       
   257             {
       
   258             PRINT((_L("CAudProcessorImpl::ProcessSongL create WAV file handler")));
       
   259             CProcInFileHandler* inFileHandler = 
       
   260                 CProcWAVInFileHandler::NewL(aSong->iClipArray[a]->Info()->FileName(), 
       
   261                 aSong->iClipArray[a]->Info()->FileHandle(), 
       
   262                 aSong->iClipArray[a],
       
   263                 4096, iSong->OutputFileProperties().iSamplingRate,
       
   264                 iSong->OutputFileProperties().iChannelMode);
       
   265             
       
   266             iInFiles.Insert(inFileHandler, iInFiles.Count());
       
   267             inFileHandler->SetPropertiesL(aSong->iClipArray[a]->Info()->Properties());
       
   268             inFileHandler->SetPriority(aSong->iClipArray[a]->Priority());
       
   269             inFileHandler->SeekCutInFrame();
       
   270             
       
   271             if (IsDecodingRequired(aSong->OutputFileProperties(), 
       
   272                                    aSong->iClipArray[a]->Info()->Properties()))
       
   273                 {
       
   274                 inFileHandler->SetDecodingRequired(ETrue);
       
   275                 }
       
   276             
       
   277             }
       
   278         
       
   279         }
       
   280     
       
   281     
       
   282     // find the biggest frame size for mixing buffer
       
   283     TInt maxFrameSize = 0;
       
   284     for (TInt q = 0 ; q < iInFiles.Count() ; q++)
       
   285         {
       
   286         iInFiles[q]->SetRawAudioFrameSize(aRawFrameSize);
       
   287         
       
   288         if (iInFiles[q]->GetDecodedFrameSize() > maxFrameSize)
       
   289             {
       
   290             maxFrameSize = iInFiles[q]->GetDecodedFrameSize();
       
   291             }
       
   292             
       
   293         }
       
   294         
       
   295         
       
   296     
       
   297     GetProcessingEventsL();
       
   298     iProcessingEvents[0]->GetAllIndexes(iClipsWritten);
       
   299     iTimeLeft = iProcessingEvents[1]->iPosition;
       
   300     iCurEvent = 0;
       
   301     
       
   302     
       
   303     if (iGetTimeEstimation)
       
   304         {
       
   305         iTimer.HomeTime();
       
   306         
       
   307         if (iTimeLeft >= KTimeEstimateTime)
       
   308             {
       
   309             iTimeEstimateCoefficient = iTimeLeft/KTimeEstimateTime;
       
   310             
       
   311             iTimeLeft = KTimeEstimateTime;
       
   312             }
       
   313         else
       
   314             {
       
   315             iTimeEstimateCoefficient = 1;
       
   316             }
       
   317         
       
   318         }
       
   319     
       
   320         
       
   321     PRINT((_L("CAudProcessorImpl::ProcessSongL out")));
       
   322     }
       
   323 
       
   324 TBool CAudProcessorImpl::ProcessSyncPieceL(HBufC8*& aFrame, TInt& aProgress,
       
   325                                        TTimeIntervalMicroSeconds& aDuration, TBool& aRaw) 
       
   326 {
       
   327     
       
   328     PRINT((_L("CAudProcessorImpl::ProcessSyncPieceL in")));
       
   329     aDuration = 0;
       
   330     
       
   331     if (iSongProcessedMilliSeconds > iSongDurationMilliSeconds)
       
   332         {
       
   333         // processing is ready
       
   334         StopProcessing();
       
   335         PRINT((_L("CAudProcessorImpl::ProcessSyncPieceL stopped processing 1, out")));
       
   336         return ETrue;
       
   337         
       
   338         }
       
   339     
       
   340     
       
   341     while (iTimeLeft <= 0) 
       
   342         {
       
   343         
       
   344         iCurEvent++;
       
   345     
       
   346         if (iCurEvent >= iProcessingEvents.Count()-1) 
       
   347             {
       
   348 
       
   349             // do we need silence in the end?
       
   350             if (iSongProcessedMilliSeconds < ProcTools::MilliSeconds(iSong->iSongDuration))
       
   351                 {
       
   352                 
       
   353                 if (iGetTimeEstimation)
       
   354                     {
       
   355                     StopProcessing();
       
   356                     PRINT((_L("CAudProcessorImpl::ProcessSyncPieceL stopped processing in time estimate case, out")));
       
   357                     return ETrue;        
       
   358                     
       
   359                     }
       
   360                 
       
   361                
       
   362                 WriteSilenceL(aFrame, aProgress, aDuration, aRaw);
       
   363                 return EFalse;
       
   364                 }
       
   365             // processing is ready
       
   366             StopProcessing();
       
   367             PRINT((_L("CAudProcessorImpl::ProcessSyncPieceL stopped processing 2, out")));
       
   368             return ETrue;
       
   369             }
       
   370         
       
   371         iClipsWritten.Reset();
       
   372         for (TInt tr = 0 ; tr < iProcessingEvents[iCurEvent]->IndexCount() ; tr++)
       
   373             {
       
   374             
       
   375             TInt clipIndex = iProcessingEvents[iCurEvent]->GetIndex(tr);
       
   376 
       
   377             
       
   378             if (clipIndex == -1 || !iSong->Clip(clipIndex, KAllTrackIndices)->Muting())
       
   379                 {
       
   380                 iClipsWritten.Append(iProcessingEvents[iCurEvent]->GetIndex(tr));
       
   381                 
       
   382                 }
       
   383             
       
   384             }
       
   385         iTimeLeft = iProcessingEvents[iCurEvent+1]->iPosition -
       
   386                 iProcessingEvents[iCurEvent]->iPosition;
       
   387                 
       
   388         if (iGetTimeEstimation)
       
   389             {
       
   390             
       
   391             TTime timeNow;
       
   392             timeNow.HomeTime();
       
   393             
       
   394             // how long has it been from the previous event?
       
   395             TTimeIntervalMicroSeconds msFromPrev = timeNow.MicroSecondsFrom(iTimer);
       
   396             
       
   397             iTimeEstimate += msFromPrev.Int64() * iTimeEstimateCoefficient;
       
   398             
       
   399             // set iTimer to home time
       
   400             iTimer.HomeTime();
       
   401             
       
   402             if (iTimeLeft > KTimeEstimateTime)
       
   403                 {
       
   404                 iTimeEstimateCoefficient = iTimeLeft/KTimeEstimateTime;
       
   405                 iTimeLeft = KTimeEstimateTime;
       
   406                 }
       
   407             else
       
   408                 {
       
   409                 iTimeEstimateCoefficient = 1;
       
   410                 }
       
   411             
       
   412             }
       
   413                     
       
   414         }
       
   415     
       
   416     
       
   417     if (iClipsWritten.Count() == 1) 
       
   418         {
       
   419         // if silence
       
   420         WriteSilenceL(aFrame, aProgress, aDuration, aRaw);
       
   421         PRINT((_L("CAudProcessorImpl::ProcessSyncPieceL silence, out")));
       
   422         return EFalse;
       
   423         
       
   424         }
       
   425     else if (iTimeLeft > 0) 
       
   426         {
       
   427 
       
   428 
       
   429         TInt inClipIndex1 = 0;
       
   430         TInt inClipIndex2 = 0;
       
   431         
       
   432         HighestInFilePriority(inClipIndex1, inClipIndex2);
       
   433         
       
   434         CAudClip* clip1 = iSong->iClipArray[iClipsWritten[inClipIndex1]];
       
   435         CAudClip* clip2 = iSong->iClipArray[iClipsWritten[inClipIndex2]];
       
   436         
       
   437         CProcInFileHandler* inHandler1 = iInFiles[iClipsWritten[inClipIndex1]];
       
   438         CProcInFileHandler* inHandler2 = iInFiles[iClipsWritten[inClipIndex2]];
       
   439         
       
   440         
       
   441         TBool writeClip1 = ETrue;
       
   442         TBool writeClip2 = ETrue;
       
   443         
       
   444         if (clip1 == clip2)
       
   445             {
       
   446             writeClip2 = EFalse;
       
   447             }
       
   448         if (clip1->Muting())
       
   449             {
       
   450             writeClip1 = EFalse;
       
   451             }
       
   452         if (clip2->Muting())
       
   453             {
       
   454             writeClip2 = EFalse;
       
   455             }
       
   456 
       
   457 
       
   458         HBufC8* frame1 = 0;
       
   459         HBufC8* frame2 = 0;
       
   460         TInt siz1 = 0;
       
   461         TInt32 tim1 = 0;
       
   462         TInt siz2 = 0;
       
   463         TInt32 tim2 = 0;
       
   464         
       
   465         TBool getFrameRet1 = EFalse;
       
   466         TBool getFrameRet2 = EFalse;
       
   467         // If the clip is muted -> return silence
       
   468         
       
   469         if (!writeClip1 && !writeClip2)
       
   470             {
       
   471             
       
   472             getFrameRet1 = inHandler1->GetSilentAudioFrameL(frame1, siz1, tim1, aRaw);
       
   473             
       
   474             }
       
   475             
       
   476         else if (!writeClip1 && writeClip2)
       
   477             {
       
   478             
       
   479             getFrameRet2 = inHandler2->GetAudioFrameL(frame2, siz2, tim2, aRaw);
       
   480                 
       
   481             }
       
   482         else if (writeClip1 && !writeClip2)
       
   483             {
       
   484             
       
   485             getFrameRet1 = inHandler1->GetAudioFrameL(frame1, siz1, tim1, aRaw);
       
   486                 
       
   487             }
       
   488         else
       
   489             {
       
   490             
       
   491             TBool decodingRequired1 = inHandler1->DecodingRequired();
       
   492             TBool decodingRequired2 = inHandler2->DecodingRequired();
       
   493             
       
   494             // decoding is needed due to mixing
       
   495             inHandler1->SetDecodingRequired(ETrue);
       
   496             inHandler2->SetDecodingRequired(ETrue);
       
   497             
       
   498             getFrameRet1 = inHandler1->GetAudioFrameL(frame1, siz1, tim1, aRaw);
       
   499             
       
   500             // fix to rel2, put frame1 to cleanup stack for the next operation
       
   501             CleanupStack::PushL(frame1);
       
   502             getFrameRet2 = inHandler2->GetAudioFrameL(frame2, siz2, tim2, aRaw);
       
   503             CleanupStack::Pop(); // frame1, will be put to cleanupstack later->
       
   504 
       
   505 
       
   506             inHandler1->SetDecodingRequired(decodingRequired1);
       
   507             inHandler2->SetDecodingRequired(decodingRequired2);
       
   508             
       
   509             }
       
   510             
       
   511         
       
   512         if(!getFrameRet1 && !getFrameRet2)
       
   513             {
       
   514             // no audio frames left -> write silence
       
   515         
       
   516             getFrameRet1 = inHandler1->GetSilentAudioFrameL(frame1, siz1, tim1, aRaw);
       
   517                             
       
   518         }
       
   519         
       
   520         if (frame1 != 0)
       
   521             {
       
   522             CleanupStack::PushL(frame1);
       
   523             }
       
   524         if (frame2 != 0)
       
   525             {
       
   526             CleanupStack::PushL(frame2);
       
   527             }
       
   528             
       
   529 
       
   530         if (getFrameRet1 && getFrameRet2)
       
   531             {
       
   532            
       
   533             // mix the two frames
       
   534             iWAVFrameHandler->MixL(frame1, frame2, aFrame);
       
   535             CleanupStack::PopAndDestroy(frame2);
       
   536             CleanupStack::PopAndDestroy(frame1);
       
   537             aDuration = TUint(tim1*1000);
       
   538             
       
   539             }
       
   540         else if (getFrameRet1 && !getFrameRet2)
       
   541             {
       
   542             aFrame = HBufC8::NewL(frame1->Length());
       
   543             aFrame->Des().Copy(frame1->Des());
       
   544             CleanupStack::PopAndDestroy(frame1);
       
   545             aDuration = TUint(tim1*1000);
       
   546             
       
   547             
       
   548             }
       
   549         else if (!getFrameRet1 && getFrameRet2)
       
   550             {
       
   551             
       
   552             aFrame = HBufC8::NewL(frame2->Length());
       
   553             aFrame->Des().Copy(frame2->Des());
       
   554             CleanupStack::PopAndDestroy(frame2);
       
   555             aDuration = TUint(tim2*1000);
       
   556             
       
   557             }
       
   558         else if (!getFrameRet1 && !getFrameRet2)
       
   559             {
       
   560             
       
   561             // shouldn't get here...
       
   562             
       
   563             User::Leave(KErrGeneral);
       
   564             }
       
   565 
       
   566         
       
   567         iTimeLeft -= ProcTools::MilliSeconds(aDuration);
       
   568         iSongProcessedMilliSeconds += ProcTools::MilliSeconds(aDuration);
       
   569         
       
   570         
       
   571     }
       
   572     
       
   573     if (iSongDurationMilliSeconds > 0)
       
   574         {
       
   575         
       
   576         // update progress
       
   577         aProgress = (iSongProcessedMilliSeconds*100)/iSongDurationMilliSeconds;
       
   578             
       
   579         }
       
   580     PRINT((_L("CAudProcessorImpl::ProcessSyncPieceL out")));
       
   581     return EFalse;
       
   582     
       
   583     }
       
   584 
       
   585 
       
   586 void CAudProcessorImpl::GetAudFilePropertiesL(const TDesC& aFileName, RFile* aFileHandle,
       
   587                                               TAudFileProperties* aProperties) 
       
   588     {
       
   589 
       
   590     PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL in")));
       
   591     
       
   592     
       
   593 
       
   594     PRINT(_L("CAudProcessorImpl::GetAudFilePropertiesL read header from file"));
       
   595     
       
   596     TBuf8<10> fileHeader;
       
   597 
       
   598     if (!aFileHandle)
       
   599     {
       
   600         RFs* fs = new (ELeave) RFs;
       
   601         CleanupStack::PushL(fs);
       
   602         User::LeaveIfError( fs->Connect() );
       
   603     
       
   604         RFile file;    
       
   605         TInt error = file.Open(*fs, aFileName, EFileShareReadersOnly | EFileStream | EFileRead);//EFileShareAny | EFileStream | EFileRead);
       
   606         if (error != KErrNone)
       
   607             {
       
   608             error = file.Open(*fs, aFileName, EFileShareAny | EFileStream | EFileRead);
       
   609             }
       
   610         if (error == KErrNone)
       
   611             {
       
   612             error = file.Read(fileHeader);
       
   613             }
       
   614         file.Close();
       
   615         fs->Close();
       
   616         CleanupStack::PopAndDestroy(fs);
       
   617         User::LeaveIfError(error);
       
   618     } 
       
   619     else
       
   620     {
       
   621         TInt pos = 0;
       
   622         
       
   623         User::LeaveIfError( aFileHandle->Seek(ESeekCurrent, pos) );
       
   624         
       
   625         TInt zero = 0;        
       
   626         User::LeaveIfError( aFileHandle->Seek(ESeekStart, zero) );
       
   627         User::LeaveIfError( aFileHandle->Read(fileHeader) );
       
   628         
       
   629         User::LeaveIfError( aFileHandle->Seek(ESeekStart, pos) );
       
   630     }
       
   631         
       
   632     if (fileHeader.Length() < 10 )  //AMR-WB has 9-byte header, but header-only clips are not accepted. Hence accepting only 10 and more byte clips.
       
   633         {
       
   634         PRINT(_L("CAudProcessorImpl::GetAudFilePropertiesL the file has less than 9 bytes, it must be invalid"));        
       
   635         User::Leave(KErrCorrupt);
       
   636         }
       
   637 
       
   638     PRINT(_L("CAudProcessorImpl::GetAudFilePropertiesL interpret the header"));
       
   639     
       
   640     TParse fp;
       
   641     TFileName name;
       
   642         
       
   643     if (!aFileHandle)
       
   644         fp.Set(aFileName, NULL, NULL);
       
   645     else
       
   646     {
       
   647         User::LeaveIfError( aFileHandle->FullName(name) );
       
   648         fp.Set(name, NULL, NULL);
       
   649     }    
       
   650     
       
   651     if ( fileHeader.Mid(4,4) == _L8("ftyp") )
       
   652             {
       
   653         PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL 3gp/mp4/m4a based on ftyp")));
       
   654         // 3gp/mp4/m4a; extension-based recognition later
       
   655         CProcInFileHandler* inFileHandler = CProcMP4InFileHandler::NewL(aFileName, aFileHandle, 0, 4096);
       
   656         CleanupStack::PushL(inFileHandler);
       
   657         inFileHandler->GetPropertiesL(aProperties);
       
   658         
       
   659         CleanupStack::PopAndDestroy(inFileHandler);
       
   660         }
       
   661     else if (fileHeader.Mid(0,6) == _L8("#!AMR\n"))
       
   662         {
       
   663         PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL AMR-NB based on #!AMR")));
       
   664         // AMR-NB
       
   665         CProcInFileHandler* inFileHandler = CProcAMRInFileHandler::NewL(aFileName, aFileHandle, 0, 4096);
       
   666         CleanupStack::PushL(inFileHandler);
       
   667 
       
   668         inFileHandler->GetPropertiesL(aProperties);    
       
   669         
       
   670         CleanupStack::PopAndDestroy(inFileHandler);
       
   671         
       
   672         }
       
   673     else if (fileHeader.Mid(0,9) == _L8("#!AMR-WB\n")) 
       
   674         {
       
   675         PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL awb based on #!AMR-WB")));
       
   676         CProcInFileHandler* inFileHandler = CProcAWBInFileHandler::NewL(aFileName, aFileHandle,0, 4096);
       
   677         CleanupStack::PushL(inFileHandler);
       
   678         inFileHandler->GetPropertiesL(aProperties);
       
   679 
       
   680         CleanupStack::PopAndDestroy(inFileHandler);
       
   681         }
       
   682     else if (fp.Ext().CompareF(_L(".aac")) == 0) 
       
   683         {
       
   684         PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL aac based on extension")));
       
   685         CProcInFileHandler* inFileHandler = CProcADTSInFileHandler::NewL(aFileName, aFileHandle, 0, 4096);
       
   686         CleanupStack::PushL(inFileHandler);
       
   687         inFileHandler->GetPropertiesL(aProperties);
       
   688 
       
   689         CleanupStack::PopAndDestroy(inFileHandler);
       
   690         }
       
   691     else if (fp.Ext().CompareF(_L(".3gp")) == 0) 
       
   692         {
       
   693         PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL 3gp based on extension")));
       
   694 
       
   695         CProcInFileHandler* inFileHandler = CProcMP4InFileHandler::NewL(aFileName, aFileHandle, 0, 4096);
       
   696         
       
   697         CleanupStack::PushL(inFileHandler);
       
   698         inFileHandler->GetPropertiesL(aProperties);
       
   699         
       
   700         CleanupStack::PopAndDestroy(inFileHandler);
       
   701     
       
   702         }
       
   703 
       
   704     else if (fp.Ext().CompareF(_L(".m4a")) == 0 || 
       
   705              fp.Ext().CompareF(_L(".mp4")) == 0) 
       
   706         {
       
   707         PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL mp4/m4a based on extension")));
       
   708         
       
   709         CProcInFileHandler* inFileHandler = 0;
       
   710 
       
   711         inFileHandler = CProcMP4InFileHandler::NewL(aFileName, aFileHandle, 0, 4096);
       
   712         CleanupStack::PushL(inFileHandler);
       
   713         inFileHandler->GetPropertiesL(aProperties);    
       
   714         CleanupStack::PopAndDestroy(inFileHandler);
       
   715         
       
   716         }
       
   717     else if (fp.Ext().CompareF(_L(".amr")) == 0)
       
   718         {
       
   719         PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL AMR-NB based on extension")));
       
   720         // AMR-NB
       
   721         CProcInFileHandler* inFileHandler = CProcAMRInFileHandler::NewL(aFileName, aFileHandle, 0, 4096);
       
   722         CleanupStack::PushL(inFileHandler);
       
   723 
       
   724         inFileHandler->GetPropertiesL(aProperties);    
       
   725         
       
   726         CleanupStack::PopAndDestroy(inFileHandler);
       
   727         }
       
   728     else if (fp.Ext().CompareF(_L(".awb")) == 0)
       
   729         {
       
   730         PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL awb based on extension")));
       
   731         CProcInFileHandler* inFileHandler = CProcAWBInFileHandler::NewL(aFileName, aFileHandle, 0, 4096);
       
   732         CleanupStack::PushL(inFileHandler);
       
   733         inFileHandler->GetPropertiesL(aProperties);
       
   734 
       
   735         CleanupStack::PopAndDestroy(inFileHandler);
       
   736         }
       
   737     else if (fp.Ext().CompareF(_L(".mp3")) == 0) 
       
   738         {
       
   739         PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL mp3 based on extension")));
       
   740         
       
   741         CProcInFileHandler* inFileHandler = CProcMP3InFileHandler::NewL(aFileName, aFileHandle, 0, 4096);
       
   742         CleanupStack::PushL(inFileHandler);
       
   743         inFileHandler->GetPropertiesL(aProperties);
       
   744         
       
   745         CleanupStack::PopAndDestroy(inFileHandler);
       
   746         }
       
   747     else if (fp.Ext().CompareF(_L(".wav")) == 0) 
       
   748         {
       
   749         PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL wav based on extension")));
       
   750         
       
   751         CProcInFileHandler* inFileHandler = CProcWAVInFileHandler::NewL(aFileName, aFileHandle, 0, 8192);
       
   752         CleanupStack::PushL(inFileHandler);
       
   753         inFileHandler->GetPropertiesL(aProperties);
       
   754         CleanupStack::PopAndDestroy(inFileHandler);
       
   755         }
       
   756     else
       
   757         {
       
   758         User::Leave(KErrNotSupported);
       
   759         }
       
   760     
       
   761     PRINT((_L("CAudProcessorImpl::GetAudFilePropertiesL out")));
       
   762     }
       
   763     
       
   764     
       
   765 TInt64 CAudProcessorImpl::GetFinalTimeEstimate() const
       
   766     {
       
   767     return iTimeEstimate;
       
   768     }
       
   769 
       
   770 void CAudProcessorImpl::GetProcessingEventsL() 
       
   771     {
       
   772 
       
   773     TInt clips = iSong->iClipArray.Count();
       
   774 
       
   775     CProcessingEvent* newEvent = 0;
       
   776     
       
   777     TInt a = 0;
       
   778 
       
   779     // create a new processing event from each clips cutIn and cutOut
       
   780     for (a = 0 ; a < clips ; a++) 
       
   781         {
       
   782         
       
   783         
       
   784         // cut in time:
       
   785         newEvent = CProcessingEvent::NewL();
       
   786         newEvent->iChangedClipIndex = a;
       
   787         newEvent->iCutIn = ETrue;
       
   788         TInt32 startTime = iSong->iClipArray[a]->StartTimeMilliSeconds();
       
   789         TInt32 cutInTime= iSong->iClipArray[a]->CutInTimeMilliSeconds(); 
       
   790         newEvent->iPosition = startTime+cutInTime;
       
   791         iProcessingEvents.Insert(newEvent, 0);
       
   792 
       
   793         // cut out time
       
   794         newEvent = CProcessingEvent::NewL();
       
   795         newEvent->iChangedClipIndex = a;
       
   796         newEvent->iCutIn = EFalse;
       
   797         TInt32 cutOutTime= iSong->iClipArray[a]->CutOutTimeMilliSeconds(); 
       
   798         newEvent->iPosition = startTime+cutOutTime;
       
   799         iProcessingEvents.Insert(newEvent, 0);
       
   800 
       
   801         }
       
   802 
       
   803     
       
   804     
       
   805 
       
   806     // order processing events
       
   807     TLinearOrder<CProcessingEvent> order(CProcessingEvent::Compare);
       
   808     iProcessingEvents.Sort(order);
       
   809 
       
   810     // add a new processing events in the beginning to represent silence
       
   811     // (there is a possibility that the first clip doesn't start from 0 ms)
       
   812     newEvent = CProcessingEvent::NewL();
       
   813     newEvent->iChangedClipIndex = -1;
       
   814     newEvent->InsertIndex(-1);
       
   815     newEvent->iCutIn = ETrue;
       
   816     newEvent->iPosition = 0;
       
   817     iProcessingEvents.Insert(newEvent, 0);
       
   818 
       
   819     // the next for-loop adds indexes of those clips that are supposed to be mixed to
       
   820     // each processing event
       
   821 
       
   822     for (TInt r = 1; r < iProcessingEvents.Count() ; r++) 
       
   823         {
       
   824         
       
   825         
       
   826         for (TInt i = 0 ; i < iProcessingEvents[r-1]->IndexCount() ; i++)
       
   827             {
       
   828             iProcessingEvents[r]->InsertIndex(iProcessingEvents[r-1]->GetIndex(i));
       
   829             }
       
   830 
       
   831         
       
   832         if (iProcessingEvents[r]->iCutIn)
       
   833             {
       
   834             iProcessingEvents[r]->InsertIndex(iProcessingEvents[r]->iChangedClipIndex);
       
   835             }
       
   836         else
       
   837             {
       
   838 
       
   839             TInt oldIndexInArray = iProcessingEvents[r]->FindIndex(iProcessingEvents[r]->iChangedClipIndex);
       
   840 
       
   841             if (oldIndexInArray >= 0 && oldIndexInArray < iProcessingEvents[r]->IndexCount())
       
   842                 {
       
   843                 iProcessingEvents[r]->RemoveIndex(oldIndexInArray);
       
   844                 }
       
   845 
       
   846             }
       
   847 
       
   848         }
       
   849                 
       
   850     //iSongDurationMilliSeconds = (iSong->iSongDuration.Int64()/1000);
       
   851     iSongDurationMilliSeconds = ProcTools::MilliSeconds(iSong->iSongDuration);
       
   852     
       
   853     //iProcessingEvents[iProcessingEvents.Count()-1]->iPosition;
       
   854 
       
   855 
       
   856     }
       
   857 
       
   858 
       
   859 
       
   860 
       
   861 TBool CAudProcessorImpl::StopProcessing()
       
   862     {
       
   863 
       
   864     if (iGetTimeEstimation)
       
   865         {
       
   866         
       
   867         TTime timeNow;
       
   868         timeNow.HomeTime();
       
   869         
       
   870         // how long has it been from the previous event?
       
   871         TTimeIntervalMicroSeconds msFromPrev = timeNow.MicroSecondsFrom(iTimer);
       
   872         
       
   873         iTimeEstimate += msFromPrev.Int64() * iTimeEstimateCoefficient;
       
   874         }
       
   875 
       
   876 
       
   877     iProcessingEvents.ResetAndDestroy();
       
   878     iInFiles.ResetAndDestroy();
       
   879 
       
   880     return ETrue;
       
   881     }
       
   882 
       
   883 TBool CAudProcessorImpl::WriteSilenceL(HBufC8*& aFrame, TInt& aProgress,
       
   884                                        TTimeIntervalMicroSeconds& aDuration, TBool& aRaw)                                
       
   885     {
       
   886     HBufC8* silentFrame = 0;
       
   887     TInt silSize = 0;
       
   888     TInt32 silDur = 0;
       
   889 
       
   890     if (iSong->iProperties->iAudioType == EAudAAC_MPEG4 && 
       
   891         iSong->iProperties->iChannelMode == EAudSingleChannel)
       
   892         {
       
   893         
       
   894         aDuration = ((1024*1000)/(iSong->iProperties->iSamplingRate))*1000;
       
   895         
       
   896         silDur = ProcTools::MilliSeconds(aDuration);
       
   897         
       
   898         aFrame = HBufC8::NewL(KSilentMonoAACFrameLenght);
       
   899         aFrame->Des().Append(KSilentMonoAACFrame, KSilentMonoAACFrameLenght);
       
   900         
       
   901         aRaw = EFalse;
       
   902 
       
   903         }
       
   904     else if (iSong->iProperties->iAudioType == EAudAAC_MPEG4 && 
       
   905              iSong->iProperties->iChannelMode == EAudStereo)
       
   906         {
       
   907 
       
   908         aDuration = ((1024*1000)/(iSong->iProperties->iSamplingRate))*1000;
       
   909         
       
   910         silDur = ProcTools::MilliSeconds(aDuration);
       
   911         
       
   912         aFrame = HBufC8::NewL(KSilentStereoAACFrameLenght);    
       
   913         aFrame->Des().Append(KSilentStereoAACFrame, KSilentStereoAACFrameLenght);
       
   914         
       
   915         aRaw = EFalse;
       
   916 
       
   917         }
       
   918     else
       
   919         {
       
   920         iInFiles[0]->GetSilentAudioFrameL(silentFrame, silSize, silDur, aRaw);
       
   921     
       
   922         aFrame= silentFrame;
       
   923         aDuration = TUint(silDur*1000);
       
   924         
       
   925         }
       
   926     
       
   927     iSongProcessedMilliSeconds += silDur;
       
   928     iTimeLeft -= silDur;
       
   929     
       
   930     if (iSongDurationMilliSeconds > 0)
       
   931         {
       
   932         aProgress = (iSongProcessedMilliSeconds*100)/iSongDurationMilliSeconds;    
       
   933         }
       
   934         
       
   935     return ETrue;
       
   936     }
       
   937 
       
   938 
       
   939 TBool CAudProcessorImpl::HighestInFilePriority(TInt& aFirst, TInt& aSecond)
       
   940     {
       
   941     
       
   942     aFirst = 1;
       
   943     aSecond = 1;
       
   944     
       
   945     TInt highest = 1;
       
   946     
       
   947     TInt secondHighest = 1;
       
   948     
       
   949  
       
   950     for (TInt a = 1 ; a < iClipsWritten.Count() ; a++)
       
   951         {
       
   952         if (iInFiles[iClipsWritten[a]]->Priority() >= highest)
       
   953             {
       
   954             
       
   955             // highest priority
       
   956             aFirst = a;
       
   957             highest = iInFiles[iClipsWritten[a]]->Priority();
       
   958             
       
   959             }
       
   960         else if (iInFiles[iClipsWritten[a]]->Priority() >= secondHighest)
       
   961             {
       
   962             aSecond = a;
       
   963             secondHighest = iInFiles[iClipsWritten[a]]->Priority();
       
   964             }
       
   965  
       
   966         }
       
   967         
       
   968  
       
   969     return ETrue;
       
   970     }
       
   971     
       
   972 TBool CAudProcessorImpl::IsDecodingRequired(const TAudFileProperties& prop1, 
       
   973                                             const TAudFileProperties& prop2)
       
   974     {
       
   975     
       
   976     TBool decodingNeeded = EFalse;
       
   977     TAudFileProperties tmpProp1 = prop1;
       
   978     TAudFileProperties tmpProp2 = prop2;
       
   979     
       
   980  
       
   981     if (tmpProp1.iAudioType != 
       
   982         tmpProp2.iAudioType ||
       
   983         tmpProp1.iSamplingRate != 
       
   984         tmpProp2.iSamplingRate ||
       
   985         tmpProp1.iChannelMode != 
       
   986         tmpProp2.iChannelMode)
       
   987         {
       
   988         decodingNeeded = ETrue;
       
   989         }
       
   990         
       
   991     return decodingNeeded;
       
   992     
       
   993     
       
   994     }
       
   995 
       
   996     
       
   997