📄 oggplay.cpp
字号:
/*
* Copyright (c) 2003 L. H. Wilden.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#include <OggOs.h>
#include <e32std.h>
#include <hal.h>
#if defined(SERIES60)
#include <akndialog.h> // for about
#include <aknnotewrappers.h>
_LIT(KTsyName,"phonetsy.tsy");
#endif
#if defined(SERIES80)
#include <eikEnv.h>
#include "OggDialogsS80.h"
_LIT(KTsyName,"phonetsy.tsy");
#endif
#if defined(UIQ)
#include <quartzkeys.h> // EStdQuartzKeyConfirm etc.
_LIT(KTsyName,"erigsm.tsy");
#endif
#include <eiklabel.h> // CEikLabel
#include <gulicon.h> // CGulIcon
#include <apgwgnam.h> // CApaWindowGroupName
#include <eikmenup.h> // CEikMenuPane
#include <barsread.h>
#include "OggControls.h"
#if defined(PLUGIN_SYSTEM)
#include "OggPluginAdaptor.h"
#else
#include "OggTremor.h"
#endif
#include "OggPlayAppView.h"
#include "OggDialogs.h"
#include "OggLog.h"
#include "OggFilesSearchDialogs.h"
#if defined(UIQ)
const TInt KThreadPriority = EPriorityAbsoluteHigh;
#else
const TInt KThreadPriority = EPriorityAbsoluteBackground;
#endif
// Application entry point
#if defined(SERIES60V3)
#include <eikstart.h>
static CApaApplication* NewApplication()
{
return new COggPlayApplication;
}
GLDEF_C TInt E32Main()
{
return EikStart::RunApplication(NewApplication);
}
#else
EXPORT_C CApaApplication* NewApplication()
{
return new COggPlayApplication;
}
GLDEF_C TInt E32Dll(TDllReason)
{
return KErrNone;
}
#endif
CApaDocument* COggPlayApplication::CreateDocumentL()
{
return new (ELeave)COggPlayDocument(*this);
}
TUid COggPlayApplication::AppDllUid() const
{
TUid id = { KOggPlayApplicationUidValue };
return id;
}
// COggPlayDocument class
CFileStore* COggPlayDocument::OpenFileL(TBool /*aDoOpen*/,const TDesC& aFilename, RFs& /*aFs*/)
{
iAppUi->OpenFileL(aFilename);
return NULL;
}
#if defined(SERIES60)
COggPlayDocument::COggPlayDocument(CAknApplication& aApp)
#else
COggPlayDocument::COggPlayDocument(CEikApplication& aApp)
#endif
: CEikDocument(aApp)
{
}
CEikAppUi* COggPlayDocument::CreateAppUiL()
{
CEikAppUi* appUi = new (ELeave) COggPlayAppUi;
return appUi;
}
void ROggPlayListStack::Reset()
{
iPlayListArray.Reset();
iPlayingIdxArray.Reset();
}
TInt ROggPlayListStack::Push(const TOggPlayListStackEntry& aPlayListStackEntry)
{
TInt err = iPlayListArray.Append(aPlayListStackEntry.iPlayList);
if (err != KErrNone)
return err;
err = iPlayingIdxArray.Append(aPlayListStackEntry.iPlayingIdx);
if (err != KErrNone)
iPlayListArray.Remove(iPlayListArray.Count()-1);
return err;
}
void ROggPlayListStack::Pop(TOggPlayListStackEntry& aPlayListStackEntry)
{
aPlayListStackEntry.iPlayList = NULL;
aPlayListStackEntry.iPlayingIdx = -1;
TInt lastIndex = iPlayListArray.Count()-1;
if (lastIndex>=0)
{
aPlayListStackEntry.iPlayList = iPlayListArray[lastIndex];
aPlayListStackEntry.iPlayingIdx = iPlayingIdxArray[lastIndex];
iPlayListArray.Remove(lastIndex);
iPlayingIdxArray.Remove(lastIndex);
}
}
void ROggPlayListStack::Close()
{
iPlayListArray.Close();
iPlayingIdxArray.Close();
}
// COggActive class
#ifdef MONITOR_TELEPHONE_LINE
COggActive::COggActive()
{
}
void COggActive::ConstructL(COggPlayAppUi* theAppUi)
{
iAppUi = theAppUi;
#if !defined(__WINS__)
// The destructor panics in emulator
iServer= new (ELeave) RTelServer;
User::LeaveIfError(iServer->Connect());
User::LeaveIfError(iServer->LoadPhoneModule(KTsyName));
TInt nPhones;
User::LeaveIfError(iServer->EnumeratePhones(nPhones));
RTelServer::TPhoneInfo pInfo;
User::LeaveIfError(iServer->GetPhoneInfo(0, pInfo));
iPhone= new (ELeave) RPhone;
User::LeaveIfError(iPhone->Open(*iServer, pInfo.iName));
TInt nofLines;
User::LeaveIfError(iPhone->EnumerateLines(nofLines));
iLine= new (ELeave) RLine;
#if defined(UIQ)
iLineToMonitor = 0;
iLineCallsReportedAtIdle = 0;
#else
// Series 60 1.X reports 3 lines 0='Fax' 1='Data' and 2='VoiceLine1'
// Series 60 2.0 reports 4 lines 0='Voice1' 1='Voice2' 2='Data' 3='Fax'
// (and 'VoiceLine1' reports '1' in EnumerateCall() when in idle ?!?)
TInt linesToTest = nofLines;
// S60: Why is 'iLineCallsReportedAtIdle' not '0' at idle as
// should be expected ??? The voice line reports '1' ???
RPhone::TLineInfo lInfo;
for (TInt i=0; i<linesToTest; i++)
{
User::LeaveIfError(iPhone->GetLineInfo(i, lInfo));
// Test code, left here because this is likely to change between
// phone and it's nice to keep it in traces.
User::LeaveIfError(iLine->Open(*iPhone, lInfo.iName));
TInt nCalls=-1;
iLine->EnumerateCall(nCalls);
iLine->Close();
TRACEF(COggLog::VA(_L("Line%d:%S=%d"), i, &lInfo.iName, nCalls ));
// End of test code
if (lInfo.iName.Match(_L("Voice*1")) != KErrNotFound)
{
iLineToMonitor = i;
iLineCallsReportedAtIdle = nCalls;
}
}
#endif
#endif
#if defined(SERIES60) || defined(SERIES80)
iTimer = CPeriodic::New(CActive::EPriorityStandard);
iCallBack = new (ELeave) TCallBack(COggActive::CallBack, this);
#endif
}
TInt COggActive::CallBack(TAny* aPtr)
{
COggActive* self= (COggActive*) aPtr;
TInt callBackAgain = self->CallBack();
if (!callBackAgain)
self->CancelCallBack();
return callBackAgain;
}
TInt COggActive::CallBack()
{
iAppUi->NotifyUpdate();
#if !defined(__WINS__)
RPhone::TLineInfo lInfo;
iPhone->GetLineInfo(iLineToMonitor, lInfo);
iLine->Open(*iPhone, lInfo.iName);
TInt nCalls=0;
iLine->EnumerateCall(nCalls);
iLine->Close();
TBool isRinging = nCalls > iLineCallsReportedAtIdle;
TBool isIdle = nCalls == iLineCallsReportedAtIdle;
if (isRinging && !iInterrupted)
{
// the phone is ringing or someone is making a call, pause the music if any
if (iAppUi->iOggPlayback->State()==CAbsPlayback::EPlaying)
{
TRACEF(_L("GSM is active"));
iInterrupted= ETrue;
iAppUi->HandleCommandL(EOggPauseResume);
// Continue monitoring
return 1;
}
}
else if (iInterrupted)
{
// our music was interrupted by a phone call, now what
if (isIdle)
{
TRACEF(_L("GSM is idle"));
// okay, the phone is idle again, let's continue with the music
iInterrupted= EFalse;
if (iAppUi->iOggPlayback->State()==CAbsPlayback::EPaused)
iAppUi->HandleCommandL(EOggPauseResume);
}
}
#endif
// Continue monitoring if we have been interrupted or if we are now playing
return iInterrupted || (iAppUi->iOggPlayback->State()==CAbsPlayback::EPlaying) || iAppUi->iTryResume;
}
void COggActive::IssueRequest()
{
#if defined(SERIES60) || defined(SERIES80)
iTimer->Cancel();
iTimer->Start(TTimeIntervalMicroSeconds32(1000000), TTimeIntervalMicroSeconds32(1000000), *iCallBack);
#endif
}
void COggActive::CancelCallBack()
{
iTimer->Cancel();
}
COggActive::~COggActive()
{
if (iLine)
{
iLine->Close();
delete iLine;
}
if (iPhone)
{
iPhone->Close();
delete iPhone;
}
if (iServer)
{
iServer->Close();
delete iServer;
}
#if defined(SERIES60) || defined(SERIES80)
if (iTimer)
{
iTimer->Cancel();
delete iTimer;
}
delete iCallBack;
#endif
}
#endif // MONITOR_TELEPHONE_LINE
COggStartUpAO::COggStartUpAO(COggPlayAppUi& aAppUi)
: CActive(EPriorityHigh), iAppUi(aAppUi)
{
CActiveScheduler::Add(this);
}
COggStartUpAO::~COggStartUpAO()
{
}
void COggStartUpAO::NextStartUpState()
{
TRequestStatus* status = &iStatus;
User::RequestComplete(status, KErrNone);
SetActive();
}
void COggStartUpAO::RunL()
{
iAppUi.NextStartUpState();
}
void COggStartUpAO::DoCancel()
{
}
// App UI class, COggPlayAppUi
COggPlayAppUi::COggPlayAppUi()
: iViewBy(ETop)
{
}
_LIT(KLogFile,"C:\\Logs\\OggPlay\\OggPlay.log");
void COggPlayAppUi::ConstructL()
{
// Delete the existing log
iCoeEnv->FsSession().Delete(KLogFile);
// Trace that we have at least reached the start of the code
TRACEF(_L("COggPlayAppUi::ConstructL()"));
#if defined(SERIES60V3)
BaseConstructL(EAknEnableSkin);
#else
BaseConstructL();
#endif
// Construct the splash view
TRACEF(_L("COggPlayAppUi::ConstructL(): Construct Splash views..."));
iSplashFOView = new(ELeave) COggSplashView(KOggPlayUidSplashFOView);
iSplashFOView->ConstructL();
RegisterViewL(*iSplashFOView);
#if defined(UIQ) && !defined(MOTOROLA)
iSplashFCView = new(ELeave) COggSplashView(KOggPlayUidSplashFCView);
iSplashFCView->ConstructL();
RegisterViewL(*iSplashFCView);
#endif
// Construct required startup objects
TRACEF(_L("COggPlayAppUi::ConstructL(): Construct StartUp objects..."));
iStartUpAO = new(ELeave) COggStartUpAO(*this);
#if defined(SERIES60)
iStartUpErrorDlg = new(ELeave) CAknErrorNote(ETrue);
#endif
iEikonEnv->ReadResource(iStartUpErrorTxt1, R_OGG_ERROR_31);
iEikonEnv->ReadResource(iStartUpErrorTxt2, R_OGG_ERROR_32);
// Wait for the view server to activate the splash
// view before completing the startup process
iStartUpState = EActivateSplashView;
}
void COggPlayAppUi::NextStartUpState(TInt aErr)
{
if (iStartUpState == EStartUpFailed)
return;
if (aErr == KErrNone)
iStartUpAO->NextStartUpState();
else
StartUpError(aErr);
}
void COggPlayAppUi::NextStartUpState()
{
switch(iStartUpState)
{
case EActivateSplashView:
iStartUpState = EStartOggPlay;
StartOggPlay();
break;
case EStartOggPlay:
iStartUpState = EActivateStartUpView;
ActivateStartUpView();
break;
case EActivateStartUpView:
iStartUpState = EPostConstruct;
PostConstruct();
break;
case EPostConstruct:
iStartUpState = EStartUpComplete;
// Delete the startup AO, we have finished with it now
delete iStartUpAO;
iStartUpAO = NULL;
#if defined(SERIES60)
// Delete the startup error dialog, we have finished with that too
delete iStartUpErrorDlg;
iStartUpErrorDlg = NULL;
#endif
break;
default:
User::Panic(_L("COPAUi::NSUS"), 0);
break;
}
}
void COggPlayAppUi::StartOggPlay()
{
TRAPD(err, StartOggPlayL());
#if defined(OS70S)
NextStartUpState(err);
#else
if (err != KErrNone)
StartUpError(err);
#endif
}
void COggPlayAppUi::ActivateStartUpView()
{
TRAPD(err, ActivateStartUpViewL());
NextStartUpState(err);
}
void COggPlayAppUi::ActivateStartUpViewL()
{
iFOView = new(ELeave) COggFOView(*iAppView);
RegisterViewL(*iFOView);
#if defined(SERIES60)
iSettingsView = new(ELeave) COggSettingsView(*iAppView, KOggPlayUidSettingsView);
RegisterViewL(*iSettingsView);
iUserHotkeysView = new(ELeave) COggUserHotkeysView(*iAppView);
RegisterViewL(*iUserHotkeysView);
#if defined(PLUGIN_SYSTEM)
iCodecSelectionView = new(ELeave) COggPluginSettingsView(*iAppView);
RegisterViewL(*iCodecSelectionView);
#endif
#if defined(MULTI_THREAD_PLAYBACK)
iPlaybackOptionsView = new(ELeave) COggPlaybackOptionsView(*iAppView, KOggPlayUidPlaybackOptionsView);
RegisterViewL(*iPlaybackOptionsView);
#endif
iAlarmSettingsView = new(ELeave) COggAlarmSettingsView(*iAppView, KOggPlayUidAlarmSettingsView);
RegisterViewL(*iAlarmSettingsView);
#elif defined(UIQ)
iFCView = new(ELeave) COggFCView(*iAppView);
RegisterViewL(*iFCView);
#endif
ActivateOggViewL();
}
void COggPlayAppUi::StartUpError(TInt aErr)
{
// Format a string with the state and error code
TBuf<128> errorTxt;
errorTxt.Format(iStartUpErrorTxt2, iStartUpState, aErr);
// Mark that the startup has failed
iStartUpState = EStartUpFailed;
// Display an error dialog and exit
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -