📄 aigenerator.cpp
字号:
#include "global.h"
#include "aigenerator.h"
//-----------------------------------------------------------------------------
// Name:
// Desc:
//-----------------------------------------------------------------------------
CAiGenerator::CAiGenerator() {
SetRect( &m_rtAvoid[0], 0, 0, 0, 0 );
m_pAim = NULL;
m_nAimProb = 0;
m_nTrackProb = 3;
m_nMaxProb = DEFMAXPROB;
m_nCurrentProb = 0;
ZeroMemory(CmdProbs, sizeof(int)*6);
m_nFireMaxProb = 16; // maybe 1 shot per step of 2 block at speed of 4
m_nFireProb = 1;
m_bLastBlock = false;
m_LastCmd.cmd = CMD_DOWN; // !!!Don't change this
m_LastCmd.fire = false;
m_LastAim = NULL;
}
//-----------------------------------------------------------------------------
// Name:
// Desc:
//-----------------------------------------------------------------------------
CAiGenerator::~CAiGenerator() {
}
//-----------------------------------------------------------------------------
// Name:
// Desc:
//-----------------------------------------------------------------------------
bool CAiGenerator::CreateGenerator( CObjTank *ptk, RECT scope ) {
m_pHost = ptk;
m_rtScope = scope;
m_LastPos = ptk->GetRect();
return true;
}
//-----------------------------------------------------------------------------
// Name:
// Desc:
//-----------------------------------------------------------------------------
void CAiGenerator::SetAim( CMobileObject *pmo, int prob ) {
m_pAim = pmo;
if ( prob < 0 )
m_nAimProb = m_nMaxProb;
else
m_nAimProb = prob;
}
//-----------------------------------------------------------------------------
// Name:
// Desc:
//-----------------------------------------------------------------------------
void CAiGenerator::SetAvoid ( RECT rt ) {
// r, d, u, l
SetRect( &m_rtAvoid[DIR_RIGHT], 0, rt.top-24, rt.left, rt.bottom-24 );
SetRect( &m_rtAvoid[DIR_DOWN], rt.left-24, 0, rt.right-24, rt.top );
SetRect( &m_rtAvoid[DIR_UP], rt.left-24, rt.top, rt.right-24, g_FrameWidth );
SetRect( &m_rtAvoid[DIR_LEFT], rt.left, rt.top-24, g_FrameWidth, rt.bottom-24 );
}
//-----------------------------------------------------------------------------
// Name:
// Desc:
//-----------------------------------------------------------------------------
TANKCMD CAiGenerator::Generator( CMobileObject **ppmos, int num )
{
TANKCMD curcmd, blockcmd;
bool analyzecmd = false;
// Test last command's effect
if ( m_LastCmd.cmd == CMD_NONE ) {
blockcmd.cmd = CMD_NONE;
analyzecmd = true;
}
else {
// straight forward
if ( m_LastPos.left != m_pHost->GetRect().left ||
m_LastPos.top != m_pHost->GetRect().top ) {
curcmd.cmd = m_LastCmd.cmd;
if ( rand() % m_nFireMaxProb < m_nFireProb ) // 1/16
curcmd.fire = true;
else
curcmd.fire = false;
m_bLastBlock = false;
}
// block just now
else if ( !m_bLastBlock ) {
m_bLastBlock = true;
curcmd.cmd = m_LastCmd.cmd;
curcmd.fire = true;
}
// block already
else {
m_bLastBlock = false;
blockcmd.cmd = m_LastCmd.cmd;
analyzecmd = true;
}
}
// Analyze a new commmand according to the aims
if ( analyzecmd ) {
POINT step = m_pHost->GetDirectionUnit();
int diff;
bool randcmd;
if ( blockcmd.cmd != CMD_NONE ) {
m_nCurrentProb = rand() % m_nMaxProb;
if ( m_pAim && m_nCurrentProb < m_nTrackProb) { // track aim
if ( step.x != 0 ) // turn up/down
{
diff = m_pAim->GetRect().top - m_pHost->GetRect().top;
if ( diff > 0 )
curcmd.cmd = CMD_DOWN;
else if ( diff < 0 )
curcmd.cmd = CMD_UP;
else
curcmd.cmd = 5 - blockcmd.cmd; // turn back
}
else if ( step.y != 0 ) // turn left/right
{
diff = m_pAim->GetRect().left - m_pHost->GetRect().left;
if ( diff > 0 )
curcmd.cmd = CMD_RIGHT;
else if ( diff < 0 )
curcmd.cmd = CMD_LEFT;
else
curcmd.cmd = 5 - blockcmd.cmd; // turn back
}
randcmd = false;
}
else { // no aim, but block
m_nCurrentProb = rand() % m_nMaxProb;
for ( int i=1; i<5; i++ ) {
if ( i != (int)blockcmd.cmd ) {
m_nCurrentProb -= m_nMaxProb/3;
if ( m_nCurrentProb <= 0 ) {
curcmd.cmd = i;
break;
}
}
}
}
} else { // no blockcmd, maybe aim
m_nCurrentProb = rand() % m_nMaxProb;
if ( m_pAim && m_nCurrentProb < m_nTrackProb) { // track aim
diff = m_pAim->GetRect().top - m_pHost->GetRect().top;
if ( diff > 0 )
curcmd.cmd = CMD_DOWN;
else if ( diff < 0 )
curcmd.cmd = CMD_UP;
else {
diff = m_pAim->GetRect().left - m_pHost->GetRect().left;
if ( diff > 0 )
curcmd.cmd = CMD_RIGHT;
else if ( diff < 0 )
curcmd.cmd = CMD_LEFT;
else {
m_nCurrentProb = rand() % m_nMaxProb;
for ( int i=1; i<5; i++ ) {
m_nCurrentProb -= m_nMaxProb/4;
if ( m_nCurrentProb <= 0 ) {
curcmd.cmd = i;
break;
}
}
}
}
} else { // no blockcmd, no aim
m_nCurrentProb = rand() % m_nMaxProb;
for ( int i=1; i<5; i++ ) {
m_nCurrentProb -= m_nMaxProb/4;
if ( m_nCurrentProb <= 0 ) {
curcmd.cmd = i;
break;
}
}
}
}
if ( rand() % m_nFireMaxProb < m_nFireProb ) // 1/16
curcmd.fire = true;
else
curcmd.fire = false;
}
// avoid beat base
if ( PtInRect( &m_rtAvoid[m_LastCmd.cmd], *(POINT *)&m_LastPos ) )
curcmd.fire = false;
// Attack nearby
// Store last values
m_LastPos = m_pHost->GetRect();
m_LastCmd = curcmd;
return m_LastCmd;
}
//-----------------------------------------------------------------------------
// Name:
// Desc:
//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
// Name:
// Desc:
//-----------------------------------------------------------------------------
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -