chuyiwen_gmsv/npc/npc_gambleroulette.c
2017-01-14 00:37:03 +09:00

475 lines
13 KiB
C

#include "version.h"
#include <string.h>
#include "char.h"
#include "object.h"
#include "char_base.h"
#include "npcutil.h"
#include "readmap.h"
#include "lssproto_serv.h"
#include "handletime.h"
#ifdef _GAMBLE_ROULETTE
#include "npc_gambleroulette.h"
#define _OTHER_ROUND //另一种跑法
static void Gamble_Roulette_walk( int meindex);
static int Gamble_RouletteSetPoint( int meindex );
static void Find_Master( int meindex);
int RunRand( int meindex, int flg );
BOOL SetEndPoint( int meindex );
void Gamble_Roulette_Reset( int meindex, int flg);
void ResetDataStart( int meindex);
BOOL ReadPointData( int meindex );
enum {
NPC_WORK_ROUTETOX = CHAR_NPCWORKINT1,
NPC_WORK_ROUTETOY = CHAR_NPCWORKINT2,
NPC_WORK_ROUTEPOINT = CHAR_NPCWORKINT3,
NPC_WORK_ROUNDTRIP = CHAR_NPCWORKINT4,
NPC_WORK_MODE = CHAR_NPCWORKINT5,
NPC_WORK_CURRENTROUTE = CHAR_NPCWORKINT6,
NPC_WORK_ROUTEMAX = CHAR_NPCWORKINT7,
NPC_WORK_WAITTIME = CHAR_NPCWORKINT8,
NPC_WORK_CURRENTTIME = CHAR_NPCWORKINT9,
NPC_WORK_SEFLG = CHAR_NPCWORKINT10, //记录主持人index
};
typedef struct tagRoulettePoint {
int x;
int y;
int flg;
}RoulettePoint;
RoulettePoint PointData[]={
{-1,-1,-1},{-1,-1,-1},{-1,-1,-1},{-1,-1,-1},
};
RoulettePoint TestPointData[4*8];
#define ROULETTE_STANDBY 1500
#define ROULETTE_LOOPTIME 1000
#define ROULETTE_RUNTIME1 50
BOOL NPC_Gamble_RouletteInit( int meindex )
{
char argstr[NPC_UTIL_GETARGSTR_BUFSIZE];
NPC_Util_GetArgStr( meindex, argstr, sizeof( argstr));
CHAR_setInt( meindex , CHAR_WHICHTYPE , CHAR_GAMBLEROULETTE );
//CHAR_setWorkInt( meindex, NPC_WORK_ROUTEMAX, routenum);
//小猪要走几格才停
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEMAX, 0);
CHAR_setWorkInt( meindex, NPC_WORK_SEFLG, -1);
// NPC_WORK_MODE 小猪的状态 0:等待 1:走(顺)
CHAR_setWorkInt( meindex, NPC_WORK_MODE, 0);
//第几个地图点
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEPOINT, 0);
//顺向 1 逆向 0
CHAR_setWorkInt( meindex, NPC_WORK_ROUNDTRIP, 1);
//第几个路线
CHAR_setWorkInt( meindex, NPC_WORK_CURRENTROUTE, 0);
//设定LOOP TIMER
CHAR_setInt( meindex, CHAR_LOOPINTERVAL, ROULETTE_STANDBY);
//用来记录时间点
CHAR_setWorkInt( meindex, NPC_WORK_CURRENTTIME, NowTime.tv_sec);
CHAR_sendCToArroundCharacter( CHAR_getWorkInt( meindex, CHAR_WORKOBJINDEX));
if( ReadPointData( meindex) == FALSE )
return FALSE;
return TRUE;
}
void NPC_Gamble_RouletteTalked( int meindex , int talkerindex , char *szMes , int color )
{
return;
}
void NPC_Gamble_RouletteWindowTalked( int meindex, int talkerindex, int seqno, int select, char *data)
{
return;
}
void NPC_Gamble_RouletteLoop( int meindex)
{
int objmeindex = -1, index = 0, act = 0;
objmeindex = CHAR_getWorkInt( meindex, CHAR_WORKOBJINDEX);
switch( CHAR_getWorkInt( meindex, NPC_WORK_MODE )) {
case 0: //停止时等待 为等待主持人下命令
//抓主持人index 检查主持人 是否喊开始
if( CHAR_getWorkInt( meindex, NPC_WORK_SEFLG) < 0 ) {
CHAR_setWorkInt( meindex, NPC_WORK_MODE,5);
}else {
index = CHAR_getWorkInt( meindex, NPC_WORK_SEFLG);
//CHAR_NPCWORKINT7 0 null 1 准备 2 跑 3 停
if( CHAR_getWorkInt( index, CHAR_NPCWORKINT7 ) == 2 ) {
CHAR_sendCToArroundCharacter( objmeindex);
CHAR_setWorkInt( meindex, NPC_WORK_MODE,1);
CHAR_setInt( meindex, CHAR_LOOPINTERVAL, ROULETTE_RUNTIME1);
//决定小猪走几格
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEMAX, RunRand( meindex, 0 ) );
ResetDataStart( meindex);//决定进点
if( CHAR_getInt( meindex, CHAR_X) == 14 &&
CHAR_getInt( meindex, CHAR_Y) == 8 ) {
}else {
print("\n\n####################\n 小猪不在原点!![%d,%d]",
CHAR_getInt( meindex, CHAR_X),
CHAR_getInt( meindex, CHAR_Y)
);
}
}else if( CHAR_getWorkInt( index, CHAR_NPCWORKINT7 ) == 1 ||
( CHAR_getWorkInt( index, CHAR_NPCWORKINT9) < 30 &&
CHAR_getWorkInt( index, CHAR_NPCWORKINT9) > 24 )
) { //准备
if( CHAR_getInt( meindex, CHAR_X) == 14 && CHAR_getInt( meindex, CHAR_Y) == 8 ) {
}else {
CHAR_warpToSpecificPoint( meindex, CHAR_getInt( meindex, CHAR_FLOOR),
14, 8);
CHAR_setInt( meindex, CHAR_X, 14);
CHAR_setInt( meindex, CHAR_Y, 8);
CHAR_sendCToArroundCharacter( objmeindex);
}
}
}
break;
case 1:
Gamble_Roulette_walk( meindex);
break;
case 2:
break;
case 3:
//点归零
CHAR_setWorkInt( meindex, NPC_WORK_MODE, 0);
//动作
act = CHAR_ACTATTACK;
CHAR_sendWatchEvent( objmeindex, act, NULL,0, FALSE);
CHAR_setWorkInt( meindex, CHAR_WORKACTION, act);
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEMAX, 0);
CHAR_setInt( meindex, CHAR_LOOPINTERVAL, ROULETTE_STANDBY);
//送人物资料给视觉范围内的人
CHAR_sendCToArroundCharacter( objmeindex);
if( SetEndPoint( meindex ) == FALSE ) {
print("\n not Set EndPoint !!");
}
#ifdef _OTHER_ROUND
#else
ReadPointData( meindex); //load round data
#endif
//还原主持人
index = CHAR_getWorkInt( meindex, NPC_WORK_SEFLG);
CHAR_setWorkInt( index, CHAR_NPCWORKINT7, 3);
break;
case 5: //寻找主持人
Find_Master( meindex);
if( CHAR_getWorkInt( meindex, NPC_WORK_SEFLG) < 0 ) {
CHAR_setInt( meindex, CHAR_LOOPINTERVAL, 0);
CHAR_setWorkInt( meindex, NPC_WORK_MODE,-1);
}else {
CHAR_setWorkInt( meindex, NPC_WORK_MODE, 0);
}
break;
default:
//重置 错误处理
Gamble_Roulette_Reset( meindex, 0);
break;
}
}
static void Gamble_Roulette_walk( int meindex)
{
POINT start, end;
int dir;
int ret;
int i,run_num = 0;
int objmeindex = -1;
objmeindex = CHAR_getWorkInt( meindex, CHAR_WORKOBJINDEX);
start.x = CHAR_getInt( meindex, CHAR_X);
start.y = CHAR_getInt( meindex, CHAR_Y);
end.x = CHAR_getWorkInt( meindex, NPC_WORK_ROUTETOX);
end.y = CHAR_getWorkInt( meindex, NPC_WORK_ROUTETOY);
// loop timer分为两部分 1. 处理下一点 2. 走到下一点
if( start.x == end.x && start.y == end.y ) {
#ifdef _OTHER_ROUND
#else
int add = 1;
//如果为 NPC_WORK_ROUNDTRIP != 1 逆向
if( CHAR_getWorkInt( meindex, NPC_WORK_ROUNDTRIP ) != 1 ) {
add *= -1;
}
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEPOINT,
CHAR_getWorkInt( meindex, NPC_WORK_ROUTEPOINT) +add);
#endif
if( Gamble_RouletteSetPoint( meindex ) == FALSE ) {
#ifdef _OTHER_ROUND
CHAR_setWorkInt( meindex, NPC_WORK_MODE,3);
CHAR_setWorkInt( meindex, NPC_WORK_CURRENTTIME, NowTime.tv_sec);
return;
#else
if( CHAR_getWorkInt( meindex, NPC_WORK_ROUNDTRIP ) != 1 ) {
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEPOINT, arraysizeof( PointData) ); //逆向
}else {
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEPOINT, -1); //顺向
}
return;
#endif
}else {
return;
}
}
//--------------------------------------------------------------------
run_num = CHAR_getWorkInt( meindex, NPC_WORK_ROUTEMAX);
if( run_num > 0 ){
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEMAX, (run_num - 1) );
}else {
#ifdef _OTHER_ROUND
CHAR_setWorkInt( meindex, NPC_WORK_MODE,3);
CHAR_setWorkInt( meindex, NPC_WORK_CURRENTTIME, NowTime.tv_sec);
return;
#else
int npc_ai=0;
int masterindex;
masterindex = CHAR_getWorkInt( meindex, NPC_WORK_SEFLG);
npc_ai = CHAR_getWorkInt( masterindex, CHAR_NPCWORKINT3);
if( npc_ai > 10 ) {
if( start.x == 7 && start.y == 5 ) { // 7,5
CHAR_setWorkInt( masterindex, CHAR_NPCWORKINT3, 0);
}else {
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEMAX, 1);
return;
}
}
CHAR_setWorkInt( meindex, NPC_WORK_MODE,3);
CHAR_setWorkInt( meindex, NPC_WORK_CURRENTTIME, NowTime.tv_sec);
return;
#endif
}
//--------------------------------------------------------------------
dir = NPC_Util_getDirFromTwoPoint( &start,&end );
for( i = 0; i < 100; i ++ ) {
if( dir < 0 ) {
dir = RAND( 0,7);
}
dir = NPC_Util_SuberiWalk( meindex, dir);
if( dir >= 0 && dir <= 7) break;
}
if( dir >= 0 && dir <= 7 ) {
ret = CHAR_walk( meindex, dir, 0);
}
}
static void Find_Master( int meindex)
{
int floor, x=14, y=3;
OBJECT object;
floor = CHAR_getInt( meindex , CHAR_FLOOR);
for( object = MAP_getTopObj( floor, x, y) ; object ; object = NEXT_OBJECT(object ) ){
int findex;
int objindex = GET_OBJINDEX(object);
if( !CHECKOBJECTUSE( objindex)) continue;
findex = OBJECT_getIndex( objindex);
if( !CHAR_CHECKINDEX( findex)) continue;
if( CHAR_getInt( findex , CHAR_WHICHTYPE ) != CHAR_GAMBLEMASTER ) continue;
if( CHAR_getWorkInt( findex, CHAR_NPCWORKINT8) != 10001 ) continue;
CHAR_setWorkInt( meindex, NPC_WORK_SEFLG, findex) ;
return;
}
}
int RunRand( int meindex, int flg )
{
#define RAND(x,y) ((x-1)+1+ (int)( (double)(y-(x-1))*rand()/(RAND_MAX+1.0)) )
int run_num1=0;
int i;
run_num1 = RAND( 90, 150);
for( i=0; i<6; i++ ) {
run_num1 += RAND( 0, 20);
}
return run_num1;
}
BOOL SetEndPoint( int meindex )
{
int x,y;
int master;
int endpoint;
master = CHAR_getWorkInt( meindex, NPC_WORK_SEFLG);
if( !CHAR_CHECKINDEX( master) )
return FALSE;
if( CHAR_getWorkInt( master, CHAR_NPCWORKINT7) != 2 ) {
print("\n error( master,CHAR_NPCWORKINT7) != 2 ");
return FALSE;
}
x = CHAR_getInt( meindex, CHAR_X);
y = CHAR_getInt( meindex, CHAR_Y);
endpoint = (x<<16)+(y<<0);
CHAR_setWorkInt( master, CHAR_NPCWORKINT10, endpoint);
return TRUE;
}
void Gamble_Roulette_Reset( int meindex, int flg)
{
//错误处理
int index;
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEMAX, 0);
CHAR_setWorkInt( meindex, NPC_WORK_MODE, 0);
CHAR_setInt( meindex, CHAR_LOOPINTERVAL, ROULETTE_STANDBY);
index = CHAR_getWorkInt( meindex, NPC_WORK_SEFLG);
if( !CHAR_CHECKINDEX( index) ) {
print("\n Gamble_Roulette error: no master !!");
return;
}
CHAR_setWorkInt( index, CHAR_NPCWORKINT7, 3);
CHAR_setWorkInt( index, CHAR_NPCWORKINT10, 0);
}
void ResetDataStart( int meindex )
{
#define RAND(x,y) ((x-1)+1+ (int)( (double)(y-(x-1))*rand()/(RAND_MAX+1.0)) )
int Start=1;
struct tagWalkStartPoint{
int x;
int y;
int rip;
}WalkStart[]={
{7,5,1}, {7,11,0}, {22,11,1}, {22,5,0},
};
Start = RAND( 0, 3);
CHAR_setWorkInt( meindex, NPC_WORK_ROUNDTRIP, WalkStart[Start].rip );
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEPOINT, Start);
CHAR_setWorkInt( meindex, NPC_WORK_ROUTETOX, WalkStart[Start].x );
CHAR_setWorkInt( meindex, NPC_WORK_ROUTETOY, WalkStart[Start].y );
{
int i=0,k;
int RIP = CHAR_getWorkInt( meindex, NPC_WORK_ROUNDTRIP);
k = CHAR_getWorkInt( meindex, NPC_WORK_ROUTEPOINT);
if( RIP ) {
while( i < (arraysizeof( TestPointData))) {
k++;
if( k > 3 ) k = 0;
TestPointData[i].x = PointData[k].x;
TestPointData[i].y = PointData[k].y;
i++;
}
}else {
while( i < (arraysizeof( TestPointData))) {
k--;
if( k < 0 ) k = 3;
TestPointData[i].x = PointData[k].x;
TestPointData[i].y = PointData[k].y;
i++;
}
}
}
#ifdef _OTHER_ROUND
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEPOINT, 0);
#endif
}
BOOL ReadPointData( int meindex )
{
char buf1[256], buf2[32], buf3[16];
char argstr[NPC_UTIL_GETARGSTR_BUFSIZE];
int k=1,i=0;
NPC_Util_GetArgStr( meindex, argstr, sizeof( argstr));
if( NPC_Util_GetStrFromStrWithDelim( argstr, "roulette",buf1, sizeof(buf1)) == NULL ) {
print("\n roulette error: not found !!");
return FALSE;
}
k=1;
while( getStringFromIndexWithDelim( buf1, ";", k, buf2, sizeof(buf2) ) != FALSE ) {
k++;
if( strstr( buf2,",") == NULL )
continue;
if( getStringFromIndexWithDelim( buf2, ",", 1, buf3, sizeof(buf3)) == FALSE) {
return FALSE;
}
PointData[i].x = atoi( buf3);
if( getStringFromIndexWithDelim( buf2, ",", 2, buf3, sizeof(buf3)) == FALSE) {
return FALSE;
}
PointData[i].y = atoi( buf3);
if( i > 9 ) {
break;
}
i++;
}
#ifdef _OTHER_ROUND
#else
Gamble_RouletteSetPoint( meindex);
#endif
return TRUE;//arraysizeof( PointData)
}
static int Gamble_RouletteSetPoint( int meindex )
{
#ifdef _OTHER_ROUND
int i;
i = CHAR_getWorkInt( meindex, NPC_WORK_ROUTEPOINT);
CHAR_setWorkInt( meindex, NPC_WORK_ROUTETOX, TestPointData[i].x );
CHAR_setWorkInt( meindex, NPC_WORK_ROUTETOY, TestPointData[i].y );
i++;
CHAR_setWorkInt( meindex, NPC_WORK_ROUTEPOINT, i);
if( i >= arraysizeof( TestPointData) ) {
return FALSE;
}
#else
int i;
i = CHAR_getWorkInt( meindex, NPC_WORK_ROUTEPOINT);
if( i<0 || i>arraysizeof( PointData) -1) {
return FALSE;
}
CHAR_setWorkInt( meindex, NPC_WORK_ROUTETOX, PointData[i].x );
CHAR_setWorkInt( meindex, NPC_WORK_ROUTETOY, PointData[i].y );
#endif
{//检查路线
struct tagWalkStartPoint{
int x;
int y;
}WalkStart[]={
{22,5}, {7,5}, {7,11}, {22,11}, {22,5}, {7,5}
};
int ch_x,ch_y;
int next_x,next_y;
int h;
ch_x = CHAR_getInt( meindex, CHAR_X);
ch_y = CHAR_getInt( meindex, CHAR_Y);
for( h=1; h<5; h++) {
if( ch_x == WalkStart[h].x &&
ch_y == WalkStart[h].y) {
next_x = CHAR_getWorkInt( meindex, NPC_WORK_ROUTETOX);
next_y = CHAR_getWorkInt( meindex, NPC_WORK_ROUTETOY);
if( next_x == WalkStart[h+1].x &&
next_y == WalkStart[h+1].y) {
}else if( next_x == WalkStart[h-1].x &&
next_y == WalkStart[h-1].y) {
}else {
print("\n ##############################");
print("\n ERR : [%d,%d] -> [%d,%d]",ch_x,ch_y,next_x,next_y);
}
break;
}
}
}
return TRUE;
}
#endif