mirror of
https://github.com/libretro/scummvm.git
synced 2025-01-16 06:49:58 +00:00
fd6ace361c
svn-id: r10373
312 lines
8.9 KiB
C++
312 lines
8.9 KiB
C++
/* 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 <SonyClie.h>
|
|
|
|
#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);
|
|
}
|
|
} |