From fd6ace361c06d7031575c9b12887df81beb46808 Mon Sep 17 00:00:00 2001 From: Chris Apers Date: Tue, 23 Sep 2003 15:49:33 +0000 Subject: CD Audio track support via MP3 on PalmOS svn-id: r10373 --- backends/PalmOS/Src/cd_msa.cpp | 312 +++++++++++++++++++++++++++++++++++++++++ backends/PalmOS/Src/cd_msa.h | 62 ++++++++ backends/PalmOS/Src/cdaudio.h | 56 ++++++++ 3 files changed, 430 insertions(+) create mode 100644 backends/PalmOS/Src/cd_msa.cpp create mode 100644 backends/PalmOS/Src/cd_msa.h create mode 100644 backends/PalmOS/Src/cdaudio.h (limited to 'backends/PalmOS') diff --git a/backends/PalmOS/Src/cd_msa.cpp b/backends/PalmOS/Src/cd_msa.cpp new file mode 100644 index 0000000000..4dd5da5c42 --- /dev/null +++ b/backends/PalmOS/Src/cd_msa.cpp @@ -0,0 +1,312 @@ +/* ScummVM - Scumm Interpreter + * Copyright (C) 2001 Ludvig Strigeus + * Copyright (C) 2001-2003 The ScummVM project + * + * 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. + * + * $Header$ + * + */ +#include + +#include "scumm.h" +#include "common/system.h" +#include "cd_msa.h" +#include "start.h" // for appFileCreator + +MsaCDPlayer::MsaCDPlayer(OSystem *sys) { + _sys = sys; + _msaRefNum = sysInvalidRefNum; +} + +bool MsaCDPlayer::init() { + SonySysFtrSysInfoP sonySysFtrSysInfoP; + Err error = errNone; + + if (!(error = FtrGet(sonySysFtrCreator, sonySysFtrNumSysInfoP, (UInt32*)&sonySysFtrSysInfoP))) { + // not found with audio adapter ?! + //if (sonySysFtrSysInfoP->libr & sonySysFtrSysInfoLibrMsa) { + if ((error = SysLibFind(sonySysLibNameMsa, &_msaRefNum))) + if (error == sysErrLibNotFound) + error = SysLibLoad(sonySysFileTMsaLib, sonySysFileCMsaLib, &_msaRefNum); + + if (!error) { +// Char buf[100]; +// StrPrintF(buf,"MSA refNum %ld, Try to open lib ...", refNum); +// FrmCustomAlert(1000,buf,0,0); + MsaLibClose(_msaRefNum, msaLibOpenModeAlbum); // close the lib if we previously let it open (?) Need to add Notify for sonySysNotifyMsaEnforceOpenEvent just in case ... + error = MsaLibOpen(_msaRefNum, msaLibOpenModeAlbum); +/* switch (error) { + case msaErrAlreadyOpen: + FrmCustomAlert(1000,"msaErrAlreadyOpen",0,0); + break; + case msaErrMemory: + FrmCustomAlert(1000,"msaErrMemory",0,0); + break; + case msaErrDifferentMode: + FrmCustomAlert(1000,"msaErrDifferentMode",0,0); + break; + case expErrCardNotPresent: + FrmCustomAlert(1000,"expErrCardNotPresent",0,0); + break; + } +*/ + if (error == msaErrAlreadyOpen) + error = MsaLibEnforceOpen(_msaRefNum, msaLibOpenModeAlbum, appFileCreator); + + error = (error != msaErrStillOpen) ? error : errNone; + } + //} + } + + if (error) + _msaRefNum = sysInvalidRefNum; + + _isInitialized = (_msaRefNum != sysInvalidRefNum); + initInternal(); + return _isInitialized; +} + +void MsaCDPlayer::initInternal() { + if (!_isInitialized) + return; + + // Beeeeeep !!! +// MsaOutCapabilityType capability; +// MsaOutInit(_msaRefNum); +// MsaOutGetCapability(_msaRefNum, &capability); +// MsaOutSetBeepLevel(_msaRefNum, capability.beepMaxLebel); +// MsaOutStartBeep(_msaRefNum, 1000, msaOutBeepPatternOK); + + Err e; + UInt32 dummy, albumIterater = albumIteratorStart; + Char nameP[256]; + MemSet(&_msaAlbum, sizeof(_msaAlbum), 0); + _msaAlbum.maskflag = msa_INF_ALBUM; + _msaAlbum.code = msa_LANG_CODE_ASCII; + _msaAlbum.nameP = nameP; + _msaAlbum.fileNameLength = 256; + + e = MsaAlbumEnumerate(_msaRefNum, &albumIterater, &_msaAlbum); +// if (e) doErr(e, "MsaAlbumEnumerate"); + e = MsaSetAlbum(_msaRefNum, _msaAlbum.albumRefNum, &dummy); +// if (e) doErr(e, "MsaSetAlbum"); +// e = MsaGetPBRate(_msaRefNum, &_msaPBRate); +// if (e) doErr(e, "MsaGetPBRate"); + + // TODO : use RMC to control volume + // move this to setSolume + MsaOutSetVolume(_msaRefNum, 20, 20); +} + +void MsaCDPlayer::release() { + if (_isInitialized) { + if (_msaRefNum != sysInvalidRefNum) { + // stop the current track if any (needed if we use enforce open to prevent the track to play after exit) + MsaStop(_msaRefNum, true); + MsaLibClose(_msaRefNum, msaLibOpenModeAlbum); + } + } + + // self delete + delete this; +} + +bool MsaCDPlayer::poll() { + if (!_isInitialized) + return false; + + MsaPBStatus pb; + MsaGetPBStatus(_msaRefNum, &pb); + return (_msaLoops != 0 && (_sys->get_msecs() < _msaEndTime || pb.status != msa_STOPSTATUS)); +} + +void MsaCDPlayer::update() { + if (!_isInitialized) + return; + + // stop replay upon request of stop_cdrom() + if (_msaStopTime != 0 && _sys->get_msecs() >= _msaStopTime) { + MsaStop(_msaRefNum, true); + _msaLoops = 0; + _msaStopTime = 0; + _msaEndTime = 0; + return; + } + + // not fully played + if (_sys->get_msecs() < _msaEndTime) + return; + + if (_msaLoops == 0) { + MsaStop(_msaRefNum, true); + return; + } + + // track ends and last play, force stop if still playing + if (_msaLoops != 1) { + MsaPBStatus pb; + MsaGetPBStatus(_msaRefNum, &pb); + if (pb.status != msa_STOPSTATUS) { +// debug(0,"Stop It now"); + MsaStop(_msaRefNum, true); + return; + } + } + + // loop again ? + if (_msaLoops > 0) { + MsaStop(_msaRefNum, true); // stop if loop=0 + _msaLoops--; + } + + // loop if needed + if (_msaLoops != 0) { + MsaStop(_msaRefNum, true); +// debug(0,"Next loop : %d", _msaLoops); + + _msaEndTime = _sys->get_msecs() + _msaTrackLength; + if (_msaStartFrame == 0 && _msaEndFrame == 0) + MsaPlay(_msaRefNum, _msaTrack, 0, msa_PBRATE_SP); + else + MsaPlay(_msaRefNum, _msaTrack, _msaTrackStart, msa_PBRATE_SP); + } +} + +static void doErr(Err e, const Char *msg) { + Char err[100]; + StrPrintF(err, "%ld : " , e); + StrCat(err,msg); + FrmCustomAlert(1000,err,0,0); +} + +void MsaCDPlayer::stop() { /* Stop CD Audio in 1/10th of a second */ + if (!_isInitialized) + return; + + _msaStopTime = _sys->get_msecs() + 100; + _msaLoops = 0; + return; +} + +// frames are 1/75 sec +#define CD_FPS 75 +#define TO_MSECS(frame) ((UInt32)((frame) * 1000 / CD_FPS)) +// consider frame at 1/1000 sec +#define TO_SEC(msecs) ((UInt16)((msecs) / 1000)) +#define TO_MIN(msecs) ((UInt16)(TO_SEC((msecs)) / 60)) +#define FROM_MIN(mins) ((UInt32)((mins) * 60 * 1000)) +#define FROM_SEC(secs) ((UInt32)((secs) * 1000)) + +#define FRAMES_TO_MSF(f, M,S,F) { \ + int value = f; \ + *(F) = value%CD_FPS; \ + value /= CD_FPS; \ + *(S) = value%60; \ + value /= 60; \ + *(M) = value; \ +} + +void MsaCDPlayer::play(int track, int num_loops, int start_frame, int duration) { + if (!_isInitialized) + return; + + if (!num_loops && !start_frame) + return; + + Err e; + +/* + if (start_frame > 0) + start_frame += CD_FPS >> 1; +*/ + if (duration > 0) + duration += 5; + +// debug(0, ">> Request : track %d / loops : %d / start : %d / duration : %d", track, num_loops, start_frame, duration); + + _msaLoops = num_loops; + _msaTrack = track + gVars->music.firstTrack - 1; // first track >= 1 ?, not 0 (0=album) + _msaStartFrame = TO_MSECS(start_frame); + _msaEndFrame = TO_MSECS(duration); + +// debug(0, ">> To MSECS : start : %d / duration : %d", _msaStartFrame, _msaEndFrame); + + // if gVars->MP3 audio track +// Err e; + MemHandle trackH; + + // stop current play if any + MsaStop(_msaRefNum, true); + // retreive track infos + e = MsaGetTrackInfo(_msaRefNum, _msaTrack, 0, msa_LANG_CODE_ASCII, &trackH); +// if (e) doErr(e, "MsaGetTrackInfo"); + // track exists + if (!e && trackH) { + MsaTime tTime; + UInt32 SU, fullLength; + MsaTrackInfo *tiP; + + // FIXME : this enable MsaSuToTime to return the right value + MsaPlay(_msaRefNum, _msaTrack, 0, msa_PBRATE_SP); + MsaStop(_msaRefNum, true); + + tiP = (MsaTrackInfo *)MemHandleLock(trackH); + MsaSuToTime(_msaRefNum, tiP->totalsu, &tTime); + SU = tiP->totalsu; + MemPtrUnlock(tiP); + MemHandleFree(trackH); + +// debug(0, ">> SU of track : %d (%d%:%d.%d)", SU, tTime.minute, tTime.second, tTime.frame); + +// Char buf[200]; +// StrPrintF(buf,"Track : %ld - %ld%:%ld.%ld (%ld)", track, tTime.minute, tTime.second, tTime.frame, SU); +// FrmCustomAlert(1000,buf,0,0); + + _msaStopTime = 0; + fullLength = FROM_MIN(tTime.minute) + FROM_SEC(tTime.second) + tTime.frame; + +// debug(0, ">> Full length : %d", fullLength); + + if (_msaEndFrame > 0) { + _msaTrackLength = _msaEndFrame; + } else if (_msaStartFrame > 0) { + _msaTrackLength = fullLength; + _msaTrackLength -= _msaStartFrame; + } else { + _msaTrackLength = fullLength; + } + + // try to play the track + if (start_frame == 0 && duration == 0) { + MsaPlay(_msaRefNum, _msaTrack, 0, msa_PBRATE_SP); + } else { + // FIXME : MsaTimeToSu doesn't work ... (may work with previous FIXME) + _msaTrackStart = (UInt32) ((float)(_msaStartFrame) / ((float)fullLength / (float)SU)); +// debug(0, ">> start at (float) : %d", _msaTrackStart); +/* +UInt32 f; + FRAMES_TO_MSF(start_frame, &tTime.minute, &tTime.second, &f) + tTime.frame = 0; + MsaTimeToSu(_msaRefNum, &tTime, &SU); + debug(0, ">> start at (MsaTimeToSu) : %d", SU); +*/ + MsaPlay(_msaRefNum, _msaTrack, _msaTrackStart, msa_PBRATE_SP); + } + + _msaEndTime = _sys->get_msecs() + _msaTrackLength; +// debug(0, ">> track length : %d / end : %d", _msaTrackLength, _msaEndTime); + } +} \ No newline at end of file diff --git a/backends/PalmOS/Src/cd_msa.h b/backends/PalmOS/Src/cd_msa.h new file mode 100644 index 0000000000..fe9650c871 --- /dev/null +++ b/backends/PalmOS/Src/cd_msa.h @@ -0,0 +1,62 @@ +/* ScummVM - Scumm Interpreter + * Copyright (C) 2001 Ludvig Strigeus + * Copyright (C) 2001-2003 The ScummVM project + * + * 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. + * + * $Header$ + * + */ + + #ifndef CD_MSA_H + #define CD_MSA_H + + #include "cdaudio.h" + + class MsaCDPlayer : public CDAudio { + public: + MsaCDPlayer(OSystem *sys); + + bool init(); + void release(); + + bool poll(); + void update(); + void play(int track, int num_loops, int start_frame, int duration); + void stop(); + + private: + void initInternal(); + + OSystem *_sys; + UInt16 _msaRefNum; + + // cdrom + AlbumInfoType _msaAlbum; + UInt16 _msaLoops; + + UInt32 _msaStopTime; + UInt32 _msaEndTime; + + UInt32 _msaStartFrame; + UInt32 _msaEndFrame; + + UInt16 _msaTrack; + UInt32 _msaTrackStart; + UInt32 _msaTrackLength; + + }; + + #endif \ No newline at end of file diff --git a/backends/PalmOS/Src/cdaudio.h b/backends/PalmOS/Src/cdaudio.h new file mode 100644 index 0000000000..69ec0d7ba5 --- /dev/null +++ b/backends/PalmOS/Src/cdaudio.h @@ -0,0 +1,56 @@ +/* ScummVM - Scumm Interpreter + * Copyright (C) 2001 Ludvig Strigeus + * Copyright (C) 2001-2003 The ScummVM project + * + * 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. + * + * $Header$ + * + */ + +#ifndef CDAUDIO_H +#define CDAUDIO_H + +#include "common/system.h" + +class CDAudio { +public: + CDAudio() { + _isInitialized = false; + _volumeLevel = 100; + }; + + virtual bool init() = 0; + virtual void release() = 0; + + // OSystem functions + virtual bool poll() = 0; + virtual void play(int track, int num_loops, int start_frame, int duration) = 0; + virtual void stop() = 0; + virtual void update() = 0; + + // volume in percent + virtual void setVolume(int volume) { _volumeLevel = volume; } + virtual int getVolume() { return _volumeLevel; } + + virtual void upVolume(int value) {}; + virtual void downVolume(int value) {}; + +protected: + int _volumeLevel; + bool _isInitialized; +}; + +#endif \ No newline at end of file -- cgit v1.2.3