www.pudn.com > ncdzsrc.rar > cdda.c
/***************************************************************************
cdda.c
NEOGEO CD CDDA制御
***************************************************************************/
#include "neogeocd.h"
#define VERBOSE OUTPUT_CDDA_LOG
#if VERBOSE
#define LOG(x) logerror x
#else
#define LOG(x)
#endif
/****************************************************************************
ローカル変数
***************************************************************************/
static int cdda_ready;
static int cdda_current_volume;
static int cdda_autoloop;
static int kof96ngc_comment_playing = 0;
static int kof96ngc_prev_track = 0;
int kof96ngc_track_list[] = {
4, // 京コメント
6, // テリー、キムコメント
8, // リョウ、大門コメント
9, // ユリコメント
11, // レオナ、香澄、バイスコメント
13, // アテナコメント
15, // チョイ、ラルフ、紅丸コメント
19, // 舞コメント
21, // キングコメント
23, // 庵コメント
25, // クラウザーコメント
27, // ギースコメント
29, // Mr.BIG コメント
31, // マチュアコメント
33, // ちづるコメント
36, // ゲーニッツ、クラークコメント
43, // アンディコメント
44, // ロバートコメント
45, // ケンスウコメント
46, // チンコメント
47, // チャンコメント
48, // ジョーNGコメント(舞)
49, // ジョー紹介(舞)
50, // ジョーコメント(アンディ)
-1
};
/***************************************************************************
グローバル関数
***************************************************************************/
/*------------------------------------------------------
CDDAの初期化
引 数: なし
戻り値: 成功=1,エラー=0
-----------------------------------------------------*/
int neogeo_cdda_init(void)
{
// 変数初期化
cdda_ready = 0;
cdda_current_volume = -1;
cdda_autoloop = 0;
if (cdrom_current_drive == -1 || !options.enable_cdda)
return 1;
if (osd_cdda_init(cdrom_current_drive) == OSD_ERROR)
{
logerror("CDDA: drive %c: could not initialize.\n", cdrom_current_drive + 'A');
return 0;
}
// ミキサーボリュームの設定
if (options.cdda_volume != -1)
{
cdda_set_volume(options.cdda_volume);
}
cdda_ready = 1;
kof96ngc_comment_playing = 0;
kof96ngc_prev_track = 0;
return 1;
}
/*------------------------------------------------------
CDDAの終了
引 数: なし
戻り値: なし
-----------------------------------------------------*/
void neogeo_cdda_exit(void)
{
if (cdda_ready)
{
osd_cdda_restore_volume();
osd_cdda_stop();
osd_cdda_exit();
cdda_current_volume = -1;
cdda_autoloop = 0;
// CDDA関連のメモリをクリア
m68000_write_memory_32(0x10f6ea, 0);
m68000_write_memory_8(0x10f678, 0);
m68000_write_memory_8(0x10f64b, 0);
m68000_write_memory_8(0x10f6f8, 0);
m68000_write_memory_8(0x10f6f7, 0);
m68000_write_memory_8(0x10f6f6, 0);
}
cdda_ready = 0;
}
/*------------------------------------------------------
CDDAのリセット
引 数: なし
戻り値: なし
-----------------------------------------------------*/
void neogeo_cdda_reset(void)
{
kof96ngc_comment_playing = 0;
kof96ngc_prev_track = 0;
if (cdda_ready)
{
osd_cdda_set_autoloop(0);
osd_cdda_stop();
}
}
/*------------------------------------------------------
CDDAのコマンド発行チェック (MC68000)
引 数: なし
戻り値: なし
-----------------------------------------------------*/
void neogeo_cdda_control(void)
{
int command = (m68000_get_reg(M68K_D0) >> 8) & 0xff;
int track = m68000_get_reg(M68K_D0) & 0xff;
offs_t offset;
if ((command & 2) == 0)
{
m68000_write_memory_8(0x108000 + 0x764b, track);
m68000_write_memory_8(0x108000 + 0x76f8, track);
m68000_write_memory_8(0x108000 + 0x76f7, command);
}
m68000_write_memory_8(0x108000 + 0x76f6, command);
if (command <= 7)
{
if ((command || track) && cdda_ready)
neogeo_cdda_post_command(command, track);
}
offset = m68000_read_memory_32(0x108000 + 0x76ea);
if (offset)
{
m68000_write_memory_8(0x108000 + 0x7678, 0x01);
if (command > 7)
{
logerror("Z80 I/O ERROR ( ID = %02x, DATA = %02x )\n",
m68000_read_memory_8(0x108000 + 0x7678), command);
}
else
{
UINT8 *mem = memory_region(REGION_CPU2);
offset = (offset - 0xe00000) >> 1;
mem[offset + 0] = 0;
mem[offset + 1] = 0;
}
}
}
/*------------------------------------------------------
CDDAのコマンド発行チェック (Z80)
引 数: なし
戻り値: なし
-----------------------------------------------------*/
void neogeo_cdda_check(void)
{
offs_t offset;
if (kof96ngc_comment_playing)
{
if (osd_cdda_get_status() == CDDA_STOP)
{
int D0 = m68000_get_reg(M68K_D0);
kof96ngc_comment_playing = 0;
m68000_set_reg(M68K_D0, kof96ngc_prev_track);
neogeo_cdda_control();
m68000_set_reg(M68K_D0, D0);
m68000_write_memory_16(0x108000 + 0x2cb8, 0x0000); // コントローラ入力受付再開
return;
}
}
offset = m68000_read_memory_32(0x108000 + 0x76ea);
if (offset)
{
UINT8 *mem = memory_region(REGION_CPU2);
UINT8 command, track;
offset = (offset - 0xe00000) >> 1;
command = mem[offset + 0];
track = mem[offset + 1];
mem[offset + 0] = 0;
mem[offset + 1] = 0;
if (command > 7)
{
logerror("Z80 I/O ERROR ( ID = %02x, DATA = %02x )\n",
m68000_read_memory_8(0x108000 + 0x7678), command);
}
else if ((command || track) && cdda_ready)
{
neogeo_cdda_post_command(command, track);
}
}
}
/*------------------------------------------------------
CDDAのコマンドを実行
引 数: int command 実行するコマンド番号
int track 再生するトラック番号
戻り値: なし
-----------------------------------------------------*/
void neogeo_cdda_post_command(int command, int track)
{
int loop, _track;
_track = track;
track = ((track >> 4) * 10) + (track & 0x0f);
loop = !(command & 1);
switch (command)
{
case 0:
case 1:
case 4:
case 5:
if (track > 1 && track <= 99)
{
if (GAME_NAME("kof96ngc"))
{
extern int kof96ngc_cdda_play_comment_track(int track);
int i = 0;
while (kof96ngc_track_list[i] != -1)
{
if (kof96ngc_track_list[i] == track)
{
kof96ngc_comment_playing = 1;
kof96ngc_cdda_play_comment_track(track);
if (track == 49) kof96ngc_prev_track = 5;
osd_cdda_set_autoloop(0);
cdda_autoloop = 0;
return;
}
i++;
}
kof96ngc_comment_playing = 0;
kof96ngc_prev_track = _track;
}
/* play */
LOG(("CDDA: command = %d track = %d / play (auto-loop:%s)\n", command, track, loop ? "on" : "off"));
if (osd_cdda_play_track(track) == OSD_ERROR)
{
logerror("CDDA: play track %d failed.\n", track);
}
else
{
osd_cdda_set_autoloop(loop);
cdda_autoloop = loop;
}
}
break;
case 2:
case 6:
if (osd_cdda_get_status() == CDDA_PLAY)
{
LOG(("CDDA: command = %d track = %d / pause\n", command, track));
osd_cdda_set_autoloop(0);
osd_cdda_pause();
}
break;
case 3:
case 7:
if (osd_cdda_get_status() == CDDA_PAUSE)
{
LOG(("CDDA: command = %d track = %d / resume\n", command, track));
osd_cdda_set_autoloop(cdda_autoloop);
osd_cdda_resume();
}
break;
}
}
/*------------------------------------------------------
CDDA停止
引 数: なし
戻り値: なし
-----------------------------------------------------*/
void neogeo_cdda_stop(void)
{
osd_cdda_stop();
kof96ngc_comment_playing = 0;
kof96ngc_prev_track = 0;
}
/*------------------------------------------------------
CDDAの音量設定
引 数: 設定する音量(0-200)
戻り値: なし
-----------------------------------------------------*/
void cdda_set_volume(int volume)
{
if (cdda_ready)
{
int new_volume = (int)(65535.0 * ((double)volume / 200.0));
if (volume != cdda_current_volume)
{
cdda_current_volume = volume;
if (volume == -1)
{
osd_cdda_restore_volume();
}
else
{
if (cdda_current_volume == -1)
osd_cdda_init_volume();
osd_cdda_set_volume(new_volume);
cdda_current_volume = volume;
}
}
}
}