mirror of
https://github.com/kichikuou/xsystem35-sdl2.git
synced 2026-10-02 11:48:04 +03:00
285 lines
6.4 KiB
C
285 lines
6.4 KiB
C
/*
|
|
* nact.c シナリオデータの解析
|
|
*
|
|
* Copyright (C) 1997-1998 Masaki Chikama (Wren) <chikama@kasumi.ipl.mech.nagoya-u.ac.jp>
|
|
* 1998- <masaki-c@is.aist-nara.ac.jp>
|
|
*
|
|
* 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
|
|
*
|
|
*/
|
|
/* $Id: nact.c,v 1.24 2003/11/09 15:06:13 chikama Exp $ */
|
|
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <unistd.h>
|
|
#ifdef __EMSCRIPTEN__
|
|
#include <emscripten.h>
|
|
#endif
|
|
|
|
#include "portab.h"
|
|
#include "scenario.h"
|
|
#include "xsystem35.h"
|
|
#include "ags.h"
|
|
#include "counter.h"
|
|
#include "nact.h"
|
|
#include "selection.h"
|
|
#include "message.h"
|
|
#include "imput.h"
|
|
#include "menu.h"
|
|
|
|
/*
|
|
|
|
SCOでのコード ZH 0 ZH 1
|
|
半角カナ 全角平仮名 半角カナ
|
|
全角平仮名 全角平仮名 全角平仮名
|
|
全角片仮名 全角片仮名 半角カナ
|
|
|
|
MS コマンド: 表示時の ZH に依存, MS cali,str(:) のstrは常に全角文字が格納.
|
|
MG コマンド: 表示時の ZH に依存
|
|
|
|
*/
|
|
|
|
/* defined in hankaku.c */
|
|
extern BYTE *zen2han(BYTE *src);
|
|
extern BYTE *han2zen(BYTE *src);
|
|
/* defined by hankan2sjis.c */
|
|
extern char *hankana2sjis(int index);
|
|
/* defined by cmd_check.c */
|
|
extern void check_command(int c0);
|
|
/* defined by cmdv.c */
|
|
extern void va_animation();
|
|
/* コマンド解析時の展開バッファ */
|
|
static char msgbuf[512];
|
|
/* 半角モード */
|
|
static int msg_msgHankakuMode = 0; /* 0:全角 1:半角, 2: 無変換 */
|
|
|
|
/* ゲームシステム情報 */
|
|
static NACTINFO nactprv;
|
|
NACTINFO *nact = &nactprv;
|
|
|
|
/* メッセージの半角化 */
|
|
void sys_setHankakuMode(int mode) {
|
|
msg_msgHankakuMode = mode;
|
|
}
|
|
|
|
/* 文字列の取り出し */
|
|
char *sys_getString(char term) {
|
|
int c0;
|
|
char *index = msgbuf;
|
|
|
|
while ((c0 = sl_getc()) != (int)term) {
|
|
*index++ = c0;
|
|
}
|
|
*index = 0;
|
|
return msgbuf;
|
|
}
|
|
|
|
/* 特殊 const string */
|
|
char *sys_getConstString() {
|
|
int c0;
|
|
char *index = msgbuf;
|
|
|
|
c0 = sl_getc();
|
|
|
|
while ((c0 = sl_getc()) != 0) {
|
|
*index++ = ((c0 & 0xf0) >> 4) + ((c0 & 0x0f) << 4);
|
|
}
|
|
|
|
*index = 0;
|
|
return msgbuf;
|
|
}
|
|
|
|
/* 加工済み(半カナ->全カナ) 文字列抽出 */
|
|
char* sys_getConvString(char term) {
|
|
int c0;
|
|
char *index = msgbuf;
|
|
char *kindex;
|
|
|
|
while ((c0 = sl_getc()) != (int)term) {
|
|
if (c0 == 0x20) {
|
|
*index++ = 0x81; *index++ = 0x40;
|
|
} else if (c0 >= 0xe0) {
|
|
*index++ = (char)c0; *index++ = (char)sl_getc();
|
|
} else if (c0 >= 0xa0) {
|
|
kindex = hankana2sjis(c0);
|
|
*index++ = *kindex; *index++ = *(kindex+1);
|
|
} else {
|
|
*index++ = (char)c0; *index++ = (char)sl_getc();
|
|
}
|
|
}
|
|
*index = 0;
|
|
return msgbuf;
|
|
}
|
|
|
|
/* 選択肢・通常メッセージ振り分け */
|
|
void sys_addMsg(char *str) {
|
|
char *msg = NULL;
|
|
|
|
switch(msg_msgHankakuMode) {
|
|
case 0:
|
|
msg = han2zen(str); break;
|
|
case 1:
|
|
msg = zen2han(str); break;
|
|
case 2:
|
|
msg = str; break;
|
|
default:
|
|
return;
|
|
}
|
|
|
|
if (nact->sel.in_setting) {
|
|
// 選択肢のバッファへ
|
|
sel_addElement(msg);
|
|
} else {
|
|
// 通常のメッセージ
|
|
DEBUG_MESSAGE("%s", msg);
|
|
if (nact->is_msg_out) {
|
|
msg_putMessage(msg);
|
|
}
|
|
if (nact->msgout) {
|
|
nact->msgout(msg);
|
|
}
|
|
}
|
|
|
|
if (msg && msg_msgHankakuMode < 2) {
|
|
free(msg);
|
|
}
|
|
}
|
|
|
|
/* 文字列抽出 */
|
|
static int checkMessage() {
|
|
char *index = msgbuf;
|
|
int c0 = sl_getc();
|
|
|
|
while (c0 == 0x20 || c0 > 0x80) {
|
|
if (c0 == 0x20) {
|
|
*index++ = (char)c0;
|
|
} else if (c0 >= 0xe0) {
|
|
*index++ = (char)c0; *index++ = (char)sl_getc();
|
|
} else if (c0 >= 0xa0) {
|
|
*index++ = (char)c0;
|
|
} else {
|
|
*index++ = (char)c0; *index++ = (char)sl_getc();
|
|
}
|
|
c0 = sl_getc();
|
|
}
|
|
if (index != msgbuf) {
|
|
*index = 0;
|
|
sys_addMsg(msgbuf);
|
|
}
|
|
return c0;
|
|
}
|
|
|
|
#define MAINLOOP_EVENTCHECK_INTERVAL 16 /* 16 msec */
|
|
|
|
#ifdef __EMSCRIPTEN__
|
|
|
|
extern int cdrom_getpos_count;
|
|
|
|
static void mainloop() {
|
|
if (nact->is_quit)
|
|
emscripten_cancel_main_loop();
|
|
|
|
cdrom_getpos_count = 0;
|
|
|
|
for (int cnt = 0; cnt < 10000; cnt++) {
|
|
nact->input_state = InputNotChecked;
|
|
|
|
DEBUG_MESSAGE("%d:%x\n", sl_getPage(), sl_getIndex());
|
|
if (!nact->popupmenu_opened) {
|
|
int c0 = checkMessage();
|
|
check_command(c0);
|
|
}
|
|
nact->callback();
|
|
|
|
if (nact->input_state == InputCheckMissed)
|
|
break;
|
|
if (cdrom_getpos_count >= 2)
|
|
break;
|
|
}
|
|
if (!nact->is_message_locked && nact->input_state == InputNotChecked)
|
|
sys_getInputInfo();
|
|
sdl_updateScreen();
|
|
}
|
|
|
|
#endif // __EMSCRIPTEN__
|
|
|
|
void nact_main() {
|
|
reset_counter_high(SYSTEMCOUNTER_MSEC, 1, 0);
|
|
reset_counter_high(SYSTEMCOUNTER_MAINLOOP, MAINLOOP_EVENTCHECK_INTERVAL, 0);
|
|
#ifdef __EMSCRIPTEN__
|
|
#ifdef EMTERPRETIFY_ADVISE
|
|
// Using mainloop as a function pointer screws up EMTERPRETIFY_ADVISE!
|
|
mainloop();
|
|
#else
|
|
emscripten_set_main_loop(mainloop, 0, TRUE);
|
|
#endif
|
|
#else
|
|
int c0;
|
|
static int cnt = 0;
|
|
|
|
while (!nact->is_quit) {
|
|
#ifdef ENABLE_SDL
|
|
nact->input_state = InputNotChecked;
|
|
#endif
|
|
DEBUG_MESSAGE("%d:%x\n", sl_getPage(), sl_getIndex());
|
|
if (!nact->popupmenu_opened) {
|
|
c0 = checkMessage();
|
|
check_command(c0);
|
|
}
|
|
if (!nact->is_message_locked) {
|
|
if (get_high_counter(SYSTEMCOUNTER_MAINLOOP)) {
|
|
sys_getInputInfo();
|
|
reset_counter_high(SYSTEMCOUNTER_MAINLOOP, MAINLOOP_EVENTCHECK_INTERVAL, 0);
|
|
}
|
|
}
|
|
if (cnt == 10000) {
|
|
Sleep(1); /* XXXX */
|
|
cnt = 0;
|
|
}
|
|
cnt++;
|
|
nact->callback();
|
|
#ifdef ENABLE_SDL
|
|
if (nact->input_state == InputCheckMissed) {
|
|
sdl_updateScreen();
|
|
Sleep(10);
|
|
}
|
|
#endif
|
|
}
|
|
#endif // __EMSCRIPTEN__
|
|
}
|
|
|
|
static void nact_callback() {
|
|
if (nact->is_va_animation) {
|
|
va_animation();
|
|
}
|
|
if (nact->is_cursor_animation) {
|
|
/* cursor animation */
|
|
}
|
|
if (nact->popupmenu_opened) {
|
|
menu_gtkmainiteration();
|
|
if (nact->is_quit) sys_exit(0);
|
|
}
|
|
}
|
|
|
|
void nact_init() {
|
|
nact->sys_mouse_movesw = 2;
|
|
nact->is_quit = FALSE;
|
|
nact->is_va_animation = FALSE;
|
|
nact->is_cursor_animation = FALSE;
|
|
nact->is_message_locked = FALSE;
|
|
nact->is_msg_out = TRUE;
|
|
nact->callback = nact_callback;
|
|
}
|