// BOSSSND.CPP
//
// Copyright (c) 1998 Symbian Ltd.  All rights reserved.
//

#include "bosssnd.h"

#include <baspyrc.h>
#include <eiksndpy.h>
#include <eikenv.h>
#include <eikappui.h>

//
// CBossDinger
//

class CBossDinger : public CBase, public MSoundPlayerObserver
	{
public:
	void ConstructL(CBossSoundEffects* aSound);
	~CBossDinger();
	// functions
	void Play();
	void Cancel();
private: // from MSoundPlayerObserver
	void PlayComplete(TInt aStatus);	
private:
	CBossSoundEffects* iSound;
	CSoundPlayer* iPlayer;
	};

void CBossDinger::ConstructL(CBossSoundEffects* aSound)
	{
	iSound=aSound;
	iPlayer=CSoundPlayer::NewL(*this, iSound->iDevice);
	}

CBossDinger::~CBossDinger()
	{
	if (iPlayer)
		Cancel();
	delete iPlayer;
	}

const TInt KSoundDriverBufferSize=8000; // 1 second

void CBossDinger::Play()
	{
	//constant declarations
	_LIT(KTextDing,"ding");


	// try to open device
	if (iSound->iDevice.Open()!=KErrNone)
		return;
	// configure for playing sampled sound
	TSoundConfig config;
	iSound->iDevice.Config(config);
	config().iVolume=EVolumeMedium;
	config().iAlawBufferSize=KSoundDriverBufferSize; // needed for sampled sound
	if (iSound->iDevice.SetConfig(config)!=KErrNone)
		{
		iSound->iDevice.Close();
		return;
		}
	TPtrC appName=iSound->Application()->AppFullName();
	TParse parse;
	TPtrC dingName=TPtrC(KTextDing);
	parse.Set(appName, NULL, NULL);
	parse.Set(parse.DriveAndPath(), &dingName, NULL);
	TPtrC fullSoundName=parse.FullName();
	TRAPD(error, iPlayer->PlayFileL(fullSoundName, CEikonEnv::Static()->FsSession()));
	if (error) iSound->iDevice.Close();
	}

void CBossDinger::Cancel()
	{
	iPlayer->Stop();
	}

void CBossDinger::PlayComplete(TInt /* aStatus */)
	{
	iSound->iDevice.Close();
	}

//
// CBossTunePlayer
//

class CBossTunePlayer : public CBase, public MSoundPlayerObserver
	{
public:
	void ConstructL(CBossSoundEffects* aSound);
	~CBossTunePlayer();
	// functions
	void Start();
	void Cancel();
private: // from MSoundPlayerObserver
	void PlayComplete(TInt aStatus);	
private:
	void PlayNextTone();
private:
	CBossSoundEffects* iSound;
	CSoundPlayer* iPlayer;
	TInt iToneCount;
	};

void CBossTunePlayer::ConstructL(CBossSoundEffects* aSound)
	{
	iSound=aSound;
	iPlayer=CSoundPlayer::NewL(*this, iSound->iDevice);
	}

CBossTunePlayer::~CBossTunePlayer()
	{
	if (iPlayer)
		Cancel();
	delete iPlayer;
	}

void CBossTunePlayer::Start()
	{
	// try to open device
	if (iSound->iDevice.Open()!=KErrNone)
		return;
	// configure for playing sampled sound
	TSoundConfig config;
	iSound->iDevice.Config(config);
	config().iVolume=EVolumeMedium;
	if (iSound->iDevice.SetConfig(config)!=KErrNone)
		{
		iSound->iDevice.Close();
		return;
		}
	iToneCount=0;
	PlayNextTone();
	}

// arpeggio of A major
const TInt KMaxTones = 3;
const TInt KBossFrequencies[KMaxTones] = {440 , 557 , 660 };
const TInt KPlayAmplitude = 99; // max permissible

void CBossTunePlayer::PlayNextTone()
	{
	iPlayer->PlayTone(KBossFrequencies[iToneCount],TTimeIntervalMicroSeconds32(100000),
								KPlayAmplitude);
	iToneCount++;
	}

void CBossTunePlayer::PlayComplete(TInt aStatus)
	{
	if (aStatus!=KErrNone || iToneCount==KMaxTones)
		{
		iSound->iDevice.Close();
		return;
		}
	PlayNextTone();
	}

void CBossTunePlayer::Cancel()
	{
	iPlayer->Stop();
	}

//
// CBossCongratulator
//

class CBossCongratulator : public CBase
	{
public:
	void ConstructL(CBossSoundEffects* aSound);
	~CBossCongratulator();
	// functions
	void Play();
	void Cancel();
private:
	CEikAlarmSoundPlayer* iPlayer;
	CBossSoundEffects* iSound;
	};

void CBossCongratulator::ConstructL(CBossSoundEffects* aSound)
	{
	iSound=aSound;
	iPlayer=CEikAlarmSoundPlayer::NewL();
	}

CBossCongratulator::~CBossCongratulator()
	{
	Cancel();
	delete iPlayer;
	}

void CBossCongratulator::Play()
	{
	_LIT(KTextChimes,"Chimes"); //constant declaration
	RFs fs;
	if (fs.Connect()!=KErrNone)
		return;
	iPlayer->Play(fs,TPtrC(KTextChimes));
	fs.Close();
	}

void CBossCongratulator::Cancel()
	{
	iPlayer->Stop();
	}

//
// CBossSoundEffects
//

// construct/destruct

void CBossSoundEffects::ConstructL()
	{
	iDinger=new (ELeave) CBossDinger;
	iDinger->ConstructL(this);
	iTunePlayer=new (ELeave) CBossTunePlayer;
	iTunePlayer->ConstructL(this);
	iCongratulator=new (ELeave) CBossCongratulator;
	iCongratulator->ConstructL(this);
	iApplication=CEikonEnv::Static()->EikAppUi()->Application();
	}

CBossSoundEffects::~CBossSoundEffects()
	{
	CancelSounds();
	delete iCongratulator;
	delete iTunePlayer;
	delete iDinger;
	}

// play things

void CBossSoundEffects::MoveWithPen()
	{
	CancelSounds();
	iDinger->Play();
	}

void CBossSoundEffects::Congratulations()
	{
	CancelSounds();
	iCongratulator->Play();
	}

void CBossSoundEffects::NewDeal()
	{
	CancelSounds();
	iTunePlayer->Start();
	}

// support

void CBossSoundEffects::CancelSounds()
	{
	iDinger->Cancel();
	iTunePlayer->Cancel();
	iCongratulator->Cancel();
	iDevice.Close();
	}

// access

CApaApplication* CBossSoundEffects::Application()
	{	
	return iApplication;
	}
